source: trunk/GSASII.py @ 428

Last change on this file since 428 was 428, checked in by vondreele, 11 years ago

begin something for plotting size & PO figures as well as mustrain
allow sorting of the indexing result by volume
fix weights for "STD" GSAS powder data files

  • Property svn:keywords set to Date Author Revision URL Id
File size: 76.7 KB
Line 
1#!/usr/bin/env python
2# -*- coding: utf-8 -*-
3#GSASII
4########### SVN repository information ###################
5# $Date: 2011-11-22 21:59:22 +0000 (Tue, 22 Nov 2011) $
6# $Author: vondreele $
7# $Revision: 428 $
8# $URL: trunk/GSASII.py $
9# $Id: GSASII.py 428 2011-11-22 21:59:22Z vondreele $
10########### SVN repository information ###################
11
12import os
13import os.path as ospath
14import sys
15import math
16import cPickle
17import time
18import copy
19import numpy as np
20import scipy as sp
21import wx
22import matplotlib as mpl
23
24# load the GSAS routines
25import GSASIIpath
26import GSASIIIO as G2IO
27import GSASIIgrid as G2gd
28import GSASIIplot as G2plt
29import GSASIIpwdGUI as G2pdG
30import GSASIIspc as G2spc
31import GSASIIstruct as G2str
32import GSASIImapvars as G2mv
33import GSASIIsolve as G2sol
34import OpenGL as ogl
35
36# print versions
37print "Available python module versions for GSASII:"
38print "python:     ",sys.version[:5]
39print "wxpython:   ",wx.__version__
40print "matplotlib: ",mpl.__version__
41print "numpy:      ",np.__version__
42print "scipy:      ",sp.__version__
43print "OpenGL:     ",ogl.__version__
44try:
45    import mkl
46    print "Max threads ",mkl.get_max_threads()
47except:
48    print "MKL module not present"
49__version__ = '0.1.5'
50G2gd.__version__ = __version__
51print "This is GSAS-II version:     ",__version__
52
53# useful degree trig functions
54sind = lambda x: math.sin(x*math.pi/180.)
55cosd = lambda x: math.cos(x*math.pi/180.)
56tand = lambda x: math.tan(x*math.pi/180.)
57asind = lambda x: 180.*math.asin(x)/math.pi
58acosd = lambda x: 180.*math.acos(x)/math.pi
59atan2d = lambda x,y: 180.*math.atan2(y,x)/math.pi
60
61def create(parent):
62    return GSASII(parent)
63
64[wxID_PATTERNTREE, 
65] = [wx.NewId() for _init_ctrls in range(1)]
66
67[wxID_FILECLOSE, wxID_FILEEXIT, wxID_FILEOPEN,  wxID_FILESAVE, wxID_FILESAVEAS, 
68wxID_REFINE, wxID_SOLVE, wxID_MAKEPDFS, wxID_VIEWLSPARMS, wxID_SEQREFINE,
69] = [wx.NewId() for _init_coll_File_Items in range(10)]
70
71[wxID_PWDRREAD,wxID_SNGLREAD,wxID_ADDPHASE,wxID_DELETEPHASE,
72 wxID_DATADELETE,wxID_READPEAKS,wxID_PWDSUM,wxID_IMGREAD,
73 wxID_IMSUM, wxID_DATARENAME,
74] = [wx.NewId() for _init_coll_Data_Items in range(10)]
75
76[wxID_IMPORT, wxID_IMPORTPATTERN, wxID_IMPORTHKL, wxID_IMPORTPHASE,
77wxID_IMPORTCIF, wxID_IMPORTPDB, 
78] = [wx.NewId() for _init_coll_Import_Items in range(6)]
79
80[wxID_EXPORT, wxID_EXPORTPATTERN, wxID_EXPORTHKL, wxID_EXPORTPHASE,
81wxID_EXPORTCIF, wxID_EXPORTPEAKLIST, wxID_EXPORTPDF,
82] = [wx.NewId() for _init_coll_Export_Items in range(7)]
83
84class GSASII(wx.Frame):
85   
86    def _init_coll_GSASIIMenu_Menus(self, parent):
87        parent.Append(menu=self.File, title='File')
88        parent.Append(menu=self.Data, title='Data')
89        parent.Append(menu=self.Calculate, title='Calculate')
90        parent.Append(menu=self.Import, title='Import')
91        parent.Append(menu=self.Export, title='Export')
92        parent.Append(menu=G2gd.MyHelp(self,helpType='Data tree'),title='&Help' )
93
94    def _init_coll_File_Items(self, parent):
95        parent.Append(help='Open a gsasii project file (*.gpx)', id=wxID_FILEOPEN,
96             kind=wx.ITEM_NORMAL,text='Open project...')
97        parent.Append(help='Save project to old file', id=wxID_FILESAVE, 
98            kind=wx.ITEM_NORMAL,text='Save project')
99        parent.Append(help='Save project to new file', id=wxID_FILESAVEAS, 
100            kind=wx.ITEM_NORMAL,text='Save As...')
101        parent.Append(help='Close project, saving is optional', id=wxID_FILECLOSE, 
102            kind=wx.ITEM_NORMAL,text='Close project')
103        parent.Append(help='Exit from gsasii', id=wxID_FILEEXIT, kind=wx.ITEM_NORMAL,
104            text='Exit')
105        self.Bind(wx.EVT_MENU, self.OnFileOpen, id=wxID_FILEOPEN)
106        self.Bind(wx.EVT_MENU, self.OnFileSave, id=wxID_FILESAVE)
107        self.Bind(wx.EVT_MENU, self.OnFileSaveas, id=wxID_FILESAVEAS)
108        self.Bind(wx.EVT_MENU, self.OnFileClose, id=wxID_FILECLOSE)
109        self.Bind(wx.EVT_MENU, self.OnFileExit, id=wxID_FILEEXIT)
110       
111    def _init_coll_Data_Items(self,parent):
112        parent.Append(help='', id=wxID_PWDRREAD, kind=wx.ITEM_NORMAL,
113            text='Read powder data...')
114        parent.Append(help='',id=wxID_IMGREAD, kind=wx.ITEM_NORMAL,
115            text='Read image data...')
116        parent.Append(help='',id=wxID_READPEAKS, kind=wx.ITEM_NORMAL,
117            text='Read Powder Pattern Peaks...')
118        parent.Append(help='', id=wxID_SNGLREAD, kind=wx.ITEM_NORMAL,
119            text='Read single crystal data...')
120        parent.Append(help='', id=wxID_PWDSUM, kind=wx.ITEM_NORMAL,
121            text='Sum powder data')
122        parent.Append(help='',id=wxID_IMSUM, kind=wx.ITEM_NORMAL,
123            text='Sum image data')
124        parent.Append(help='', id=wxID_ADDPHASE, kind=wx.ITEM_NORMAL,
125            text='Add phase')
126        parent.Append(help='', id=wxID_DELETEPHASE, kind=wx.ITEM_NORMAL,
127            text='Delete phase')
128        parent.Append(help='', id=wxID_DATARENAME, kind=wx.ITEM_NORMAL,
129            text='Rename data') 
130        parent.Append(help='', id=wxID_DATADELETE, kind=wx.ITEM_NORMAL,
131            text='Delete data')
132        self.Bind(wx.EVT_MENU, self.OnPwdrRead, id=wxID_PWDRREAD)
133        self.Bind(wx.EVT_MENU, self.OnPwdrSum, id=wxID_PWDSUM)
134        self.Bind(wx.EVT_MENU, self.OnReadPowderPeaks, id=wxID_READPEAKS)
135        self.Bind(wx.EVT_MENU, self.OnImageRead, id=wxID_IMGREAD)
136        self.Bind(wx.EVT_MENU, self.OnImageSum, id=wxID_IMSUM)
137        self.Bind(wx.EVT_MENU, self.OnSnglRead, id=wxID_SNGLREAD)
138        self.Bind(wx.EVT_MENU, self.OnAddPhase, id=wxID_ADDPHASE)
139        self.Bind(wx.EVT_MENU, self.OnDeletePhase, id=wxID_DELETEPHASE)
140        self.Bind(wx.EVT_MENU, self.OnRenameData, id=wxID_DATARENAME)
141        self.Bind(wx.EVT_MENU, self.OnDataDelete, id=wxID_DATADELETE)
142               
143    def _init_coll_Calculate_Items(self,parent):
144        self.MakePDF = parent.Append(help='Make new PDFs from selected powder patterns', 
145            id=wxID_MAKEPDFS, kind=wx.ITEM_NORMAL,text='Make new PDFs')
146        self.Bind(wx.EVT_MENU, self.OnMakePDFs, id=wxID_MAKEPDFS)
147        self.ViewLSParms = parent.Append(help='View least squares parameters', 
148            id=wxID_VIEWLSPARMS, kind=wx.ITEM_NORMAL,text='View LS parms')
149        self.Bind(wx.EVT_MENU, self.OnViewLSParms, id=wxID_VIEWLSPARMS)
150        self.Refine = parent.Append(help='', id=wxID_REFINE, kind=wx.ITEM_NORMAL,
151            text='Refine')
152        self.Refine.Enable(False)
153        self.Bind(wx.EVT_MENU, self.OnRefine, id=wxID_REFINE)
154        self.SeqRefine = parent.Append(help='', id=wxID_SEQREFINE, kind=wx.ITEM_NORMAL,
155            text='Sequental refine')
156        self.SeqRefine.Enable(False)
157        self.Bind(wx.EVT_MENU, self.OnSeqRefine, id=wxID_SEQREFINE)
158        self.Solve = parent.Append(help='', id=wxID_SOLVE, kind=wx.ITEM_NORMAL,
159            text='Solve')
160        self.Solve.Enable(False)
161        self.Bind(wx.EVT_MENU, self.OnSolve, id=wxID_SOLVE)
162       
163    def _init_coll_Import_Items(self,parent):
164        self.ImportPhase = parent.Append(help='Import phase data from GSAS EXP file',
165            id=wxID_IMPORTPHASE, kind=wx.ITEM_NORMAL,text='Import GSAS EXP Phase...')
166        self.ImportPDB = parent.Append(help='Import phase data from PDB file',
167            id=wxID_IMPORTPDB, kind=wx.ITEM_NORMAL,text='Import PDB Phase...')
168        self.ImportCIF = parent.Append(help='Import phase data from cif file',id=wxID_IMPORTCIF, kind=wx.ITEM_NORMAL,
169            text='Import CIF Phase...')
170        self.ImportPattern = parent.Append(help='',id=wxID_IMPORTPATTERN, kind=wx.ITEM_NORMAL,
171            text='Import Powder Pattern...')
172        self.ImportHKL = parent.Append(help='',id=wxID_IMPORTHKL, kind=wx.ITEM_NORMAL,
173            text='Import HKLs...')
174        self.Bind(wx.EVT_MENU, self.OnImportPhase, id=wxID_IMPORTPHASE)
175        self.Bind(wx.EVT_MENU, self.OnImportPDB, id=wxID_IMPORTPDB)
176        self.Bind(wx.EVT_MENU, self.OnImportCIF, id=wxID_IMPORTCIF)
177        self.Bind(wx.EVT_MENU, self.OnImportPattern, id=wxID_IMPORTPATTERN)
178        self.Bind(wx.EVT_MENU, self.OnImportHKL, id=wxID_IMPORTHKL)
179
180    def _init_coll_Export_Items(self,parent):
181        self.ExportPattern = parent.Append(help='Select PWDR item to enable',id=wxID_EXPORTPATTERN, kind=wx.ITEM_NORMAL,
182            text='Export Powder Patterns...')
183        self.ExportPeakList = parent.Append(help='',id=wxID_EXPORTPEAKLIST, kind=wx.ITEM_NORMAL,
184            text='Export All Peak Lists...')
185        self.ExportHKL = parent.Append(help='',id=wxID_EXPORTHKL, kind=wx.ITEM_NORMAL,
186            text='Export HKLs...')
187        self.ExportPDF = parent.Append(help='Select PDF item to enable',id=wxID_EXPORTPDF, kind=wx.ITEM_NORMAL,
188            text='Export PDF...')
189        self.ExportPhase = parent.Append(help='',id=wxID_EXPORTPHASE, kind=wx.ITEM_NORMAL,
190            text='Export Phase...')
191        self.ExportCIF = parent.Append(help='',id=wxID_EXPORTCIF, kind=wx.ITEM_NORMAL,
192            text='Export CIF...')
193        self.ExportPattern.Enable(False)
194        self.ExportPeakList.Enable(True)
195        self.ExportHKL.Enable(False)
196        self.ExportPDF.Enable(False)
197        self.ExportPhase.Enable(False)
198        self.ExportCIF.Enable(False)
199        self.Bind(wx.EVT_MENU, self.OnExportPatterns, id=wxID_EXPORTPATTERN)
200        self.Bind(wx.EVT_MENU, self.OnExportPeakList, id=wxID_EXPORTPEAKLIST)
201        self.Bind(wx.EVT_MENU, self.OnExportHKL, id=wxID_EXPORTHKL)
202        self.Bind(wx.EVT_MENU, self.OnExportPDF, id=wxID_EXPORTPDF)
203        self.Bind(wx.EVT_MENU, self.OnExportPhase, id=wxID_EXPORTPHASE)
204        self.Bind(wx.EVT_MENU, self.OnExportCIF, id=wxID_EXPORTCIF)
205               
206    def _init_utils(self):
207        self.GSASIIMenu = wx.MenuBar()
208        self.File = wx.Menu(title='')
209        self.Data = wx.Menu(title='')       
210        self.Calculate = wx.Menu(title='')       
211        self.Import = wx.Menu(title='')       
212        self.Export = wx.Menu(title='')       
213
214        self._init_coll_GSASIIMenu_Menus(self.GSASIIMenu)
215        self._init_coll_File_Items(self.File)
216        self._init_coll_Data_Items(self.Data)
217        self._init_coll_Calculate_Items(self.Calculate)
218        self._init_coll_Import_Items(self.Import)
219        self._init_coll_Export_Items(self.Export)
220       
221    def _init_ctrls(self, parent):
222        wx.Frame.__init__(self, name='GSASII', parent=parent,
223            size=wx.Size(300, 250),style=wx.DEFAULT_FRAME_STYLE, title='GSAS-II data tree')
224        clientSize = wx.ClientDisplayRect()
225        Size = self.GetSize()
226        xPos = clientSize[2]-Size[0]
227        self.SetPosition(wx.Point(xPos,clientSize[1]))
228        self._init_utils()
229        self.SetMenuBar(self.GSASIIMenu)
230        self.Bind(wx.EVT_SIZE, self.OnSize)
231        self.CreateStatusBar()
232        self.mainPanel = wx.Panel(self,-1)
233       
234        self.PatternTree = wx.TreeCtrl(id=wxID_PATTERNTREE,
235            parent=self.mainPanel, pos=wx.Point(0, 0),style=wx.TR_DEFAULT_STYLE )
236        self.PatternTree.Bind(wx.EVT_TREE_SEL_CHANGED,
237            self.OnPatternTreeSelChanged, id=wxID_PATTERNTREE)
238        self.PatternTree.Bind(wx.EVT_TREE_ITEM_COLLAPSED,
239            self.OnPatternTreeItemCollapsed, id=wxID_PATTERNTREE)
240        self.PatternTree.Bind(wx.EVT_TREE_ITEM_EXPANDED,
241            self.OnPatternTreeItemExpanded, id=wxID_PATTERNTREE)
242        self.PatternTree.Bind(wx.EVT_TREE_DELETE_ITEM,
243            self.OnPatternTreeItemDelete, id=wxID_PATTERNTREE)
244        self.root = self.PatternTree.AddRoot('Loaded Data: ')
245       
246        plotFrame = wx.Frame(None,-1,'GSASII Plots',size=wx.Size(700,600), \
247            style=wx.DEFAULT_FRAME_STYLE ^ wx.CLOSE_BOX)
248        self.G2plotNB = G2plt.G2PlotNoteBook(plotFrame)
249        plotFrame.Show()
250       
251        self.dataDisplay = None
252       
253    def __init__(self, parent):
254        self._init_ctrls(parent)
255        self.Bind(wx.EVT_CLOSE, self.ExitMain)
256        # various defaults
257        self.GSASprojectfile = ''
258        self.dirname = ''
259        self.undofile = ''
260        self.TreeItemDelete = False
261        self.Offset = [0.0,0.0]
262        self.delOffset = .02
263        self.refOffset = -100.0
264        self.refDelt = .01
265        self.Weight = False
266        self.IparmName = ''
267        self.IfPlot = False
268        self.PatternId = 0
269        self.PickId = 0
270        self.PeakTable = []
271        self.LimitsTable = []
272        self.HKL = []
273        self.Lines = []
274        self.itemPicked = None
275        self.dataFrame = None
276        self.Interpolate = 'nearest'
277        self.ContourColor = 'Paired'
278        self.VcovColor = 'RdYlGn'
279        self.Projection = 'equal area'
280        self.logPlot = False
281        self.qPlot = False
282        self.Contour = False
283        self.Legend = False
284        self.SinglePlot = False
285        self.plotView = 0
286        self.Image = 0
287        self.oldImagefile = ''
288        self.Integrate = 0
289        self.Pwdr = False
290        self.imageDefault = {}
291        self.Sngl = 0
292        self.ifGetRing = False
293        self.setPoly = False
294        arg = sys.argv
295        if len(arg) > 1:
296            self.GSASprojectfile = arg[1]
297            self.dirname = ospath.dirname(arg[1])
298            G2IO.ProjFileOpen(self)
299            self.PatternTree.Expand(self.root)
300            self.Refine.Enable(True)
301            self.SeqRefine.Enable(True)
302            self.Solve.Enable(True)
303
304    def OnSize(self,event):
305        w,h = self.GetClientSizeTuple()
306        self.mainPanel.SetSize(wx.Size(w,h))
307        self.PatternTree.SetSize(wx.Size(w,h))
308                       
309    def OnPatternTreeSelChanged(self, event):
310        if self.TreeItemDelete:
311            self.TreeItemDelete = False
312        else:
313            pltNum = self.G2plotNB.nb.GetSelection()
314            if pltNum >= 0:                         #to avoid the startup with no plot!
315                pltPage = self.G2plotNB.nb.GetPage(pltNum)
316                pltPlot = pltPage.figure
317            item = event.GetItem()
318            G2gd.MovePatternTreeToGrid(self,item)
319       
320    def OnPatternTreeItemCollapsed(self, event):
321        event.Skip()
322
323    def OnPatternTreeItemExpanded(self, event):
324        event.Skip()
325       
326    def OnPatternTreeItemDelete(self, event):
327        self.TreeItemDelete = True
328
329    def OnPatternTreeItemActivated(self, event):
330        event.Skip()
331               
332    def OnPwdrRead(self, event):
333        self.CheckNotebook()
334        dlg = wx.FileDialog(self, 'Choose files', '.', '', 
335            'GSAS fxye files (*.fxye)|*.fxye|GSAS fxy files (*.fxy)|*.fxy|Topas xye files (*.xye)|*.xye|All files (*.*)|*.*', 
336            wx.OPEN | wx.MULTIPLE)
337        if self.dirname: dlg.SetDirectory(self.dirname)
338        try:
339            if dlg.ShowModal() == wx.ID_OK:
340                filenames = dlg.GetPaths()
341                filenames.sort()
342                self.dirname = dlg.GetDirectory()
343                for filename in filenames:
344                    Data,Iparm,Comments,Temperature = G2IO.SelectPowderData(self, filename)              #Data: list of tuples (filename,Pos,Bank)
345                    if not Data:                                                    #if Data rejected by user - go to next one
346                        continue
347                    DataType = Iparm['INS   HTYPE ']                                #expect only 4 char string
348                    DataType = DataType.strip()[0:3]                                #just 1st 3 chars
349                    wx.BeginBusyCursor()
350                    Sample = G2pdG.SetDefaultSample()
351                    Sample['Temperature'] = Temperature
352                    try:
353                        for Item in Data:
354                            vals = Item[2].split()          #split up the BANK record
355                            Id = self.PatternTree.AppendItem(parent=self.root,text='PWDR '+ospath.basename(Item[0])+': '+vals[0]+vals[1])
356                            data = G2IO.GetPowderData(filename,Item[1],Item[2],DataType)
357                            self.PatternTree.SetItemPyData(Id,[Item,data])
358                            '''
359                            Each tree item data is a list with:
360                            Item: the (filename,Pos,Bank) tuple
361                            data: (x,y,w,yc,yb,yd) list  of np.arrays from GetPowderData
362                            '''
363                           
364                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Comments'),Comments)                           
365                            Tmin = min(data[0])
366                            Tmax = max(data[0])
367                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Limits'),[(Tmin,Tmax),[Tmin,Tmax]])
368                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Background'),[['chebyschev',1,3,1.0,0.0,0.0]])
369       
370                            data = [DataType,]
371                            if 'C' in DataType:
372                                s = Iparm['INS  1 ICONS']
373                                v = (G2IO.sfloat(s[:10]),G2IO.sfloat(s[10:20]),G2IO.sfloat(s[20:30]),G2IO.sfloat(s[55:65]),G2IO.sfloat(s[40:50])) #get lam1, lam2, zero, pola & ratio
374                                if not v[1]:
375                                    names = ['Type','Lam','Zero','Polariz.','U','V','W','X','Y','SH/L','Azimuth'] 
376                                    v = (v[0],v[2],v[4])
377                                    codes = [0,0,0,0]
378                                else:
379                                    names = ['Type','Lam1','Lam2','Zero','I(L2)/I(L1)','Polariz.','U','V','W','X','Y','SH/L','Azimuth']
380                                    codes = [0,0,0,0,0,0]
381                                data.extend(v)
382                                v1 = Iparm['INS  1PRCF1 '].split()                                                 
383                                v = Iparm['INS  1PRCF11'].split()
384                                data.extend([float(v[0]),float(v[1]),float(v[2])])                  #get GU, GV & GW - always here
385                                try:
386                                    azm = float(Iparm['INS  1DETAZM'])
387                                except KeyError:                                                #not in this Iparm file
388                                    azm = 0.0
389                                v = Iparm['INS  1PRCF12'].split()
390                                if v1[0] == 3:
391                                    data.extend([float(v[0]),float(v[1]),float(v[2])+float(v[3],azm)])  #get LX, LY, S+H/L & azimuth
392                                else:
393                                    data.extend([0.0,0.0,0.002,azm])                                      #OK defaults if fxn #3 not 1st in iprm file
394                                codes.extend([0,0,0,0,0,0,0])
395                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Instrument Parameters'),[tuple(data),data,codes,names])
396                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Sample Parameters'),Sample)
397                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Peak List'),[])
398                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Index Peak List'),[])
399                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Unit Cells List'),[])
400                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Reflection Lists'),{})             
401                            self.PatternId = G2gd.GetPatternTreeItemId(self,Id,'Limits')
402                    finally:
403                        wx.EndBusyCursor()
404                self.PatternTree.Expand(Id)
405                self.PatternTree.SelectItem(Id)
406   
407        finally:
408            dlg.Destroy()
409       
410    def OnReadPowderPeaks(self,event):
411        Cuka = 1.54052
412        self.CheckNotebook()
413        dlg = wx.FileDialog(self, 'Choose file with peak list', '.', '', 
414            'peak files (*.txt)|*.txt|All files (*.*)|*.*',wx.OPEN)
415        if self.dirname:
416            dlg.SetDirectory(self.dirname)
417        try:
418            if dlg.ShowModal() == wx.ID_OK:
419                self.HKL = []
420                self.powderfile = dlg.GetPath()
421                self.dirname = dlg.GetDirectory()
422                comments,peaks = G2IO.GetPowderPeaks(self.powderfile)
423                Id = self.PatternTree.AppendItem(parent=self.root,text='PKS '+ospath.basename(self.powderfile))
424                data = ['PKS',Cuka,0.0]
425                names = ['Type','Lam','Zero'] 
426                codes = [0,0]
427                self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Instrument Parameters'),[tuple(data),data,codes,names])
428                self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Comments'),comments)
429                self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Index Peak List'),peaks)
430                self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Unit Cells List'),[])             
431                self.PatternTree.Expand(Id)
432                self.PatternTree.SelectItem(Id)
433        finally:
434            dlg.Destroy()
435           
436    def OnImageRead(self,event):
437        self.CheckNotebook()
438        dlg = wx.FileDialog(self, 'Choose image files', '.', '',\
439        'Any image file (*.tif;*.tiff;*.mar*;*.avg;*.sum;*.img;*.G2img)\
440        |*.tif;*.tiff;*.mar*;*.avg;*.sum;*.img;*.G2img|\
441        Any detector tif (*.tif;*.tiff)|*.tif;*.tiff|\
442        MAR file (*.mar*)|*.mar*|\
443        GE Image (*.avg;*.sum)|*.avg;*.sum|\
444        ADSC Image (*.img)|*.img|\
445        GSAS-II Image (*.G2img)|*.G2img|\
446        All files (*.*)|*.*',
447        wx.OPEN | wx.MULTIPLE)
448        if self.dirname:
449            dlg.SetDirectory(self.dirname)
450        try:
451            if dlg.ShowModal() == wx.ID_OK:
452                self.dirname = dlg.GetDirectory()
453                imagefiles = dlg.GetPaths()
454                imagefiles.sort()
455                for imagefile in imagefiles:
456                    Comments,Data,Npix,Image = G2IO.GetImageData(self,imagefile)
457                    if Comments:
458                        Id = self.PatternTree.AppendItem(parent=self.root,text='IMG '+ospath.basename(imagefile))
459                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Comments'),Comments)
460                        Imax = np.amax(Image)
461                        Imin = max(0.0,np.amin(Image))          #force positive
462                        if self.imageDefault:
463                            Data = copy.copy(self.imageDefault)
464                            Data['showLines'] = True
465                            Data['ring'] = []
466                            Data['rings'] = []
467                            Data['cutoff'] = 10
468                            Data['pixLimit'] = 20
469                            Data['edgemin'] = 100000000
470                            Data['calibdmin'] = 0.5
471                            Data['calibskip'] = 0
472                            Data['ellipses'] = []
473                            Data['calibrant'] = ''
474                        else:
475                            Data['type'] = 'PWDR'
476                            Data['color'] = 'binary'
477                            Data['tilt'] = 0.0
478                            Data['rotation'] = 0.0
479                            Data['showLines'] = False
480                            Data['ring'] = []
481                            Data['rings'] = []
482                            Data['cutoff'] = 10
483                            Data['pixLimit'] = 20
484                            Data['calibdmin'] = 0.5
485                            Data['calibskip'] = 0
486                            Data['edgemin'] = 100000000
487                            Data['ellipses'] = []
488                            Data['calibrant'] = ''
489                            Data['IOtth'] = [2.0,5.0]
490                            Data['LRazimuth'] = [-135,-45]
491                            Data['azmthOff'] = 0.0
492                            Data['outChannels'] = 2500
493                            Data['outAzimuths'] = 1
494                            Data['fullIntegrate'] = False
495                            Data['setRings'] = False
496                            Data['background image'] = ['',1.0]                           
497                        Data['setDefault'] = False
498                        Data['range'] = [(Imin,Imax),[Imin,Imax]]
499                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Image Controls'),Data)
500                        Masks = {'Points':[],'Rings':[],'Arcs':[],'Polygons':[],'Thresholds':[(Imin,Imax),[Imin,Imax]]}
501                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Masks'),Masks)
502                        self.PatternTree.SetItemPyData(Id,[Npix,imagefile])
503                        self.PickId = Id
504                        self.Image = Id
505                self.PatternTree.SelectItem(G2gd.GetPatternTreeItemId(self,Id,'Image Controls'))             #show last one
506        finally:
507            dlg.Destroy()
508       
509    def OnSnglRead(self,event):
510        self.CheckNotebook()
511        dlg = wx.FileDialog(self, 'Choose file', '.', '', 
512            'hkl files (*.hkl)|*.hkl|All files (*.*)|*.*', 
513            wx.OPEN)
514        if self.dirname: dlg.SetDirectory(self.dirname)
515        try:
516            if dlg.ShowModal() == wx.ID_OK:
517                filename = dlg.GetPath()
518                self.dirname = dlg.GetDirectory()
519                wx.BeginBusyCursor()
520                try:
521                    Data = {}
522                    names = ['Type','Lam']
523                    HKLref,HKLmin,HKLmax,FoMax,ifFc = G2IO.GetHKLData(filename)
524                    Id = self.PatternTree.AppendItem(parent=self.root,text='HKLF '+ospath.basename(filename))
525                    self.PatternTree.SetItemPyData(Id,HKLref)
526                    Sub = self.PatternTree.AppendItem(Id,text='Instrument Parameters')
527                    data = ['SXC',1.5428,]
528                    self.PatternTree.SetItemPyData(Sub,[tuple(data),data,names])
529                    Data['Type'] = 'Fosq'
530                    Data['ifFc'] = ifFc
531                    Data['HKLmax'] = HKLmax
532                    Data['HKLmin'] = HKLmin
533                    Data['FoMax'] = FoMax
534                    Data['Zone'] = '001'
535                    Data['Layer'] = 0
536                    Data['Scale'] = 1.0
537                    Data['log-lin'] = 'lin'                   
538                    self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='HKL Plot Controls'),Data)
539                    self.PatternTree.SelectItem(Id)
540                    self.PatternTree.Expand(Id)
541                    self.Sngl = Id
542                finally:
543                    wx.EndBusyCursor()   
544        finally:
545            dlg.Destroy()
546           
547    def CheckNotebook(self):
548        if not G2gd.GetPatternTreeItemId(self,self.root,'Notebook'):
549            sub = self.PatternTree.AppendItem(parent=self.root,text='Notebook')
550            self.PatternTree.SetItemPyData(sub,[''])
551        if not G2gd.GetPatternTreeItemId(self,self.root,'Controls'):
552            sub = self.PatternTree.AppendItem(parent=self.root,text='Controls')
553            self.PatternTree.SetItemPyData(sub,{})
554        if not G2gd.GetPatternTreeItemId(self,self.root,'Covariance'):
555            sub = self.PatternTree.AppendItem(parent=self.root,text='Covariance')
556            self.PatternTree.SetItemPyData(sub,{})
557        if not G2gd.GetPatternTreeItemId(self,self.root,'Constraints'):
558            sub = self.PatternTree.AppendItem(parent=self.root,text='Constraints')
559            self.PatternTree.SetItemPyData(sub,{'Hist':[],'HAP':[],'Phase':[]})
560        if not G2gd.GetPatternTreeItemId(self,self.root,'Restraints'):
561            sub = self.PatternTree.AppendItem(parent=self.root,text='Restraints')
562            self.PatternTree.SetItemPyData(sub,{})
563           
564               
565    class CopyDialog(wx.Dialog):
566        def __init__(self,parent,title,text,data):
567            wx.Dialog.__init__(self,parent,-1,title, 
568                pos=wx.DefaultPosition,style=wx.DEFAULT_DIALOG_STYLE)
569            self.data = data
570            panel = wx.Panel(self)
571            mainSizer = wx.BoxSizer(wx.VERTICAL)
572            topLabl = wx.StaticText(panel,-1,text)
573            mainSizer.Add((10,10),1)
574            mainSizer.Add(topLabl,0,wx.ALIGN_CENTER_VERTICAL|wx.LEFT,10)
575            mainSizer.Add((10,10),1)
576            ncols = len(data)/40+1
577            dataGridSizer = wx.FlexGridSizer(rows=len(data),cols=ncols,hgap=2,vgap=2)
578            for id,item in enumerate(self.data):
579                ckbox = wx.CheckBox(panel,id,item[1])
580                ckbox.Bind(wx.EVT_CHECKBOX,self.OnCopyChange)                   
581                dataGridSizer.Add(ckbox,0,wx.LEFT,10)
582            mainSizer.Add(dataGridSizer,0,wx.EXPAND)
583            OkBtn = wx.Button(panel,-1,"Ok")
584            OkBtn.Bind(wx.EVT_BUTTON, self.OnOk)
585            cancelBtn = wx.Button(panel,-1,"Cancel")
586            cancelBtn.Bind(wx.EVT_BUTTON, self.OnCancel)
587            btnSizer = wx.BoxSizer(wx.HORIZONTAL)
588            btnSizer.Add((20,20),1)
589            btnSizer.Add(OkBtn)
590            btnSizer.Add((20,20),1)
591            btnSizer.Add(cancelBtn)
592            btnSizer.Add((20,20),1)
593           
594            mainSizer.Add(btnSizer,0,wx.EXPAND|wx.BOTTOM|wx.TOP, 10)
595            panel.SetSizer(mainSizer)
596            panel.Fit()
597            self.Fit()
598       
599        def OnCopyChange(self,event):
600            id = event.GetId()
601            self.data[id][0] = self.FindWindowById(id).GetValue()       
602           
603        def OnOk(self,event):
604            parent = self.GetParent()
605            parent.Raise()
606            self.EndModal(wx.ID_OK)             
607            self.Destroy()
608           
609        def OnCancel(self,event):
610            parent = self.GetParent()
611            parent.Raise()
612            self.EndModal(wx.ID_CANCEL)             
613            self.Destroy()
614           
615        def GetData(self):
616            return self.data
617       
618    class SumDialog(wx.Dialog):
619        def __init__(self,parent,title,text,dataType,data):
620            wx.Dialog.__init__(self,parent,-1,title, 
621                pos=wx.DefaultPosition,style=wx.DEFAULT_DIALOG_STYLE)
622            self.data = data
623            panel = wx.Panel(self)
624            mainSizer = wx.BoxSizer(wx.VERTICAL)
625            topLabl = wx.StaticText(panel,-1,text)
626            mainSizer.Add((10,10),1)
627            mainSizer.Add(topLabl,0,wx.ALIGN_CENTER_VERTICAL|wx.LEFT,10)
628            mainSizer.Add((10,10),1)
629            dataGridSizer = wx.FlexGridSizer(rows=len(data),cols=2,hgap=2,vgap=2)
630            for id,item in enumerate(self.data[:-1]):
631                name = wx.TextCtrl(panel,-1,item[1],size=wx.Size(200,20))
632                name.SetEditable(False)
633                scale = wx.TextCtrl(panel,id,'%.3f'%(item[0]),style=wx.TE_PROCESS_ENTER)
634                scale.Bind(wx.EVT_TEXT_ENTER,self.OnScaleChange)
635                scale.Bind(wx.EVT_KILL_FOCUS,self.OnScaleChange)
636                dataGridSizer.Add(scale,0,wx.LEFT,10)
637                dataGridSizer.Add(name,0,wx.RIGHT,10)
638            if dataType:
639                dataGridSizer.Add(wx.StaticText(panel,-1,'Sum result name: '+dataType),0, \
640                    wx.LEFT|wx.TOP|wx.ALIGN_CENTER_VERTICAL,10)
641                self.name = wx.TextCtrl(panel,-1,self.data[-1],size=wx.Size(200,20),style=wx.TE_PROCESS_ENTER)
642                self.name.Bind(wx.EVT_TEXT_ENTER,self.OnNameChange)
643                self.name.Bind(wx.EVT_KILL_FOCUS,self.OnNameChange)
644                dataGridSizer.Add(self.name,0,wx.RIGHT|wx.TOP,10)
645            mainSizer.Add(dataGridSizer,0,wx.EXPAND)
646            OkBtn = wx.Button(panel,-1,"Ok")
647            OkBtn.Bind(wx.EVT_BUTTON, self.OnOk)
648            cancelBtn = wx.Button(panel,-1,"Cancel")
649            cancelBtn.Bind(wx.EVT_BUTTON, self.OnCancel)
650            btnSizer = wx.BoxSizer(wx.HORIZONTAL)
651            btnSizer.Add((20,20),1)
652            btnSizer.Add(OkBtn)
653            btnSizer.Add((20,20),1)
654            btnSizer.Add(cancelBtn)
655            btnSizer.Add((20,20),1)
656           
657            mainSizer.Add(btnSizer,0,wx.EXPAND|wx.BOTTOM|wx.TOP, 10)
658            panel.SetSizer(mainSizer)
659            panel.Fit()
660            self.Fit()
661           
662        def OnNameChange(self,event):
663            self.data[-1] = self.name.GetValue() 
664           
665        def OnScaleChange(self,event):
666            id = event.GetId()
667            value = self.FindWindowById(id).GetValue()
668            try:
669                self.data[id][0] = float(value)
670                self.FindWindowById(id).SetValue('%.3f'%(self.data[id][0]))
671            except ValueError:
672                if value and '-' not in value[0]:
673                    print 'bad input - numbers only'
674                    self.FindWindowById(id).SetValue('0.000')
675           
676        def OnOk(self,event):
677            parent = self.GetParent()
678            parent.Raise()
679            self.EndModal(wx.ID_OK)             
680            self.Destroy()
681           
682        def OnCancel(self,event):
683            parent = self.GetParent()
684            parent.Raise()
685            self.EndModal(wx.ID_CANCEL)             
686            self.Destroy()
687           
688        def GetData(self):
689            return self.data
690           
691    def OnPwdrSum(self,event):
692        TextList = []
693        DataList = []
694        SumList = []
695        Names = []
696        Inst = []
697        SumItemList = []
698        Comments = ['Sum equals: \n']
699        if self.PatternTree.GetCount():
700            item, cookie = self.PatternTree.GetFirstChild(self.root)
701            while item:
702                name = self.PatternTree.GetItemText(item)
703                Names.append(name)
704                if 'PWDR' in name:
705                    TextList.append([0.0,name])
706                    DataList.append(self.PatternTree.GetItemPyData(item)[1])    # (x,y,w,yc,yb,yd)
707                    if not Inst:
708                        Inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,item, 'Instrument Parameters'))
709                item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
710            if len(TextList) < 2:
711                self.ErrorDialog('Not enough data to sum','There must be more than one "PWDR" pattern')
712                return
713            TextList.append('default_sum_name')               
714            dlg = self.SumDialog(self,'Sum data','Enter scale for each pattern in summation','PWDR',TextList)
715            try:
716                if dlg.ShowModal() == wx.ID_OK:
717                    lenX = 0
718                    Xminmax = [0,0]
719                    Xsum = []
720                    Ysum = []
721                    Vsum = []
722                    result = dlg.GetData()
723                    for i,item in enumerate(result[:-1]):
724                        scale,name = item
725                        data = DataList[i]
726                        if scale:
727                            Comments.append("%10.3f %s" % (scale,' * '+name))
728                            x,y,w,yc,yb,yd = data
729                            v = 1./w
730                            if lenX:
731                                if lenX != len(x):
732                                    self.ErrorDialog('Data length error','Data to be summed must have same number of points'+ \
733                                        '\nExpected:'+str(lenX)+ \
734                                        '\nFound:   '+str(len(x))+'\nfor '+name)
735                                    return
736                            else:
737                                lenX = len(x)
738                            if Xminmax[1]:
739                                if Xminmax != [x[0],x[-1]]:
740                                    self.ErrorDialog('Data range error','Data to be summed must span same range'+ \
741                                        '\nExpected:'+str(Xminmax[0])+' '+str(Xminmax[1])+ \
742                                        '\nFound:   '+str(x[0])+' '+str(x[-1])+'\nfor '+name)
743                                    return
744                                else:
745                                    for j,yi in enumerate(y):
746                                         Ysum[j] += scale*yi
747                                         Vsum[j] += abs(scale)*v[j]
748                            else:
749                                Xminmax = [x[0],x[-1]]
750                                YCsum = YBsum = YDsum = [0.0 for i in range(lenX)]
751                                for j,yi in enumerate(y):
752                                    Xsum.append(x[j])
753                                    Ysum.append(scale*yi)
754                                    Vsum.append(abs(scale*v[j]))
755                    Wsum = 1./np.array(Vsum)
756                    outname = 'PWDR '+result[-1]
757                    Id = 0
758                    if outname in Names:
759                        dlg2 = wx.MessageDialog(self,'Overwrite data?','Duplicate data name',wx.OK|wx.CANCEL)
760                        try:
761                            if dlg2.ShowModal() == wx.ID_OK:
762                                Id = G2gd.GetPatternTreeItemId(self,self.root,name)
763                                self.PatternTree.Delete(Id)
764                        finally:
765                            dlg2.Destroy()
766                    Id = self.PatternTree.AppendItem(parent=self.root,text=outname)
767                    if Id:
768                        Sample = G2pdG.SetDefaultSample()
769                        self.PatternTree.SetItemPyData(Id,[[''],[Xsum,Ysum,Wsum,YCsum,YBsum,YDsum]])
770                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Comments'),Comments)                   
771                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Limits'),[tuple(Xminmax),Xminmax])
772                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Background'),[['chebyschev',1,3,1.0,0.0,0.0]])
773                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Instrument Parameters'),Inst)
774                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Sample Parameters'),Sample)
775                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Peak List'),[])
776                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Index Peak List'),[])
777                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Unit Cells List'),[])             
778                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Reflection Lists'),{})             
779                        self.PatternTree.SelectItem(Id)
780                        self.PatternTree.Expand(Id)
781                   
782            finally:
783                dlg.Destroy()
784
785    def OnImageSum(self,event):
786        TextList = []
787        DataList = []
788        SumList = []
789        Names = []
790        Inst = []
791        SumItemList = []
792        Comments = ['Sum equals: \n']
793        if self.PatternTree.GetCount():
794            item, cookie = self.PatternTree.GetFirstChild(self.root)
795            while item:
796                name = self.PatternTree.GetItemText(item)
797                Names.append(name)
798                if 'IMG' in name:
799                    TextList.append([0.0,name])
800                    DataList.append(self.PatternTree.GetItemPyData(item))        #Size,Image
801                    Data = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,item,'Image Controls'))
802                item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
803            if len(TextList) < 2:
804                self.ErrorDialog('Not enough data to sum','There must be more than one "IMG" pattern')
805                return
806            TextList.append('default_sum_name')               
807            dlg = self.SumDialog(self,'Sum data','Enter scale for each image in summation','IMG',TextList)
808            try:
809                if dlg.ShowModal() == wx.ID_OK:
810                    imSize = 0
811                    result = dlg.GetData()
812                    First = True
813                    Found = False
814                    for i,item in enumerate(result[:-1]):
815                        scale,name = item
816                        data = DataList[i]
817                        if scale:
818                            Found = True                               
819                            Comments.append("%10.3f %s" % (scale,' * '+name))
820                            Npix,imagefile = data
821                            image = G2IO.GetImageData(self,imagefile,imageOnly=True)
822                            if First:
823                                newImage = np.zeros_like(image)
824                                First = False
825                            if imSize:
826                                if imSize != Npix:
827                                    self.ErrorDialog('Image size error','Images to be summed must be same size'+ \
828                                        '\nExpected:'+str(imSize)+ \
829                                        '\nFound:   '+str(Npix)+'\nfor '+name)
830                                    return
831                                newImage = newImage+scale*image
832                            else:
833                                imSize = Npix
834                                newImage = newImage+scale*image
835                            del(image)
836                    if not Found:
837                        self.ErrorDialog('Image sum error','No nonzero image multipliers found')
838                        return
839                       
840                    newImage = np.asfarray(newImage,dtype=np.float32)                       
841                    outname = 'IMG '+result[-1]
842                    Id = 0
843                    if outname in Names:
844                        dlg2 = wx.MessageDialog(self,'Overwrite data?','Duplicate data name',wx.OK|wx.CANCEL)
845                        try:
846                            if dlg2.ShowModal() == wx.ID_OK:
847                                Id = G2gd.GetPatternTreeItemId(self,self.root,name)
848                        finally:
849                            dlg2.Destroy()
850                    else:
851                        Id = self.PatternTree.AppendItem(parent=self.root,text=outname)
852                    if Id:
853                        dlg = wx.FileDialog(self, 'Choose sum image filename', '.', '', 
854                            'G2img files (*.G2img)|*.G2img', 
855                            wx.SAVE|wx.FD_OVERWRITE_PROMPT)
856                        if self.dirname: dlg.SetDirectory(self.dirname)
857                        if dlg.ShowModal() == wx.ID_OK:
858                            self.dirname = dlg.GetDirectory()
859                            newimagefile = dlg.GetPath()
860                            G2IO.PutG2Image(newimagefile,Comments,Data,Npix,newImage)
861                            Imax = np.amax(newImage)
862                            Imin = np.amin(newImage)
863                            newImage = []
864                            self.PatternTree.SetItemPyData(Id,[imSize,newimagefile])
865                            self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Comments'),Comments)
866                        del(newImage)
867                        if self.imageDefault:
868                            Data = copy.copy(self.imageDefault)
869                        Data['showLines'] = True
870                        Data['ring'] = []
871                        Data['rings'] = []
872                        Data['cutoff'] = 10
873                        Data['pixLimit'] = 20
874                        Data['ellipses'] = []
875                        Data['calibrant'] = ''
876                        Data['range'] = [(Imin,Imax),[Imin,Imax]]
877                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Image Controls'),Data)                                           
878                        Masks = {'Points':[],'Rings':[],'Arcs':[],'Polygons':[],'Thresholds':[(Imin,Imax),[Imin,Imax]]}
879                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='Masks'),Masks)
880                        self.PatternTree.SelectItem(Id)
881                        self.PatternTree.Expand(Id)
882                        self.PickId = G2gd.GetPatternTreeItemId(self,self.root,outname)
883                        self.Image = self.PickId
884            finally:
885                dlg.Destroy()
886                     
887    def OnAddPhase(self,event):
888        if not G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
889            sub = self.PatternTree.AppendItem(parent=self.root,text='Phases')
890        else:
891            sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
892        PhaseName = ''
893        dlg = wx.TextEntryDialog(None,'Enter a name for this phase','Phase Name Entry','New phase',
894            style=wx.OK)
895        if dlg.ShowModal() == wx.ID_OK:
896            PhaseName = dlg.GetValue()
897        dlg.Destroy()
898        sub = self.PatternTree.AppendItem(parent=sub,text=PhaseName)
899        E,SGData = G2spc.SpcGroup('P 1')
900        self.PatternTree.SetItemPyData(sub, {
901            'General':{
902                'Name':PhaseName,
903                'Type':'nuclear',
904                'SGData':SGData,
905                'Cell':[False,10.,10.,10.,90.,90.,90,1000.],
906                'Pawley dmin':1.0,
907                'Data plot type':'Microstrain',
908                'SH Texture':{
909                    'Order':0,
910                    'Model':'cylindrical',
911                    'Sample omega':[False,0.0],
912                    'Sample chi':[False,0.0],
913                    'Sample phi':[False,0.0],
914                    'SH Coeff':[False,{}],
915                    'SHShow':False,
916                    'PFhkl':[0,0,1],
917                    'PFxyz':[0,0,1],
918                    'PlotType':'Pole figure'}},
919            'Atoms':[],
920            'Drawing':{},
921            'Histograms':{},
922            'Pawley ref':[],
923            'Models':{},
924            })
925       
926    def OnDeletePhase(self,event):
927        #Hmm, also need to delete this phase from Reflection Lists for each PWDR histogram
928        if self.dataFrame:
929            self.dataFrame.Clear() 
930        TextList = []
931        DelList = []
932        DelItemList = []
933        if G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
934            sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
935        else:
936            return
937        if sub:
938            item, cookie = self.PatternTree.GetFirstChild(sub)
939            while item:
940                TextList.append(self.PatternTree.GetItemText(item))
941                item, cookie = self.PatternTree.GetNextChild(sub, cookie)               
942            dlg = wx.MultiChoiceDialog(self, 'Which phase to delete?', 'Delete phase', TextList, wx.CHOICEDLG_STYLE)
943            try:
944                if dlg.ShowModal() == wx.ID_OK:
945                    result = dlg.GetSelections()
946                    for i in result: DelList.append([i,TextList[i]])
947                    item, cookie = self.PatternTree.GetFirstChild(sub)
948                    i = 0
949                    while item:
950                        if [i,self.PatternTree.GetItemText(item)] in DelList: DelItemList.append(item)
951                        item, cookie = self.PatternTree.GetNextChild(sub, cookie)
952                        i += 1
953                    for item in DelItemList:
954                        name = self.PatternTree.GetItemText(item)
955                        self.PatternTree.Delete(item)
956                        self.G2plotNB.Delete(name)
957                    item, cookie = self.PatternTree.GetFirstChild(self.root)
958                    while item:
959                        name = self.PatternTree.GetItemText(item)
960                        if 'PWDR' in name:
961                            Id = G2gd.GetPatternTreeItemId(self,item, 'Reflection Lists')
962                            refList = self.PatternTree.GetItemPyData(Id)
963                            for i,item in DelList:
964                                del(refList[item])
965                            self.PatternTree.SetItemPyData(Id,refList)
966                        item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
967            finally:
968                dlg.Destroy()
969               
970    def OnRenameData(self,event):
971        name = self.PatternTree.GetItemText(self.PickId)     
972        if 'PWDR' in name or 'HKLF' in name or 'IMG' in name:
973            dataType = name[:name.index(' ')+1]                 #includes the ' '
974            dlg = wx.TextEntryDialog(self,'Data name: '+dataType,'Change data name',
975                defaultValue=name[name.index(' ')+1:])
976            try:
977                if dlg.ShowModal() == wx.ID_OK:
978                    self.PatternTree.SetItemText(self.PickId,dataType+dlg.GetValue())
979            finally:
980                dlg.Destroy()
981       
982    def GetFileList(self,fileType,skip=None):        #potentially useful?
983        fileList = []
984        Source = ''
985        id, cookie = self.PatternTree.GetFirstChild(self.root)
986        while id:
987            name = self.PatternTree.GetItemText(id)
988            if fileType in name:
989                if id == skip:
990                    Source = name
991                else:
992                    fileList.append([False,name,id])
993            id, cookie = self.PatternTree.GetNextChild(self.root, cookie)
994        if skip:
995            return fileList,Source
996        else:
997            return fileList
998           
999    def OnDataDelete(self, event):
1000        TextList = ['All Data']
1001        DelList = []
1002        DelItemList = []
1003        ifPWDR = False
1004        ifIMG = False
1005        ifHKLF = False
1006        ifPDF = False
1007        if self.PatternTree.GetCount():
1008            item, cookie = self.PatternTree.GetFirstChild(self.root)
1009            while item:
1010                name = self.PatternTree.GetItemText(item)
1011                if name not in ['Notebook','Controls','Covariance','Constraints','Restraints','Phases']:
1012                    if 'PWDR' in name: ifPWDR = True
1013                    if 'IMG' in name: ifIMG = True
1014                    if 'HKLF' in name: ifHKLF = True
1015                    if 'PDF' in name: ifPDF = True
1016                    TextList.append(name)
1017                item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1018            if ifPWDR: TextList.insert(1,'All PWDR')
1019            if ifIMG: TextList.insert(1,'All IMG')
1020            if ifHKLF: TextList.insert(1,'All HKLF')
1021            if ifPDF: TextList.insert(1,'All PDF')               
1022            dlg = wx.MultiChoiceDialog(self, 'Which data to delete?', 'Delete data', TextList, wx.CHOICEDLG_STYLE)
1023            try:
1024                if dlg.ShowModal() == wx.ID_OK:
1025                    result = dlg.GetSelections()
1026                    for i in result: DelList.append(TextList[i])
1027                    if 'All Data' in DelList:
1028                        DelList = [item for item in TextList if item[:3] != 'All']
1029                    elif 'All PWDR' in DelList:
1030                        DelList = [item for item in TextList if item[:4] == 'PWDR']
1031                    elif 'All IMG' in DelList:
1032                        DelList = [item for item in TextList if item[:3] == 'IMG']
1033                    elif 'All HKLF' in DelList:
1034                        DelList = [item for item in TextList if item[:4] == 'HKLF']
1035                    elif 'All PDF' in DelList:
1036                        DelList = [item for item in TextList if item[:3] == 'PDF']
1037                    item, cookie = self.PatternTree.GetFirstChild(self.root)
1038                    while item:
1039                        if self.PatternTree.GetItemText(item) in DelList: DelItemList.append(item)
1040                        item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1041                    for item in DelItemList:
1042                        self.PatternTree.Delete(item)
1043                    G2plt.PlotPatterns(self,True)                        #so plot gets updated
1044            finally:
1045                dlg.Destroy()
1046
1047    def OnFileOpen(self, event):
1048        result = ''
1049        Id = 0
1050        if self.PatternTree.GetChildrenCount(self.root,False):
1051            if self.dataFrame:
1052                self.dataFrame.Clear() 
1053            dlg = wx.MessageDialog(self, 'Overwrite?','Project exists!',  wx.OK | wx.CANCEL)
1054            try:
1055                result = dlg.ShowModal()
1056                if result == wx.ID_OK:
1057                    self.PatternTree.DeleteChildren(self.root)
1058                    self.GSASprojectfile = ''
1059#                    self.PatternTree.DeleteChildren(self.root)
1060                    if self.HKL: self.HKL = []
1061                    if self.G2plotNB.plotList:
1062                        self.G2plotNB.clear()
1063            finally:
1064                dlg.Destroy()
1065        if result != wx.ID_CANCEL:   
1066            if self.dataDisplay: self.dataDisplay.Destroy()
1067            dlg = wx.FileDialog(self, 'Choose GSAS-II project file', '.', '', 
1068                'GSAS-II project file (*.gpx)|*.gpx',wx.OPEN)
1069            if self.dirname: dlg.SetDirectory(self.dirname)
1070            try:
1071                if dlg.ShowModal() == wx.ID_OK:
1072                    self.GSASprojectfile = dlg.GetPath()
1073                    self.dirname = dlg.GetDirectory()
1074                    G2IO.ProjFileOpen(self)
1075                    self.PatternTree.SetItemText(self.root,'Loaded Data: '+self.GSASprojectfile)
1076                    self.PatternTree.Expand(self.root)
1077                    self.HKL = []
1078                    item, cookie = self.PatternTree.GetFirstChild(self.root)
1079                    while item and not Id:
1080                        name = self.PatternTree.GetItemText(item)
1081                        if name[:4] in ['PWDR','HKLF','IMG ','PDF ']:
1082                            Id = item
1083                        elif name == 'Controls':
1084                            data = self.PatternTree.GetItemPyData(item)
1085                            if data:
1086                                self.Refine.Enable(True)
1087                                self.SeqRefine.Enable(True)
1088                                self.Solve.Enable(True)         #not right but something needed here
1089                        item, cookie = self.PatternTree.GetNextChild(self.root, cookie)               
1090                    if Id:
1091                        self.PatternTree.SelectItem(Id)
1092                    self.CheckNotebook()
1093            finally:
1094                dlg.Destroy()
1095
1096
1097    def OnFileClose(self, event):
1098        if self.dataFrame:
1099            self.dataFrame.Clear()
1100            self.dataFrame.SetLabel('GSAS-II data display') 
1101        dlg = wx.MessageDialog(self, 'Save current project?', ' ', wx.YES | wx.NO | wx.CANCEL)
1102        try:
1103            result = dlg.ShowModal()
1104            if result == wx.ID_OK:
1105                self.OnFileSaveMenu(event)
1106            if result != wx.ID_CANCEL:
1107                self.GSASprojectfile = ''
1108                self.PatternTree.SetItemText(self.root,'Loaded Data: ')
1109                self.PatternTree.DeleteChildren(self.root)
1110                if self.HKL: self.HKL = []
1111                if self.G2plotNB.plotList:
1112                    self.G2plotNB.clear()
1113        finally:
1114            dlg.Destroy()
1115
1116    def OnFileSave(self, event):
1117        if self.GSASprojectfile: 
1118            self.PatternTree.SetItemText(self.root,'Loaded Data: '+self.GSASprojectfile)
1119            G2IO.ProjFileSave(self)
1120        else:
1121            self.OnFileSaveas(event)
1122
1123    def OnFileSaveas(self, event):
1124        dlg = wx.FileDialog(self, 'Choose GSAS-II project file name', '.', '', 
1125            'GSAS-II project file (*.gpx)|*.gpx',wx.FD_SAVE|wx.FD_OVERWRITE_PROMPT)
1126        if self.dirname:
1127            dlg.SetDirectory(self.dirname)
1128        try:
1129            if dlg.ShowModal() == wx.ID_OK:
1130                self.GSASprojectfile = dlg.GetPath()
1131                self.PatternTree.SetItemText(self.root,'Loaded Data: '+self.GSASprojectfile)
1132                G2IO.ProjFileSave(self)
1133                self.dirname = dlg.GetDirectory()
1134        finally:
1135            dlg.Destroy()
1136
1137    def ExitMain(self, event):
1138        if self.undofile:
1139            os.remove(self.undofile)
1140        sys.exit()
1141       
1142    def OnFileExit(self, event):
1143        if self.dataFrame:
1144            self.dataFrame.Clear() 
1145            self.dataFrame.Destroy()
1146        self.Close()
1147       
1148    def OnImportPattern(self,event):
1149        dlg = wx.FileDialog(self, 'Choose nonGSAS powder file', '.', '', 
1150            '(*.*)|*.*',wx.OPEN)
1151        if self.dirname:
1152            dlg.SetDirectory(self.dirname)
1153        try:
1154            if dlg.ShowModal() == wx.ID_OK:
1155                self.powderfile = dlg.GetPath()
1156                self.dirname = dlg.GetDirectory()
1157        finally:
1158            dlg.Destroy()
1159           
1160    def OnImportHKL(self,event):
1161        dlg = wx.FileDialog(self, 'Choose structure factor file', '.', '', 
1162            '(*.*)|*.*',wx.OPEN)
1163        if self.dirname:
1164            dlg.SetDirectory(self.dirname)
1165        try:
1166            if dlg.ShowModal() == wx.ID_OK:
1167                self.HKLfile = dlg.GetPath()
1168                self.dirname = dlg.GetDirectory()
1169        finally:
1170            dlg.Destroy()
1171       
1172    def OnImportPhase(self,event):
1173        dlg = wx.FileDialog(self, 'Choose GSAS EXP file', '.', '', 
1174            'EXP file (*.EXP)|*.EXP',wx.OPEN)
1175        if self.dirname:
1176            dlg.SetDirectory(self.dirname)
1177        try:
1178            Phase = {}
1179            if dlg.ShowModal() == wx.ID_OK:
1180                EXPfile = dlg.GetPath()
1181                self.dirname = dlg.GetDirectory()
1182                Phase = G2IO.ReadEXPPhase(self,EXPfile)
1183        finally:
1184            dlg.Destroy()
1185        if Phase:
1186            PhaseName = Phase['General']['Name']
1187            if not G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
1188                sub = self.PatternTree.AppendItem(parent=self.root,text='Phases')
1189            else:
1190                sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
1191            sub = self.PatternTree.AppendItem(parent=sub,text=PhaseName)
1192            self.PatternTree.SetItemPyData(sub,Phase)
1193           
1194    def OnImportPDB(self,event):
1195        dlg = wx.FileDialog(self, 'Choose PDB file', '.', '', 
1196            'PDB file (*.pdb,*.ent)|*.pdb;*.ent|All files (*.*)|*.*',wx.OPEN)
1197        if self.dirname:
1198            dlg.SetDirectory(self.dirname)
1199        try:
1200            if dlg.ShowModal() == wx.ID_OK:
1201                PDBfile = dlg.GetPath()
1202                self.dirname = dlg.GetDirectory()
1203                Phase = G2IO.ReadPDBPhase(PDBfile)
1204        finally:
1205            dlg.Destroy()
1206        if Phase:
1207            PhaseName = Phase['General']['Name']
1208            if not G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
1209                sub = self.PatternTree.AppendItem(parent=self.root,text='Phases')
1210            else:
1211                sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
1212            sub = self.PatternTree.AppendItem(parent=sub,text=PhaseName)
1213            self.PatternTree.SetItemPyData(sub,Phase)       
1214       
1215    def OnImportCIF(self,event):
1216        dlg = wx.FileDialog(self, 'Choose CIF file', '.', '', 
1217            'CIF file (*.cif)|*.cif',wx.OPEN)
1218        if self.dirname:
1219            dlg.SetDirectory(self.dirname)
1220        try:
1221            if dlg.ShowModal() == wx.ID_OK:
1222                CIFfile = dlg.GetPath()
1223                self.dirname = dlg.GetDirectory()
1224                Phase = G2IO.ReadCIFPhase(CIFfile)
1225        finally:
1226            dlg.Destroy()
1227        if Phase:
1228            PhaseName = Phase['General']['Name']
1229            if not G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
1230                sub = self.PatternTree.AppendItem(parent=self.root,text='Phases')
1231            else:
1232                sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
1233            sub = self.PatternTree.AppendItem(parent=sub,text=PhaseName)
1234            self.PatternTree.SetItemPyData(sub,Phase)       
1235       
1236    def OnExportPatterns(self,event):
1237        names = ['All']
1238        exports = []
1239        item, cookie = self.PatternTree.GetFirstChild(self.root)
1240        while item:
1241            name = self.PatternTree.GetItemText(item)
1242            if 'PWDR' in name:
1243                names.append(name)
1244            item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1245        if names:
1246            dlg = wx.MultiChoiceDialog(self,'Select','Powder patterns to export',names)
1247            if dlg.ShowModal() == wx.ID_OK:
1248                sel = dlg.GetSelections()
1249                if sel[0] == 0:
1250                    exports = names[1:]
1251                else:
1252                    for x in sel:
1253                        exports.append(names[x])
1254            dlg.Destroy()
1255        if exports:
1256            dlg = wx.FileDialog(self, 'Choose output powder file name', '.', '', 
1257                'GSAS fxye file (*.fxye)|*.fxye|xye file (*.xye)|*.xye',
1258                wx.FD_SAVE|wx.FD_OVERWRITE_PROMPT)
1259            if self.dirname:
1260                dlg.SetDirectory(self.dirname)
1261            try:
1262                if dlg.ShowModal() == wx.ID_OK:
1263                    powderfile = dlg.GetPath()
1264                    if 'fxye' in powderfile:
1265                        G2IO.powderFxyeSave(self,exports,powderfile)
1266                    else:       #just xye
1267                        G2IO.powderXyeSave(self,exports,powderfile)
1268                    self.dirname = dlg.GetDirectory()
1269            finally:
1270                dlg.Destroy()
1271       
1272    def OnExportPeakList(self,event):
1273        dlg = wx.FileDialog(self, 'Choose output peak list file name', '.', '', 
1274            '(*.*)|*.*',wx.FD_SAVE|wx.FD_OVERWRITE_PROMPT)
1275        if self.dirname:
1276            dlg.SetDirectory(self.dirname)
1277        try:
1278            if dlg.ShowModal() == wx.ID_OK:
1279                self.peaklistfile = dlg.GetPath()
1280                file = open(self.peaklistfile,'w')               
1281                item, cookie = self.PatternTree.GetFirstChild(self.root)
1282                while item:
1283                    name = self.PatternTree.GetItemText(item)
1284                    if 'PWDR' in name:
1285                        item2, cookie2 = self.PatternTree.GetFirstChild(item)
1286                        while item2:
1287                            name2 = self.PatternTree.GetItemText(item2)
1288                            if name2 == 'Peak List':
1289                                peaks = self.PatternTree.GetItemPyData(item2)
1290                                file.write("%s \n" % (name+' Peak List'))               
1291                                for peak in peaks:
1292                                    file.write("%10.4f %12.2f %10.3f %10.3f \n" % \
1293                                        (peak[0],peak[2],peak[4],peak[6]))
1294                            item2, cookie2 = self.PatternTree.GetNextChild(item, cookie2)                           
1295                    item, cookie = self.PatternTree.GetNextChild(self.root, cookie)                           
1296                file.close()
1297                self.dirname = dlg.GetDirectory()
1298        finally:
1299            dlg.Destroy()
1300       
1301    def OnExportHKL(self,event):
1302        event.Skip()
1303       
1304    def OnExportPDF(self,event):
1305        #need S(Q) and G(R) to be saved here - probably best from selection?
1306        names = ['All']
1307        exports = []
1308        item, cookie = self.PatternTree.GetFirstChild(self.root)
1309        while item:
1310            name = self.PatternTree.GetItemText(item)
1311            if 'PDF' in name:
1312                names.append(name)
1313            item, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1314        if names:
1315            dlg = wx.MultiChoiceDialog(self,'Select','PDF patterns to export',names)
1316            if dlg.ShowModal() == wx.ID_OK:
1317                sel = dlg.GetSelections()
1318                if sel[0] == 0:
1319                    exports = names[1:]
1320                else:
1321                    for x in sel:
1322                        exports.append(names[x])
1323            dlg.Destroy()
1324        if exports:
1325            G2IO.PDFSave(self,exports)
1326       
1327    def OnExportPhase(self,event):
1328        event.Skip()
1329       
1330    def OnExportCIF(self,event):
1331        event.Skip()
1332
1333    def OnMakePDFs(self,event):
1334        tth2q = lambda t,w:4.0*math.pi*sind(t/2.0)/w
1335        TextList = ['All PWDR']
1336        PDFlist = []
1337        Names = []
1338        if self.PatternTree.GetCount():
1339            id, cookie = self.PatternTree.GetFirstChild(self.root)
1340            while id:
1341                name = self.PatternTree.GetItemText(id)
1342                Names.append(name)
1343                if 'PWDR' in name:
1344                    TextList.append(name)
1345                id, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1346            if len(TextList) == 1:
1347                self.ErrorDialog('Nothing to make PDFs for','There must be at least one "PWDR" pattern')
1348                return
1349            dlg = wx.MultiChoiceDialog(self,'Make PDF controls','Make PDF controls for:',TextList, wx.CHOICEDLG_STYLE)
1350            try:
1351                if dlg.ShowModal() == wx.ID_OK:
1352                    result = dlg.GetSelections()
1353                    for i in result: PDFlist.append(TextList[i])
1354                    if 0 in result:
1355                        PDFlist = [item for item in TextList if item[:4] == 'PWDR']                       
1356                    for item in PDFlist:
1357                        PWDRname = item[4:]
1358                        Id = self.PatternTree.AppendItem(parent=self.root,text='PDF '+PWDRname)
1359                        Data = {
1360                            'Sample':{'Name':item,'Mult':1.0,'Add':0.0},
1361                            'Sample Bkg.':{'Name':'','Mult':-1.0,'Add':0.0},
1362                            'Container':{'Name':'','Mult':-1.0,'Add':0.0},
1363                            'Container Bkg.':{'Name':'','Mult':-1.0,'Add':0.0},'ElList':{},
1364                            'Geometry':'Cylinder','Diam':1.0,'Pack':0.50,'Form Vol':10.0,
1365                            'DetType':'Image plate','ObliqCoeff':0.2,'Ruland':0.025,'QScaleLim':[0,100],
1366                            'Lorch':True,}
1367                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='PDF Controls'),Data)
1368                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='I(Q)'+PWDRname),[])       
1369                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='S(Q)'+PWDRname),[])       
1370                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='F(Q)'+PWDRname),[])       
1371                        self.PatternTree.SetItemPyData(self.PatternTree.AppendItem(Id,text='G(R)'+PWDRname),[])       
1372                self.ExportPDF.Enable(True)
1373            finally:
1374                dlg.Destroy()
1375               
1376    def GetPWDRdatafromTree(self,PWDRname):
1377        ''' Returns powder data from GSASII tree
1378        input:
1379            PWDRname = powder histogram name as obtained from GetHistogramNames
1380        return:
1381            PWDRdata = powder data dictionary with:
1382                Data - powder data arrays, Limits, Instrument Parameters, Sample Parameters           
1383        '''
1384        PWDRdata = {}
1385        PWDRdata['Data'] = self.PatternTree.GetItemPyData(PWDRname)[1]          #powder data arrays
1386        PWDRdata['Limits'] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PWDRname,'Limits'))
1387        PWDRdata['Background'] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PWDRname,'Background'))
1388        PWDRdata['Instrument Parameters'] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PWDRname,'Instrument Parameters'))
1389        PWDRdata['Sample Parameters'] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PWDRname,'Sample Parameters'))
1390        PWDRdata['Reflection Lists'] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PWDRname,'Reflection Lists'))
1391        return PWDRdata
1392
1393    def GetHKLFdatafromTree(self,HKLFname):
1394        ''' Returns single crystal data from GSASII tree
1395        input:
1396            HKLFname = single crystal histogram name as obtained from GetHistogramNames
1397        return:
1398            HKLFdata = single crystal data list of reflections: for each reflection:
1399                HKLF = [np.array([h,k,l]),FoSq,sigFoSq,FcSq,Fcp,Fcpp,phase]
1400        '''
1401        HKLFdata = []
1402        while True:
1403            data = self.PatternTree.GetItemPyData(HKLFname)
1404            datum = data[0]
1405            if datum[0] == HKLFname:
1406                HKLFdata = datum[1:][0]
1407        return HKLFdata
1408                   
1409    def GetUsedHistogramsAndPhasesfromTree(self):
1410        ''' Returns all histograms that are found in any phase
1411        and any phase that uses a histogram
1412        return:
1413            Histograms = dictionary of histograms as {name:data,...}
1414            Phases = dictionary of phases that use histograms
1415        '''
1416        phaseData = {}
1417        if G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
1418            sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
1419        else:
1420            print 'no phases to be refined'
1421            return
1422        if sub:
1423            item, cookie = self.PatternTree.GetFirstChild(sub)
1424            while item:
1425                phaseData[self.PatternTree.GetItemText(item)] =  self.PatternTree.GetItemPyData(item)               
1426                item, cookie = self.PatternTree.GetNextChild(sub, cookie)               
1427        Histograms = {}
1428        Phases = {}
1429        pId = 0
1430        hId = 0
1431        for phase in phaseData:
1432            Phase = phaseData[phase]
1433            if Phase['Histograms']:
1434                if phase not in Phases:
1435                    Phase['pId'] = pId
1436                    pId += 1
1437                    Phases[phase] = Phase
1438                for hist in Phase['Histograms']:
1439                    if hist not in Histograms:
1440                        item = G2gd.GetPatternTreeItemId(self,self.root,hist)
1441                        if 'PWDR' in hist[:4]: 
1442                            Histograms[hist] = self.GetPWDRdatafromTree(item)
1443                        elif 'HKLF' in hist[:4]:
1444                            Histograms[hist] = self.GetHKLFdatafromTree(item)
1445                        #future restraint, etc. histograms here           
1446                        Histograms[hist]['hId'] = hId
1447                        hId += 1
1448        return Histograms,Phases
1449       
1450    class ViewParmDialog(wx.Dialog):
1451        def __init__(self,parent,title,parmDict):
1452            wx.Dialog.__init__(self,parent,-1,title,size=(260,430),
1453                pos=wx.DefaultPosition,style=wx.DEFAULT_DIALOG_STYLE)
1454            panel = wx.Panel(self,size=(260,430))
1455            parmNames = parmDict.keys()
1456            parmNames.sort()
1457            parmText = ' p:h:Parameter       refine?              value\n'
1458            for name in parmNames:
1459                parmData = parmDict[name]
1460                try:
1461                    parmText += ' %s \t%12.4g \n'%(name.ljust(19)+'\t'+parmData[1],parmData[0])
1462                except TypeError:
1463                    pass
1464            parmTable = wx.TextCtrl(panel,-1,parmText,
1465                style=wx.TE_MULTILINE|wx.TE_READONLY,size=(250,400))
1466            mainSizer = wx.BoxSizer(wx.VERTICAL)
1467            mainSizer.Add(parmTable)
1468            panel.SetSizer(mainSizer)
1469               
1470           
1471    def OnViewLSParms(self,event):
1472        parmDict = {}
1473        Histograms,Phases = self.GetUsedHistogramsAndPhasesfromTree()
1474        Natoms,phaseVary,phaseDict,pawleyLookup,FFtable,BLtable = G2str.GetPhaseData(Phases,Print=False)       
1475        hapVary,hapDict,controlDict = G2str.GetHistogramPhaseData(Phases,Histograms,Print=False)
1476        histVary,histDict,controlDict = G2str.GetHistogramData(Histograms,Print=False)
1477        varyList = phaseVary+hapVary+histVary
1478        parmDict.update(phaseDict)
1479        parmDict.update(hapDict)
1480        parmDict.update(histDict)
1481        for parm in parmDict:
1482            if parm.split(':')[-1] in ['Azimuth','Gonio. radius','Lam1','Lam2','Omega','Chi','Phi']:
1483                parmDict[parm] = [parmDict[parm],' ']
1484            elif parm.split(':')[-2] in ['Ax','Ay','Az','SHmodel','SHord']:
1485                parmDict[parm] = [parmDict[parm],' ']
1486            elif parm in varyList:
1487                parmDict[parm] = [parmDict[parm],'True']
1488            else:
1489                parmDict[parm] = [parmDict[parm],'False']
1490        dlg = self.ViewParmDialog(self,'Parameters for least squares',parmDict)
1491        try:
1492            if dlg.ShowModal() == wx.ID_OK:
1493                print 'do something with changes?? - No!'
1494        finally:
1495            dlg.Destroy()
1496       
1497    def OnRefine(self,event):
1498        self.OnFileSave(event)
1499        #works - but it'd be better if it could restore plots
1500        dlg = wx.ProgressDialog('Residual','Powder profile Rwp =',101.0, 
1501            style = wx.PD_ELAPSED_TIME|wx.PD_AUTO_HIDE|wx.PD_CAN_ABORT)
1502        screenSize = wx.ClientDisplayRect()
1503        Size = dlg.GetSize()
1504        Size = (int(Size[0]*1.2),Size[1]) # increase size a bit along x
1505        dlg.SetPosition(wx.Point(screenSize[2]-Size[0]-305,screenSize[1]+5))
1506        dlg.SetSize(Size)
1507        try:
1508            G2str.Refine(self.GSASprojectfile,dlg)
1509        finally:
1510            dlg.Destroy()       
1511        dlg = wx.MessageDialog(self,'Load new result?','Refinement results',wx.OK|wx.CANCEL)
1512        try:
1513            if dlg.ShowModal() == wx.ID_OK:
1514                Id = 0
1515                self.PatternTree.DeleteChildren(self.root)
1516                if self.HKL: self.HKL = []
1517                if self.G2plotNB.plotList:
1518                    self.G2plotNB.clear()
1519                G2IO.ProjFileOpen(self)
1520                item, cookie = self.PatternTree.GetFirstChild(self.root)
1521                while item and not Id:
1522                    name = self.PatternTree.GetItemText(item)
1523                    if name[:4] in ['PWDR','HKLF']:
1524                        Id = item
1525                    item, cookie = self.PatternTree.GetNextChild(self.root, cookie)               
1526                if Id:
1527                    self.PatternTree.SelectItem(Id)
1528        finally:
1529            dlg.Destroy()
1530
1531    def OnSeqRefine(self,event):
1532        Id = G2gd.GetPatternTreeItemId(self,self.root,'Sequental results')
1533        if not Id:
1534            Id = self.PatternTree.AppendItem(self.root,text='Sequental results')
1535            self.PatternTree.SetItemPyData(Id,{})           
1536        self.OnFileSave(event)
1537        dlg = wx.ProgressDialog('Residual for histogram 0','Powder profile Rwp =',101.0, 
1538            style = wx.PD_ELAPSED_TIME|wx.PD_AUTO_HIDE|wx.PD_CAN_ABORT)
1539        screenSize = wx.ClientDisplayRect()
1540        Size = dlg.GetSize()
1541        Size = (int(Size[0]*1.2),Size[1]) # increase size a bit along x
1542        dlg.SetPosition(wx.Point(screenSize[2]-Size[0]-305,screenSize[1]+5))
1543        dlg.SetSize(Size)
1544        try:
1545            G2str.SeqRefine(self.GSASprojectfile,dlg)
1546        finally:
1547            dlg.Destroy()       
1548        dlg = wx.MessageDialog(self,'Load new result?','Refinement results',wx.OK|wx.CANCEL)
1549        try:
1550            if dlg.ShowModal() == wx.ID_OK:
1551                Id = 0
1552                self.PatternTree.DeleteChildren(self.root)
1553                if self.HKL: self.HKL = []
1554                if self.G2plotNB.plotList:
1555                    self.G2plotNB.clear()
1556                G2IO.ProjFileOpen(self)
1557                item, cookie = self.PatternTree.GetFirstChild(self.root)
1558                while item and not Id:
1559                    name = self.PatternTree.GetItemText(item)
1560                    if name[:4] in ['PWDR','HKLF']:
1561                        Id = item
1562                    item, cookie = self.PatternTree.GetNextChild(self.root, cookie)               
1563                if Id:
1564                    self.PatternTree.SelectItem(Id)
1565        finally:
1566            dlg.Destroy()
1567       
1568    def OnSolve(self,event):
1569        #works - but it'd be better if it could restore plots
1570        G2sol.Solve(self.GSASprojectfile)
1571        dlg = wx.MessageDialog(self,'Load new result?','Structure solution results',wx.OK|wx.CANCEL)
1572        try:
1573            if dlg.ShowModal() == wx.ID_OK:
1574                self.PatternTree.DeleteChildren(self.root)
1575                if self.HKL: self.HKL = []
1576                if self.G2plotNB.plotList:
1577                    self.G2plotNB.clear()
1578                G2IO.ProjFileOpen(self)
1579        finally:
1580            dlg.Destroy()
1581       
1582    def ErrorDialog(self,title,message):
1583        dlg = wx.MessageDialog(self, message, title,  wx.OK)
1584        try:
1585            result = dlg.ShowModal()
1586        finally:
1587            dlg.Destroy()
1588
1589    def OnHelpHelp(self, event):
1590        event.Skip()
1591               
1592class GSASIImain(wx.App):
1593    def OnInit(self):
1594        self.main = GSASII(None)
1595        self.main.Show()
1596        self.SetTopWindow(self.main)
1597        return True
1598
1599def main():
1600    application = GSASIImain(0)
1601    #application.main.OnRefine(None)
1602    application.MainLoop()
1603   
1604if __name__ == '__main__':
1605    main()
Note: See TracBrowser for help on using the repository browser.