source: trunk/GSASII.py @ 397

Last change on this file since 397 was 397, checked in by vondreele, 12 years ago

collect default settings for Sample in one routine
add recalibrate routine for images
azimuths from image integration are now the center angle of each azimuth bin
put in 1/2 pixel offset in image calibration/integration calcs

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