source: trunk/GSASIIpwdGUI.py @ 271

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

make g77 versions of fortran for binwin2.7 - faster than gfortran!
fix to histogram2d.for
GSASII.py - allow 2D offset in multiplots, fix for large file lists
GSASIIimgGUI.py - more stuff in save/load controls
GSASIIplot.py - 2D offset in multiplots, fix bad behavior in structure drawings
GSASIIpwd.py - more mods to PDF calcs

  • Property svn:keywords set to Date Author Revision URL Id
File size: 70.9 KB
Line 
1#GSASII - data display routines
2########### SVN repository information ###################
3# $Date: 2011-04-28 18:11:32 +0000 (Thu, 28 Apr 2011) $
4# $Author: vondreele $
5# $Revision: 271 $
6# $URL: trunk/GSASIIpwdGUI.py $
7# $Id: GSASIIpwdGUI.py 271 2011-04-28 18:11:32Z vondreele $
8########### SVN repository information ###################
9import wx
10import wx.grid as wg
11import numpy as np
12import math
13import time
14import cPickle
15import GSASIIpath
16import GSASIIpwd as G2pwd
17import GSASIIlattice as G2lat
18import GSASIIspc as G2spc
19import GSASIIindex as G2indx
20import GSASIIplot as G2plt
21import GSASIIgrid as G2gd
22import GSASIIElem as G2elem
23
24VERY_LIGHT_GREY = wx.Colour(235,235,235)
25
26# trig functions in degrees
27sind = lambda x: math.sin(x*math.pi/180.)
28tand = lambda x: math.tan(x*math.pi/180.)
29cosd = lambda x: math.cos(x*math.pi/180.)
30asind = lambda x: 180.*math.asin(x)/math.pi
31       
32def UpdatePeakGrid(self, data):
33    if self.dataDisplay:
34        self.dataFrame.Clear()
35   
36    def OnUnDo(event):
37        DoUnDo()
38        self.dataFrame.UnDo.Enable(False)
39       
40    def DoUnDo():
41        print 'Undo last refinement'
42        file = open(self.undofile,'rb')
43        PatternId = self.PatternId
44        for item in ['Background','Instrument Parameters','Peak List']:
45            self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, item),cPickle.load(file))
46            if self.dataDisplay.GetName() == item:
47                if item == 'Background':
48                    UpdateBackgroundGrid(self,self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, item)))
49                elif item == 'Instrument Parameters':
50                    UpdateInstrumentGrid(self,self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, item)))
51                elif item == 'Peak List':
52                    UpdatePeakGrid(self,self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, item)))
53            print item,' recovered'
54        file.close()
55       
56    def SaveState():
57        self.undofile = self.dirname+'\\GSASII.save'
58        file = open(self.undofile,'wb')
59        PatternId = self.PatternId
60        for item in ['Background','Instrument Parameters','Peak List']:
61            cPickle.dump(self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId,item)),file,1)
62        file.close()
63        self.dataFrame.UnDo.Enable(True)
64               
65    def OnPeakFit(event):
66        SaveState()
67        print 'Peak Fitting - Do one cycle of peak fitting'
68        PatternId = self.PatternId
69        PickId = self.PickId
70        peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Peak List'))
71        if not peaks:
72            self.ErrorDialog('No peaks!','Nothing to fit!')
73            return
74        background = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Background'))[0]
75        limits = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Limits'))[1]
76        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Instrument Parameters'))
77        data = self.PatternTree.GetItemPyData(PatternId)[1]
78        OK,smin,Rwp,runtime,GoOn = G2pwd.DoPeakFit(peaks,background,limits,inst,data)
79        UpdatePeakGrid(self,peaks)
80        G2plt.PlotPatterns(self)
81        if not OK:
82            print 'Refinement failed'
83            dlg = wx.MessageDialog(self, 'Do you want to reload now?', 'Refinement failed',  wx.YES_NO)
84            try:
85                if dlg.ShowModal() == wx.ID_YES:
86                    DoUnDo()
87                    self.dataFrame.UnDo.Enable(False)
88            finally:
89                dlg.Destroy()
90        else:
91            self.dataFrame.UnDo.Enable(True)
92            print "%s%7.2f%s%12.6g" % ('Rwp = ',Rwp,'%, Smin = ',smin)
93            print "%s%8.3f%s " % ('fitpeak time =',runtime,'s')
94            print 'finished'
95        return
96       
97    def OnAutoPeakFit(event):
98        SaveState()
99        print 'AutoPeak Fitting - run until minimized'
100        PatternId = self.PatternId
101        PickId = self.PickId
102        peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Peak List'))
103        if not peaks:
104            self.ErrorDialog('No peaks!','Nothing to fit!')
105            return
106        background = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Background'))[0]
107        limits = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Limits'))[1]
108        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Instrument Parameters'))
109        data = self.PatternTree.GetItemPyData(PatternId)[1]
110        smin = 1.0e15
111        GoOn = True
112        while GoOn:
113            osmin = smin
114            OK,smin,Rwp,runtime,GoOn = G2pwd.DoPeakFit(peaks,background,limits,inst,data)
115            UpdatePeakGrid(self,peaks)
116            if not OK:
117                break
118            G2plt.PlotPatterns(self)
119            print "%s%7.2f%s%12.6g" % ('Rwp = ',Rwp,'%, Smin = ',smin)
120            rat = (osmin-smin)/smin
121            if rat < 1.0e-4: GoOn = False
122        if not OK:
123            print 'Refinement failed'
124            dlg = wx.MessageDialog(self, 'Do you want to reload now?', 'Refinement failed',  wx.YES_NO)
125            try:
126                if dlg.ShowModal() == wx.ID_YES:
127                    DoUnDo()
128                    self.dataFrame.UnDo.Enable(False)
129            finally:
130                dlg.Destroy()
131        else:
132            self.dataFrame.UnDo.Enable(True)
133            print "%s%8.3f%s " % ('fitpeak time =',runtime,'s per cycle')
134            print 'finished'
135        return       
136
137    def RefreshPeakGrid(event):
138        event.StopPropagation()
139        data = self.PeakTable.GetData()
140        T = []
141        for peak in data:T.append(peak[0])
142        D = dict(zip(T,data))
143        T.sort()
144        X = []
145        for key in T: X.append(D[key])
146        data = X       
147        G2plt.PlotPatterns(self)
148       
149    def setBackgroundColors():
150       for r in range(self.dataDisplay.GetNumberRows()):
151           for c in range(self.dataDisplay.GetNumberCols()):
152               if self.dataDisplay.GetColLabelValue(c) in ['position','intensity','sigma','gamma']:
153                   if float(self.dataDisplay.GetCellValue(r,c)) < 0.:
154                       self.dataDisplay.SetCellBackgroundColour(r,c,wx.RED)
155                   else:
156                       self.dataDisplay.SetCellBackgroundColour(r,c,wx.WHITE)
157                       
158    def RefineSelect(event):
159        data = self.PatternTree.GetItemPyData(self.PickId)
160        r,c =  event.GetRow(),event.GetCol()
161        if r < 0 and self.dataDisplay.GetColLabelValue(c) == 'refine':
162            self.dataDisplay.SelectCol(c,False)
163       
164                       
165    def RowSelect(event):
166        r,c =  event.GetRow(),event.GetCol()
167        if r < 0 and c < 0:
168            if self.dataDisplay.IsSelection():
169                self.dataDisplay.ClearSelection()
170        elif c < 0:                   #only row clicks
171            if event.ControlDown():                   
172                if r in self.dataDisplay.GetSelectedRows():
173                    self.dataDisplay.DeselectRow(r)
174                else:
175                    self.dataDisplay.SelectRow(r,True)
176            elif event.ShiftDown():
177                for row in range(r+1):
178                    self.dataDisplay.SelectRow(row,True)
179            else:
180                self.dataDisplay.ClearSelection()
181                self.dataDisplay.SelectRow(r,True)               
182       
183                           
184    def KeyEditPeakGrid(event):
185        rowList = self.dataDisplay.GetSelectedRows()
186        colList = self.dataDisplay.GetSelectedCols()
187        selectList = self.dataDisplay.GetSelectedCells()
188        data = self.PatternTree.GetItemPyData(self.PickId)
189        if event.GetKeyCode() == wx.WXK_RETURN:
190            event.Skip(True)
191        elif event.GetKeyCode() == wx.WXK_CONTROL:
192            event.Skip(True)
193        elif event.GetKeyCode() == wx.WXK_SHIFT:
194            event.Skip(True)
195        elif rowList:
196            self.dataDisplay.ClearSelection()
197            if event.GetKeyCode() == wx.WXK_DELETE:
198                self.dataDisplay.ClearGrid()
199                rowList.reverse()
200                nDel = 0
201                for row in rowList:
202                    self.PeakTable.DeleteRow(row)
203                    nDel += 1
204                if nDel:
205                    msg = wg.GridTableMessage(self.PeakTable, 
206                        wg.GRIDTABLE_NOTIFY_ROWS_DELETED,0,nDel)
207                    self.dataDisplay.ProcessTableMessage(msg)
208                data = self.PeakTable.GetData()
209                self.PatternTree.SetItemPyData(self.PickId,data[:-nDel])
210                self.dataDisplay.ForceRefresh()
211                setBackgroundColors()
212                if not len(self.PatternTree.GetItemPyData(self.PickId)): 
213                    self.dataFrame.PeakFit.Enable(False)
214                    self.dataFrame.AutoPeakFit.Enable(False)
215                       
216        elif colList:
217            self.dataDisplay.ClearSelection()
218            key = event.GetKeyCode()
219            for col in colList:
220                if self.PeakTable.GetTypeName(0,col) == wg.GRID_VALUE_BOOL:
221                    if key == 89: #'Y'
222                        for row in range(self.PeakTable.GetNumberRows()): data[row][col]=True
223                    elif key == 78:  #'N'
224                        for row in range(self.PeakTable.GetNumberRows()): data[row][col]=False
225        elif selectList:
226            self.dataDisplay.ClearSelection()
227            key = event.GetKeyCode()
228            for row,col in selectList:
229                if self.PeakTable.GetTypeName(row,col) == wg.GRID_VALUE_BOOL:
230                    if key == 89: #'Y'
231                        data[row][col]=True
232                    elif key == 78:  #'N'
233                        data[row][col]=False
234        G2plt.PlotPatterns(self)
235           
236    self.dataFrame.SetMenuBar(self.dataFrame.PeakMenu)
237    if not self.dataFrame.GetStatusBar():
238        Status = self.dataFrame.CreateStatusBar()
239    self.Bind(wx.EVT_MENU, OnUnDo, id=G2gd.wxID_UNDO)
240    self.Bind(wx.EVT_MENU, OnPeakFit, id=G2gd.wxID_PEAKFIT)
241    self.Bind(wx.EVT_MENU, OnAutoPeakFit, id=G2gd.wxID_AUTOPEAKFIT)
242    self.dataFrame.PeakFit.Enable(False)
243    self.dataFrame.AutoPeakFit.Enable(False)
244    if data:
245        self.dataFrame.PeakFit.Enable(True)
246        self.dataFrame.AutoPeakFit.Enable(True)
247    self.PickTable = []
248    rowLabels = []
249    for i in range(len(data)): rowLabels.append(str(i+1))
250    colLabels = ['position','refine','intensity','refine','sigma','refine','gamma','refine']
251    Types = [wg.GRID_VALUE_FLOAT+':10,4',wg.GRID_VALUE_BOOL,
252        wg.GRID_VALUE_FLOAT+':10,1',wg.GRID_VALUE_BOOL,
253        wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_BOOL,
254        wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_BOOL]
255    T = []
256    for peak in data:
257        T.append(peak[0])
258    D = dict(zip(T,data))
259    T.sort()
260    X = []
261    for key in T: X.append(D[key])
262    data = X       
263    self.PatternTree.SetItemPyData(self.PickId,data)
264    self.PeakTable = G2gd.Table(data,rowLabels=rowLabels,colLabels=colLabels,types=Types)
265    self.dataFrame.SetLabel('Peak List')
266    self.dataDisplay = G2gd.GSGrid(parent=self.dataFrame)
267    self.dataDisplay.SetTable(self.PeakTable, True)
268    setBackgroundColors()                         
269    self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshPeakGrid)
270    self.dataDisplay.Bind(wx.EVT_KEY_DOWN, KeyEditPeakGrid)
271    self.dataDisplay.Bind(wg.EVT_GRID_LABEL_LEFT_CLICK, RowSelect)                 
272    self.dataDisplay.Bind(wg.EVT_GRID_LABEL_LEFT_DCLICK, RefineSelect)
273    self.dataDisplay.SetMargins(0,0)
274    self.dataDisplay.AutoSizeColumns(False)
275    self.dataFrame.setSizePosLeft([535,350])
276       
277def UpdateBackgroundGrid(self,data):
278    if self.dataDisplay:
279        self.dataFrame.Clear()
280    BackId = G2gd.GetPatternTreeItemId(self,self.PatternId, 'Background')
281    maxTerm = 9
282    Types = [wg.GRID_VALUE_CHOICE+':chebyschev,another,more',
283        wg.GRID_VALUE_BOOL,
284        wg.GRID_VALUE_NUMBER+':1,'+str(maxTerm)]
285    for i in range(maxTerm):
286        Types.append(wg.GRID_VALUE_FLOAT+':10,3')
287   
288    def RefreshBackgroundGrid(event):
289        data = self.BackTable.GetData()
290        M = len(data[0])
291        N = data[0][2]+3
292        item = data[0]
293        if N > M:       #add terms
294            for i in range(M,N): 
295                item.append(0.0)
296                self.BackTable.SetColLabelValue(i,str(i-2))
297            data = [item]
298            msg = wg.GridTableMessage(self.BackTable, 
299                wg.GRIDTABLE_NOTIFY_COLS_APPENDED,0,N-M)
300            self.dataDisplay.ProcessTableMessage(msg)                         
301        elif N < M:     #delete terms
302            new = []
303            for i in range(N):
304                new.append(item[i])
305            data = [new]
306            msg = wg.GridTableMessage(self.BackTable, 
307                wg.GRIDTABLE_NOTIFY_COLS_DELETED,0,M-N)
308            self.dataDisplay.ProcessTableMessage(msg)
309        self.PatternTree.SetItemPyData(BackId,data)
310        event.StopPropagation()
311                 
312    self.BackTable = []
313    N = len(data[0])
314    M = data[0][2]
315    colLabels = ['function','refine','Nterms']
316    rowLabels=['background']
317    for i in range(M): colLabels.append(str(i+1))
318    self.BackTable = G2gd.Table(data,rowLabels=rowLabels,colLabels=colLabels,types=Types)
319    self.dataFrame.SetLabel('Background')
320    self.dataFrame.SetMenuBar(self.dataFrame.BlankMenu)
321    gridPanel = wx.Panel(self.dataFrame)
322    self.dataDisplay = G2gd.GSGrid(gridPanel)               
323    self.dataDisplay.SetTable(self.BackTable, True)
324    self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshBackgroundGrid)               
325    self.dataDisplay.SetMargins(0,0)
326    self.dataDisplay.AutoSizeColumns(False)
327    mainSizer = wx.BoxSizer(wx.VERTICAL)
328    mainSizer.Add(self.dataDisplay,0)
329    mainSizer.Layout()   
330    self.dataDisplay.SetSizer(mainSizer)
331    self.dataFrame.setSizePosLeft(mainSizer.Fit(self.dataFrame))
332       
333def UpdateLimitsGrid(self, data):
334    if self.dataDisplay:
335        self.dataFrame.Clear()
336       
337    def RefreshLimitsGrid(event):
338        event.StopPropagation()
339        data = self.LimitsTable.GetData()
340        old = data[0]
341        new = data[1]
342        new[0] = max(old[0],new[0])
343        new[1] = max(new[0],min(old[1],new[1]))
344        data = [old,new]
345        G2plt.PlotPatterns(self)
346       
347    self.LimitsTable = []
348    colLabels = ['Tmin','Tmax']
349    rowLabels = ['original','changed']
350    Types = [wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3']
351    self.LimitsTable = G2gd.Table(data,rowLabels=rowLabels,colLabels=colLabels,types=Types)
352    self.dataFrame.SetLabel('Limits')
353    self.dataFrame.SetMenuBar(self.dataFrame.BlankMenu)
354    self.dataDisplay = G2gd.GSGrid(parent=self.dataFrame)
355    self.dataDisplay.SetTable(self.LimitsTable, True)
356    self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshLimitsGrid)               
357    self.dataDisplay.SetMargins(0,0)
358    self.dataDisplay.AutoSizeColumns(False)
359    self.dataFrame.setSizePosLeft([230,120])
360   
361def UpdateInstrumentGrid(self, data):
362    if self.dataDisplay:
363        self.dataFrame.Clear()
364    Ka2 = False
365    if len(data[0]) == 13: 
366        Ka2 = True
367    self.dataFrame.SetMenuBar(self.dataFrame.BlankMenu)
368   
369    def RefreshInstrumentGrid(event,doAnyway=False):
370        if doAnyway or event.GetRow() == 1:
371            peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Peak List'))
372            ins = data[1]
373            if 'P' in ins[0]:                                       #update powder peak parameters
374                for peak in peaks:
375                    if Ka2:
376                        peak[4] = ins[6]*tand(peak[0]/2.0)**2+ins[7]*tand(peak[0]/2.0)+ins[8]
377                        peak[6] = ins[9]/cosd(peak[0]/2.0)+ins[10]*tand(peak[0]/2.0)
378                    else:
379                        peak[4] = ins[4]*tand(peak[0]/2.0)**2+ins[5]*tand(peak[0]/2.0)+ins[6]
380                        peak[6] = ins[7]/cosd(peak[0]/2.0)+ins[8]*tand(peak[0]/2.0)
381                       
382    def OnReset(event):
383        if Ka2:
384            data[1][6:12] = data[0][6:12]
385        else:
386            data[1][4:10] = data[0][4:10]
387        RefreshInstrumentGrid(event,doAnyway=True)          #to get peaks updated
388        UpdateInstrumentGrid(self, data)
389       
390    self.InstrumentTable = []
391    if 'P' in data[1][0]:                   #powder data
392        self.dataFrame.SetMenuBar(self.dataFrame.InstMenu)
393        if not self.dataFrame.GetStatusBar():
394            Status = self.dataFrame.CreateStatusBar()
395        self.Bind(wx.EVT_MENU, OnReset, id=G2gd.wxID_INSTPRMRESET)
396        if Ka2:
397            Types = [wg.GRID_VALUE_CHOICE+":PXC,PNC,PNT",wg.GRID_VALUE_FLOAT+':10,6',wg.GRID_VALUE_FLOAT+':10,6',               #type, lam-1 & lam-2
398                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3', #zero, ratio, pola
399                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3', #u,v,w
400                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_FLOAT+':10,2']
401        else:
402            Types = [wg.GRID_VALUE_CHOICE+":PXC,PNC,PNT",wg.GRID_VALUE_FLOAT+':10,6',               #type & lam-1
403                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3', #zero, pola
404                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3', #u,v,w
405                wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_FLOAT+':10,2']
406        colLabels = data[3]
407        rowLabels = ['default','changed','refine']
408        self.InstrumentTable = G2gd.Table(data[:-1],rowLabels=rowLabels,colLabels=colLabels,types=Types)
409        self.dataFrame.SetLabel('Instrument Parameters')
410        gridPanel = wx.Panel(self.dataFrame)
411        self.dataDisplay = G2gd.GSGrid(gridPanel)               
412        self.dataDisplay.SetTable(self.InstrumentTable, True)
413        self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshInstrumentGrid)               
414        self.dataDisplay.SetMargins(0,0)
415        self.dataDisplay.AutoSizeColumns(False)
416        beg = 4
417        if Ka2: beg = 6
418        for i in range(len(data[2])):
419            if i < beg or i == beg+6:
420                self.dataDisplay.SetCellRenderer(2,i,wg.GridCellStringRenderer())
421                self.dataDisplay.SetCellValue(2,i,'')
422                self.dataDisplay.SetReadOnly(2,i,isReadOnly=True)
423            else:
424                self.dataDisplay.SetCellRenderer(2,i,wg.GridCellBoolRenderer())
425                self.dataDisplay.SetCellEditor(2,i,wg.GridCellBoolEditor())
426    else:                       #single crystal data
427        Types = [wg.GRID_VALUE_CHOICE+":SXC,SNC,SNT",wg.GRID_VALUE_FLOAT+':10,6']
428        colLabels = data[2]
429        rowLabels = ['original','changed']
430        self.InstrumentTable = G2gd.Table(data[:-1],rowLabels=rowLabels,colLabels=colLabels,types=Types)
431        self.dataFrame.SetLabel('Instrument Parameters')
432        gridPanel = wx.Panel(self.dataFrame)
433        self.dataDisplay = G2gd.GSGrid(gridPanel)               
434        self.dataDisplay.SetTable(self.InstrumentTable, True)
435        self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshInstrumentGrid)               
436        self.dataDisplay.SetMargins(0,0)
437        self.dataDisplay.AutoSizeColumns(False)
438    mainSizer = wx.BoxSizer(wx.VERTICAL)
439    mainSizer.Add(self.dataDisplay,0)
440    mainSizer.Layout()   
441    self.dataDisplay.SetSizer(mainSizer)
442    self.dataFrame.setSizePosLeft(mainSizer.Fit(self.dataFrame))
443   
444def UpdateSampleGrid(self,data):
445    if self.dataDisplay:
446        self.dataFrame.Clear()
447    self.dataFrame.SetMenuBar(self.dataFrame.BlankMenu)
448    if not self.dataFrame.GetStatusBar():
449        Status = self.dataFrame.CreateStatusBar()   
450    self.dataDisplay = wx.Panel(self.dataFrame)
451   
452    if data['Type'] == 'Debye-Scherrer':
453        parms = [['DisplaceX',' Sample X displacement: ','%.4f',],
454            ['DisplaceY',' Sample Y displacement: ','%.4f',],
455            ['Absorption',' Sample absorption: ','%.4f',],]
456    elif data['Type'] == 'Bragg-Brentano':
457        parms = [['Shift',' Sample displacement: ','%.4f',],
458            ['Transparency',' Sample transparency: ','%.4f'],]
459    parms.append(['Temperature',' Sample temperature: ','%.2f'])
460    parms.append(['Pressure',' Sample pressure: ','%.3f'])
461    parms.append(['Humidity',' Sample humidity: ','%.1f'])
462    parms.append(['Voltage',' Sample voltage: ','%.3f'])
463    parms.append(['Force',' Applied load: ','%.3f'])
464    objList = {}
465
466    def OnScaleRef(event):
467        Obj = event.GetEventObject()
468        data['Scale'][1] = Obj.GetValue()
469       
470    def OnScaleVal(event):
471        Obj = event.GetEventObject()
472        try:
473            scale = float(Obj.GetValue())
474            if scale > 0:
475                data['Scale'][0] = scale
476        except ValueError:
477            pass
478        Obj.SetValue("%.4f"%(data['Scale'][0]))          #reset in case of error
479       
480    def OnHistoType(event):
481        Obj = event.GetEventObject()
482        data['Type'] = Obj.GetValue()
483        if data['Type'] == 'Bragg-Brentano' and 'Shift' not in data:    #set up defaults for new type(s)
484            data['Shift'] = [0.0,False]
485            data['Transparency'] = [0.0,False]
486        self.dataDisplay.Destroy()
487        UpdateSampleGrid(self,data)
488       
489    def OnParmRef(event):
490        Obj = event.GetEventObject()
491        parm = objList[Obj.GetId()]
492        data[parm][1] = Obj.GetValue()
493       
494    def OnParmVal(event):
495        Obj = event.GetEventObject()
496        parm = objList[Obj.GetId()]
497        try:
498            if 'list' in str(type(data[parm[0]])): 
499                data[parm[0]][0] = float(Obj.GetValue())
500            else:
501                data[parm[0]] = float(Obj.GetValue())
502        except ValueError:
503            pass
504        if 'list' in str(type(data[parm[0]])): 
505            Obj.SetValue(parm[2]%(data[parm[0]][0]))          #reset in case of error
506        else:
507            Obj.SetValue(parm[2]%(data[parm[0]]))          #reset in case of error
508               
509    mainSizer = wx.BoxSizer(wx.VERTICAL)
510    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' Sample parameters: '),0,wx.ALIGN_CENTER_VERTICAL)
511    mainSizer.Add((5,5),0)
512    scaleSizer = wx.BoxSizer(wx.HORIZONTAL)
513    scaleRef = wx.CheckBox(self.dataDisplay,label=' Histogram scale factor: ')
514    scaleRef.SetValue(data['Scale'][1])
515    scaleRef.Bind(wx.EVT_CHECKBOX, OnScaleRef)
516    scaleSizer.Add(scaleRef,0,wx.ALIGN_CENTER_VERTICAL)
517    scaleVal = wx.TextCtrl(self.dataDisplay,wx.ID_ANY,
518        '%.4f'%(data['Scale'][0]),style=wx.TE_PROCESS_ENTER)
519    scaleVal.Bind(wx.EVT_TEXT_ENTER,OnScaleVal)
520    scaleVal.Bind(wx.EVT_KILL_FOCUS,OnScaleVal)
521    scaleSizer.Add(scaleVal,0,wx.ALIGN_CENTER_VERTICAL)
522    mainSizer.Add(scaleSizer)
523    mainSizer.Add((0,5),0)
524    typeSizer = wx.BoxSizer(wx.HORIZONTAL)
525    choices = ['Debye-Scherrer','Bragg-Brentano',]
526    histoType = wx.ComboBox(self.dataDisplay,wx.ID_ANY,value=data['Type'],choices=choices,
527        style=wx.CB_READONLY|wx.CB_DROPDOWN)
528    histoType.Bind(wx.EVT_COMBOBOX, OnHistoType)
529    typeSizer.Add(histoType)
530    mainSizer.Add(typeSizer)
531    mainSizer.Add((0,5),0)
532   
533    for parm in parms:
534        parmSizer = wx.BoxSizer(wx.HORIZONTAL)
535        if 'list' in str(type(data[parm[0]])):
536            parmRef = wx.CheckBox(self.dataDisplay,label=parm[1])
537            objList[parmRef.GetId()] = parm[0]
538            parmRef.SetValue(data[parm[0]][1])
539            parmRef.Bind(wx.EVT_CHECKBOX, OnParmRef)
540            parmSizer.Add(parmRef,0,wx.ALIGN_CENTER_VERTICAL)
541            parmVal = wx.TextCtrl(self.dataDisplay,wx.ID_ANY,
542                parm[2]%(data[parm[0]][0]),style=wx.TE_PROCESS_ENTER)
543        else:
544            parmSizer.Add(wx.StaticText(self.dataDisplay,label=parm[1]),
545                0,wx.ALIGN_CENTER_VERTICAL)
546            parmVal = wx.TextCtrl(self.dataDisplay,wx.ID_ANY,
547                parm[2]%(data[parm[0]]),style=wx.TE_PROCESS_ENTER)       
548        objList[parmVal.GetId()] = parm
549        parmVal.Bind(wx.EVT_TEXT_ENTER,OnParmVal)
550        parmVal.Bind(wx.EVT_KILL_FOCUS,OnParmVal)
551        parmSizer.Add(parmVal,0,wx.ALIGN_CENTER_VERTICAL)
552        mainSizer.Add(parmSizer)
553        mainSizer.Add((0,5),0)   
554   
555    mainSizer.Layout()   
556    self.dataDisplay.SetSizer(mainSizer)
557    Size = mainSizer.Fit(self.dataFrame)
558    self.dataDisplay.SetSize(Size)
559    self.dataFrame.setSizePosLeft(Size)
560               
561def UpdateIndexPeaksGrid(self, data):
562    IndexId = G2gd.GetPatternTreeItemId(self,self.PatternId, 'Index Peak List')
563   
564    def RefreshIndexPeaksGrid(event):
565        data = self.IndexPeaksTable.GetData()
566        self.PatternTree.SetItemPyData(IndexId,data)
567       
568    def OnReload(event):
569        data = []
570        peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Peak List'))
571        for peak in peaks:
572            dsp = inst[1]/(2.0*sind(peak[0]/2.0))
573            data.append([peak[0],peak[2],True,False,0,0,0,dsp,0.0])
574        self.PatternTree.SetItemPyData(IndexId,data)
575        UpdateIndexPeaksGrid(self,data)
576       
577    def KeyEditPickGrid(event):
578        colList = self.dataDisplay.GetSelectedCols()
579        rowList = self.dataDisplay.GetSelectedRows()
580        data = self.PatternTree.GetItemPyData(IndexId)
581        if event.GetKeyCode() == wx.WXK_RETURN:
582            event.Skip(True)
583        elif event.GetKeyCode() == wx.WXK_CONTROL:
584            event.Skip(True)
585        elif event.GetKeyCode() == wx.WXK_SHIFT:
586            event.Skip(True)
587        elif colList:
588            self.dataDisplay.ClearSelection()
589            key = event.GetKeyCode()
590            for col in colList:
591                if self.IndexPeaksTable.GetTypeName(0,col) == wg.GRID_VALUE_BOOL:
592                    if key == 89: #'Y'
593                        for row in range(self.IndexPeaksTable.GetNumberRows()): data[row][col]=True
594                    elif key == 78:  #'N'
595                        for row in range(self.IndexPeaksTable.GetNumberRows()): data[row][col]=False
596           
597    if self.dataDisplay:
598        self.dataFrame.Clear()
599    self.dataFrame.SetMenuBar(self.dataFrame.IndPeaksMenu)
600    if not self.dataFrame.GetStatusBar():
601        Status = self.dataFrame.CreateStatusBar()
602    self.Bind(wx.EVT_MENU, OnReload, id=G2gd.wxID_INDXRELOAD)
603    inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Instrument Parameters'))[1]
604    self.dataFrame.IndexPeaks.Enable(False)
605    self.IndexPeaksTable = []
606    if data:
607        self.dataFrame.IndexPeaks.Enable(True)
608        cells = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Unit Cells List'))
609        if cells:
610            cellist = cells[2]
611            dmin = cells[3]
612            self.HKL = []
613            for i,cell in enumerate(cellist):
614                if cell[-1]:
615                    ibrav = cell[2]
616                    A = G2lat.cell2A(cell[3:9])
617                    self.HKL = G2lat.GenHBravais(dmin,ibrav,A)
618                    G2indx.IndexPeaks(data,self.HKL)
619                    for hkl in self.HKL:
620                        hkl.append(2.0*asind(inst[1]/(2.*hkl[3])))             
621    rowLabels = []
622    for i in range(len(data)): rowLabels.append(str(i+1))
623    colLabels = ['position','intensity','use','indexed','h','k','l','d-obs','d-calc']
624    Types = [wg.GRID_VALUE_FLOAT+':10,4',wg.GRID_VALUE_FLOAT+':10,1',wg.GRID_VALUE_BOOL,
625        wg.GRID_VALUE_BOOL,wg.GRID_VALUE_LONG,wg.GRID_VALUE_LONG,wg.GRID_VALUE_LONG,
626        wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_FLOAT+':10,5']
627    self.PatternTree.SetItemPyData(IndexId,data)
628    self.IndexPeaksTable = G2gd.Table(data,rowLabels=rowLabels,colLabels=colLabels,types=Types)
629    self.dataFrame.SetLabel('Index Peak List')
630    self.dataDisplay = G2gd.GSGrid(parent=self.dataFrame)               
631    self.dataDisplay.SetTable(self.IndexPeaksTable, True)
632    self.dataDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshIndexPeaksGrid)
633    self.dataDisplay.Bind(wx.EVT_KEY_DOWN, KeyEditPickGrid)                 
634    self.dataDisplay.SetMargins(0,0)
635    self.dataDisplay.AutoSizeColumns(False)
636    self.dataFrame.setSizePosLeft([490,300])
637 
638def UpdateUnitCellsGrid(self, data):
639    UnitCellsId = G2gd.GetPatternTreeItemId(self,self.PatternId, 'Unit Cells List')
640    bravaisSymb = ['Fm3m','Im3m','Pm3m','R3-H','P6/mmm','I4/mmm',
641        'P4/mmm','Fmmm','Immm','Cmmm','Pmmm','C2/m','P2/m','P1']
642    spaceGroups = ['F m 3 m','I m 3 m','P m 3 m','R -3 H','P 6/m m m','I 4/m m m',
643        'P 4/m m m','F m m m','I m m m','C m m m','P m m m','C 2/m','P 2/m','P -1']
644       
645    def SetLattice(controls):
646        ibrav = bravaisSymb.index(controls[5])
647        if ibrav in [0,1,2]:
648            controls[7] = controls[8] = controls[6]
649            controls[9] = controls[10] = controls[11] = 90.
650        elif ibrav in [3,4,5,6]:
651            controls[7] = controls[6]
652            controls[9] = controls[10] = controls[11] = 90.
653            if ibrav in [3,4]:
654                controls[11] = 120.
655        elif ibrav in [7,8,9,10]:
656            controls[9] = controls[10] = controls[11] = 90.
657        elif ibrav in [11,12]:
658            controls[9] = controls[11] = 90.  # b unique
659        if len(controls) < 13: controls.append(0)
660        controls[12] = G2lat.calc_V(G2lat.cell2A(controls[6:12]))
661        return ibrav
662       
663    def OnNcNo(event):
664        controls[2] = NcNo.GetValue()
665       
666    def OnStartVol(event):
667        try:
668            stVol = int(startVol.GetValue())
669        except ValueError:
670            stVol = 25
671        controls[3] = stVol
672        startVol.SetValue("%d"%(stVol))
673       
674    def OnBravais(event):
675        Obj = event.GetEventObject()
676        bravais[bravList.index(Obj.GetId())] = Obj.GetValue()
677       
678    def OnZero(event):
679        try:
680            Zero = min(0.1,max(-0.1,float(zero.GetValue())))
681        except ValueError:
682            Zero = 0.1
683        controls[1] = Zero
684        zero.SetValue("%.2f"%(Zero))
685       
686    def OnZeroVar(event):
687        controls[0] = zeroVar.GetValue()
688       
689    def OnBravSel(event):
690        controls[5] = bravSel.GetString(bravSel.GetSelection())       
691        UpdateUnitCellsGrid(self,data)
692       
693    def OnCellChange(event):
694        ibrav = bravaisSymb.index(controls[5])
695        Obj = event.GetEventObject()
696        ObjId = cellList.index(Obj.GetId())
697        try:
698            value = max(1.0,float(Obj.GetValue()))
699        except ValueError:
700            if ObjId < 3:               #bad cell edge - reset
701                value = controls[6+ObjId]
702            else:                       #bad angle
703                value = 90.
704        if ibrav in [0,1,2]:
705            controls[6] = controls[7] = controls[8] = value
706            controls[9] = controls[10] = controls[11] = 90.0
707            Obj.SetValue("%.5f"%(controls[6]))
708        elif ibrav in [3,4,5,6]:
709            if ObjId == 0:
710                controls[6] = controls[7] = value
711                Obj.SetValue("%.5f"%(controls[6]))
712            else:
713                controls[8] = value
714                Obj.SetValue("%.5f"%(controls[8]))
715            controls[9] = controls[10] = controls[11] = 90.0
716            if ibrav in [3,4]:
717                controls[11] = 120.
718        elif ibrav in [7,8,9,10]:
719            controls[6+ObjId] = value
720            Obj.SetValue("%.5f"%(controls[6+ObjId]))
721            controls[9] = controls[10] = controls[11] = 90.0
722        elif ibrav in [11,12]:
723            controls[9] = controls[11] = 90.0
724            if ObjId != 3:
725                controls[6+ObjId] = value
726                Obj.SetValue("%.5f"%(controls[6+ObjId]))
727            else:
728                controls[10] = value
729                Obj.SetValue("%.3f"%(controls[10]))
730        else:
731            controls[6+ObjId] = value
732            if ObjId < 3:
733                Obj.SetValue("%.5f"%(controls[6+ObjId]))
734            else:
735                Obj.SetValue("%.3f"%(controls[6+ObjId]))
736        controls[12] = G2lat.calc_V(G2lat.cell2A(controls[6:12]))
737        volVal.SetValue("%.3f"%(controls[12]))
738       
739    def OnHklShow(event):
740        hklShow.SetValue(False)
741        PatternId = self.PatternId
742        PickId = self.PickId   
743        limits = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Limits'))[1]
744        controls,bravais,cells,dmin = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Unit Cells List'))
745        cell = controls[6:12]
746        A = G2lat.cell2A(cell)
747        ibrav = bravaisSymb.index(controls[5])
748        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Instrument Parameters'))
749        inst = dict(zip(inst[3],inst[1]))
750        if 'Lam' in inst:
751            wave = inst['Lam']
752        else:
753            wave = inst['Lam1']
754        dmin = wave/(2.0*sind(limits[1]/2.0))
755        self.HKL = G2lat.GenHBravais(dmin,ibrav,A)
756        for hkl in self.HKL:
757            hkl.append(2.0*asind(wave/(2.*hkl[3])))             
758        if 'PKS' in self.PatternTree.GetItemText(self.PatternId):
759            G2plt.PlotPowderLines(self)
760        else:
761            G2plt.PlotPatterns(self)
762       
763       
764    def RefineCell(event):
765        def cellPrint(ibrav,A):
766            cell = G2lat.A2cell(A)
767            Vol = G2lat.calc_V(A)
768            if ibrav in [0,1,2]:
769                print "%s%10.6f" % ('a =',cell[0])
770            elif ibrav in [3,4,5,6]:
771                print "%s%10.6f %s%10.6f %s%12.3f" % ('a =',cell[0],' c =',cell[2],' volume =',Vol)
772            elif ibrav in [7,8,9,10]:
773                print "%s%10.6f %s%10.6f %s%10.6f %s%12.3f" % ('a =',cell[0],'b =',cell[1],'c =',cell[2],' volume =',Vol)
774            elif ibrav in [11,12]:
775                print "%s%10.6f %s%10.6f %s%10.6f %s%8.3f %s%12.3f" % ('a =',cell[0],'b =',cell[1],'c =',cell[2],'beta =',cell[4],' volume =',Vol)
776            else:
777                print "%s%10.6f %s%10.6f %s%10.6f" % ('a =',cell[0],'b =',cell[1],'c =',cell[2])
778                print "%s%8.3f %s%8.3f %s%8.3f %s%12.3f" % ('alpha =',cell[3],'beta =',cell[4],'gamma =',cell[5],' volume =',Vol)
779             
780        PatternId = self.PatternId
781        PickId = self.PickId   
782        peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Index Peak List'))
783        if not peaks:
784            self.ErrorDialog('No peaks!', 'Nothing to refine!')
785            return       
786        print 'Refine cell'
787        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Instrument Parameters'))[1]
788        controls,bravais,cells,dmin = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Unit Cells List'))
789        cell = controls[6:12]
790        A = G2lat.cell2A(cell)
791        print controls[5]
792        ibrav = bravaisSymb.index(controls[5])
793        dmin = G2indx.getDmin(peaks)-0.005
794        Lhkl,M20,X20 = G2indx.refinePeaks(peaks,ibrav,A)
795        controls[6:12] = G2lat.A2cell(A)
796        controls[12] = G2lat.calc_V(A)
797        data = [controls,bravais,cells,dmin]
798        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Unit Cells List'),data)
799        self.HKL = G2lat.GenHBravais(dmin,ibrav,A)
800        UpdateUnitCellsGrid(self,data)
801        print "%s%10.3f" % ('refinement M20 = ',M20)
802        print 'unindexed lines = ',X20
803        cellPrint(ibrav,A)
804        for hkl in self.HKL:
805            hkl.append(2.0*asind(inst[1]/(2.*hkl[3])))             
806        if 'PKS' in self.PatternTree.GetItemText(self.PatternId):
807            G2plt.PlotPowderLines(self)
808        else:
809            G2plt.PlotPatterns(self)
810       
811    def IndexPeaks(event):
812        PatternId = self.PatternId   
813#        peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Index Peak List'))
814#        if not peaks:
815#            self.ErrorDialog('No peaks!', 'Nothing to index!')
816#            return
817        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Instrument Parameters'))[1]
818        print 'Peak Indexing'
819        try:
820            controls,bravais,cells,dmin = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Unit Cells List'))
821            cells = []
822        except ValueError:
823            self.ErrorDialog('Error','Need to set controls in Unit Cell List first')
824            return
825        if True not in bravais:
826            self.ErrorDialog('Error','No Bravais lattices selected')
827            return
828        self.dataFrame.CopyCell.Enable(False)
829        OK,dmin,cells = G2indx.DoIndexPeaks(peaks,inst,controls,bravais)
830        if OK:
831            data = [controls,bravais,cells,dmin]
832            self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PatternId, 'Unit Cells List'),data)
833            UpdateUnitCellsGrid(self,data)
834            bestCell = cells[0]
835            if bestCell[0] > 10.:
836                self.HKL = G2lat.GenHBravais(dmin,bestCell[2],G2lat.cell2A(bestCell[3:9]))
837                for hkl in self.HKL:
838                    hkl.append(2.0*asind(inst[1]/(2.*hkl[3])))             
839                if 'PKS' in self.PatternTree.GetItemText(self.PatternId):
840                    G2plt.PlotPowderLines(self)
841                else:
842                    G2plt.PlotPatterns(self)
843        self.dataFrame.CopyCell.Enable(True)
844        self.dataFrame.IndexPeaks.Enable(True)
845        self.dataFrame.MakeNewPhase.Enable(True)
846        UpdateUnitCellsGrid(self,data)
847               
848    def CopyUnitCell(event):
849        controls,bravais,cells,dmin = self.PatternTree.GetItemPyData(UnitCellsId)
850        for Cell in cells:
851            if Cell[-1]:
852                break
853        cell = Cell[2:9]
854        controls[4] = 1
855        controls[5] = bravaisSymb[cell[0]]
856        controls[6:12] = cell[1:8]
857        controls[12] = G2lat.calc_V(G2lat.cell2A(controls[6:12]))
858        self.PatternTree.SetItemPyData(UnitCellsId,[controls,bravais,cells,dmin])
859        UpdateUnitCellsGrid(self,data)
860        self.dataFrame.RefineCell.Enable(True)
861       
862    def MakeNewPhase(event):
863        if not G2gd.GetPatternTreeItemId(self,self.root,'Phases'):
864            sub = self.PatternTree.AppendItem(parent=self.root,text='Phases')
865        else:
866            sub = G2gd.GetPatternTreeItemId(self,self.root,'Phases')
867        PhaseName = ''
868        dlg = wx.TextEntryDialog(None,'Enter a name for this phase','Phase Name Entry','New phase',
869            style=wx.OK)
870        if dlg.ShowModal() == wx.ID_OK:
871            PhaseName = dlg.GetValue()
872        dlg.Destroy()
873        cells = self.PatternTree.GetItemPyData(UnitCellsId)[2]
874        for Cell in cells:
875            if Cell[-1]:
876                break
877        cell = Cell[2:10]       
878        sub = self.PatternTree.AppendItem(parent=sub,text=PhaseName)
879        E,SGData = G2spc.SpcGroup(spaceGroups[cell[0]])
880        self.PatternTree.SetItemPyData(sub, \
881            {'General':{'Name':'phase name','Type':'nuclear','SGData':SGData,
882            'Cell':[False,]+cell[1:],
883            'Pawley dmin':0.25},'Atoms':[],'Drawing':{},'Histograms':{}})
884        Status.SetStatusText('Change space group if needed')
885           
886    def RefreshUnitCellsGrid(event):
887        cells,dmin = self.PatternTree.GetItemPyData(UnitCellsId)[2:]
888        r,c =  event.GetRow(),event.GetCol()
889        if cells:
890            if c == 2:
891                for i in range(len(cells)):
892                    cells[i][-1] = False
893                    UnitCellsTable.SetValue(i,c,False)
894                UnitCellsTable.SetValue(r,c,True)
895                cells[r][-1] = True
896                ibrav = cells[r][2]
897                A = G2lat.cell2A(cells[r][3:9])
898                self.HKL = G2lat.GenHBravais(dmin,ibrav,A)
899                for hkl in self.HKL:
900                    hkl.append(2.0*asind(inst[1]/(2.*hkl[3])))
901                if 'PKS' in self.PatternTree.GetItemText(self.PatternId):
902                    G2plt.PlotPowderLines(self)
903                else:
904                    G2plt.PlotPatterns(self)
905       
906    if self.dataDisplay:
907        self.dataFrame.Clear()
908    self.dataFrame.SetMenuBar(self.dataFrame.IndexMenu)
909    if not self.dataFrame.GetStatusBar():
910        Status = self.dataFrame.CreateStatusBar()
911    self.Bind(wx.EVT_MENU, IndexPeaks, id=G2gd.wxID_INDEXPEAKS)
912    self.Bind(wx.EVT_MENU, CopyUnitCell, id=G2gd.wxID_COPYCELL)
913    self.Bind(wx.EVT_MENU, RefineCell, id=G2gd.wxID_REFINECELL)
914    self.Bind(wx.EVT_MENU, MakeNewPhase, id=G2gd.wxID_MAKENEWPHASE)
915   
916    controls,bravais,cells,dmin = data
917    if len(controls) < 13:              #add cell volume if missing
918        controls.append(G2lat.calc_V(G2lat.cell2A(controls[6:12])))
919    self.PatternTree.SetItemPyData(UnitCellsId,data)            #update with volume
920    inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Instrument Parameters'))[1]
921    bravaisNames = ['Cubic-F','Cubic-I','Cubic-P','Trigonal-R','Trigonal/Hexagonal-P',
922        'Tetragonal-I','Tetragonal-P','Orthorhombic-F','Orthorhombic-I','Orthorhombic-C',
923        'Orthorhombic-P','Monoclinic-C','Monoclinic-P','Triclinic']
924    cellGUIlist = [[[0,1,2],4,zip([" Unit cell: a = "," Vol = "],["%.5f","%.3f"],[True,False],[0,0])],
925    [[3,4,5,6],6,zip([" Unit cell: a = "," c = "," Vol = "],["%.5f","%.5f","%.3f"],[True,True,False],[0,2,0])],
926    [[7,8,9,10],8,zip([" Unit cell: a = "," b = "," c = "," Vol = "],["%.5f","%.5f","%.5f","%.3f"],
927        [True,True,True,False],[0,1,2,0])],
928    [[11,12],10,zip([" Unit cell: a = "," b = "," c = "," beta = "," Vol = "],
929        ["%.5f","%.5f","%.5f","%.3f","%.3f"],[True,True,True,True,False],[0,1,2,4,0])],
930    [[13,],8,zip([" Unit cell: a = "," b = "," c = "," Vol = "," alpha = "," beta = "," gamma = "],
931        ["%.5f","%.5f","%.5f","%.3f","%.3f","%.3f","%.3f"],
932        [True,True,True,False,True,True,True],[0,1,2,0,3,4,5])]]
933   
934    self.dataFrame.SetLabel('Unit Cells List')
935    self.sp = wx.SplitterWindow(self.dataFrame)
936    self.dataDisplay = wx.Panel(self.sp, style=wx.SUNKEN_BORDER)
937    self.dataFrame.IndexPeaks.Enable(False)
938    peaks = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.PatternId, 'Index Peak List'))
939    if peaks:
940        self.dataFrame.IndexPeaks.Enable(True)
941    self.dataFrame.RefineCell.Enable(False)
942    if controls[12] > 1.0:                               #if a "real" volume (i.e. not default)
943        self.dataFrame.RefineCell.Enable(True)   
944    self.dataFrame.CopyCell.Enable(False)
945    self.dataFrame.MakeNewPhase.Enable(False)       
946    if cells:
947        self.bottom = wx.Panel(self.sp, style=wx.SUNKEN_BORDER)
948        self.sp.SplitHorizontally(self.dataDisplay,self.bottom,0)
949        self.dataFrame.CopyCell.Enable(True)
950        self.dataFrame.MakeNewPhase.Enable(True)       
951    mainSizer = wx.BoxSizer(wx.VERTICAL)
952    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' Indexing controls: '),0,wx.ALIGN_CENTER_VERTICAL)
953    mainSizer.Add((5,5),0)
954    littleSizer = wx.FlexGridSizer(2,5,5,5)
955    littleSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' Max Nc/Nobs '),0,wx.ALIGN_CENTER_VERTICAL)
956    NcNo = wx.SpinCtrl(self.dataDisplay)
957    NcNo.SetRange(1,6)
958    NcNo.SetValue(controls[2])
959    NcNo.Bind(wx.EVT_SPINCTRL,OnNcNo)
960    littleSizer.Add(NcNo,0,wx.ALIGN_CENTER_VERTICAL)
961    littleSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' Start Volume '),0,wx.ALIGN_CENTER_VERTICAL)
962    startVol = wx.TextCtrl(self.dataDisplay,value=str(controls[3]),style=wx.TE_PROCESS_ENTER)
963    startVol.Bind(wx.EVT_TEXT_ENTER,OnStartVol)
964    startVol.Bind(wx.EVT_KILL_FOCUS,OnStartVol)
965    littleSizer.Add(startVol,0,wx.ALIGN_CENTER_VERTICAL)
966    mainSizer.Add(littleSizer,0)
967    mainSizer.Add((5,5),0)
968    mainSizer.Add(wx.StaticText(self.dataDisplay,label=' Select Bravais Lattices for indexing: '),
969        0,wx.ALIGN_CENTER_VERTICAL)
970    mainSizer.Add((5,5),0)
971    littleSizer = wx.FlexGridSizer(2,7,5,5)
972    bravList = []
973    bravs = zip(bravais,bravaisNames)
974    for brav,bravName in bravs:
975        bravCk = wx.CheckBox(self.dataDisplay,label=bravName)
976        bravList.append(bravCk.GetId())
977        bravCk.SetValue(brav)
978        bravCk.Bind(wx.EVT_CHECKBOX,OnBravais)
979        littleSizer.Add(bravCk,0,wx.ALIGN_CENTER_VERTICAL)
980    mainSizer.Add(littleSizer,0)
981    mainSizer.Add((5,5),0)
982    littleSizer = wx.FlexGridSizer(1,3,5,5)
983    littleSizer.Add(wx.StaticText(self.dataDisplay,label=" Zero offset"),0,wx.ALIGN_CENTER_VERTICAL)
984    zero = wx.TextCtrl(self.dataDisplay,value="%.2f"%(controls[1]),style=wx.TE_PROCESS_ENTER)
985    zero.Bind(wx.EVT_TEXT_ENTER,OnZero)
986    zero.Bind(wx.EVT_KILL_FOCUS,OnZero)
987    littleSizer.Add(zero,0,wx.ALIGN_CENTER_VERTICAL)
988    zeroVar = wx.CheckBox(self.dataDisplay,label="Vary? (not implemented)")
989    zeroVar.Bind(wx.EVT_CHECKBOX,OnZeroVar)
990    littleSizer.Add(zeroVar,0,wx.ALIGN_CENTER_VERTICAL)
991    mainSizer.Add(littleSizer,0)
992    mainSizer.Add((5,5),0)
993    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' Cell Refinement: '),0,wx.ALIGN_CENTER_VERTICAL)
994    mainSizer.Add((5,5),0)
995    littleSizer = wx.FlexGridSizer(1,3,5,5)
996    littleSizer.Add(wx.StaticText(self.dataDisplay,label=" Bravais lattice "),0,wx.ALIGN_CENTER_VERTICAL)
997    bravSel = wx.Choice(self.dataDisplay,choices=bravaisSymb)
998    bravSel.SetSelection(bravaisSymb.index(controls[5]))
999    bravSel.Bind(wx.EVT_CHOICE,OnBravSel)
1000    littleSizer.Add(bravSel,0,wx.ALIGN_CENTER_VERTICAL)
1001    hklShow = wx.CheckBox(self.dataDisplay,label="Show starting hkl positions")
1002    hklShow.Bind(wx.EVT_CHECKBOX,OnHklShow)
1003    littleSizer.Add(hklShow,0,wx.ALIGN_CENTER_VERTICAL)
1004    mainSizer.Add(littleSizer,0)
1005    mainSizer.Add((5,5),0)
1006    ibrav = SetLattice(controls)
1007    for cellGUI in cellGUIlist:
1008        if ibrav in cellGUI[0]:
1009            useGUI = cellGUI
1010    cellList = []
1011    littleSizer = wx.FlexGridSizer(2,useGUI[1],5,5)
1012    for txt,fmt,ifEdit,Id in useGUI[2]:
1013        littleSizer.Add(wx.StaticText(self.dataDisplay,label=txt),0,wx.ALIGN_CENTER_VERTICAL)
1014        if ifEdit:          #a,b,c,etc.
1015            cellVal = wx.TextCtrl(self.dataDisplay,value=(fmt%(controls[6+Id])),style=wx.TE_PROCESS_ENTER)
1016            cellVal.Bind(wx.EVT_TEXT_ENTER,OnCellChange)       
1017            cellVal.Bind(wx.EVT_KILL_FOCUS,OnCellChange)
1018            littleSizer.Add(cellVal,0,wx.ALIGN_CENTER_VERTICAL)
1019            cellList.append(cellVal.GetId())
1020        else:               #volume
1021            volVal = wx.TextCtrl(self.dataDisplay,value=(fmt%(controls[12])),style=wx.TE_READONLY)
1022            volVal.SetBackgroundColour(VERY_LIGHT_GREY)
1023            littleSizer.Add(volVal,0,wx.ALIGN_CENTER_VERTICAL)
1024    mainSizer.Add(littleSizer,0)
1025    mainSizer.Layout()   
1026    self.dataDisplay.SetSizer(mainSizer)
1027    topSize = mainSizer.Fit(self.dataFrame)
1028    self.dataDisplay.SetSize(topSize)
1029    if cells:
1030        if ibrav == 13:
1031            topSize[1] += 230
1032        else:
1033            topSize[1] += 200
1034    self.dataFrame.setSizePosLeft(topSize)
1035   
1036   
1037    if cells:
1038        bottomSize = self.bottom.GetSize()
1039        if ibrav == 13:
1040            bottomSize[1] -= 240
1041        else:
1042            bottomSize[1] -= 210
1043        wx.StaticText(parent=self.bottom,label=' Indexing Result ')
1044        rowLabels = []
1045        colLabels = ['M20','X20','use','Bravais','a','b','c','alpha','beta','gamma','Volume']
1046        Types = [wg.GRID_VALUE_FLOAT+':10,2',wg.GRID_VALUE_NUMBER,wg.GRID_VALUE_BOOL,wg.GRID_VALUE_STRING,
1047            wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_FLOAT+':10,5',wg.GRID_VALUE_FLOAT+':10,5',
1048            wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',wg.GRID_VALUE_FLOAT+':10,3',
1049            wg.GRID_VALUE_FLOAT+':10,2']
1050        numRows = len(cells)
1051        table = []
1052        for cell in cells:
1053            rowLabels.append('')
1054            row = cell[0:2]+[cell[-1]]+[bravaisSymb[cell[2]]]+cell[3:10]
1055            if cell[-1]:
1056                A = G2lat.cell2A(cell[3:9])
1057                self.HKL = G2lat.GenHBravais(dmin,cell[2],A)
1058                for hkl in self.HKL:
1059                    hkl.append(2.0*asind(inst[1]/(2.*hkl[3])))
1060            table.append(row)
1061        UnitCellsTable = G2gd.Table(table,rowLabels=rowLabels,colLabels=colLabels,types=Types)
1062        gridDisplay = G2gd.GSGrid(self.bottom)
1063        gridDisplay.SetPosition(wx.Point(0,20))               
1064        gridDisplay.SetTable(UnitCellsTable, True)
1065        self.dataFrame.CopyCell.Enable(True)
1066        gridDisplay.Bind(wg.EVT_GRID_CELL_CHANGE, RefreshUnitCellsGrid)
1067        gridDisplay.SetMargins(0,0)
1068        gridDisplay.SetRowLabelSize(0)
1069        gridDisplay.AutoSizeColumns(False)
1070        for r in range(gridDisplay.GetNumberRows()):
1071            for c in range(gridDisplay.GetNumberCols()):
1072                if c == 2:
1073                    gridDisplay.SetReadOnly(r,c,isReadOnly=False)
1074                else:
1075                    gridDisplay.SetReadOnly(r,c,isReadOnly=True)
1076        gridDisplay.SetSize(bottomSize)
1077
1078def UpdatePDFGrid(self,data):
1079    global inst
1080    tth2q = lambda t,w:4.0*math.pi*sind(t/2.0)/w
1081    dataFile = self.PatternTree.GetItemText(self.PatternId)
1082    powName = 'PWDR'+dataFile[4:]
1083    powId = G2gd.GetPatternTreeItemId(self,self.root, powName)
1084    fullLimits,limits = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,powId, 'Limits'))
1085    inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,powId, 'Instrument Parameters'))
1086    inst = dict(zip(inst[3],inst[1]))
1087    if 'Lam' in inst:
1088        keV = 12.397639/inst['Lam']
1089    else:
1090        keV = 12.397639/inst['Lam1']
1091    wave = 12.397639/keV
1092    qLimits = [tth2q(fullLimits[0],wave),tth2q(fullLimits[1],wave)]
1093    data['QScaleLim'][0] = max(qLimits[0],data['QScaleLim'][0])
1094    data['QScaleLim'][1] = min(qLimits[1],data['QScaleLim'][1])
1095    polariz = inst['Polariz.']
1096    azimuth = inst['Azimuth']
1097    itemDict = {}
1098   
1099    def FillFileSizer(fileSizer,key):
1100        #fileSizer is a FlexGridSizer(3,6)
1101       
1102        def OnSelectFile(event):
1103            Obj = event.GetEventObject()
1104            fileKey,itemKey,fmt = itemDict[Obj.GetId()]
1105            if itemKey == 'Name':
1106                value = Obj.GetValue()
1107            Obj.SetValue(fmt%(value))
1108            data[fileKey][itemKey] = value
1109            UpdatePDFGrid(self,data)
1110       
1111        def OnValueChange(event):
1112            Obj = event.GetEventObject()
1113            fileKey,itemKey,fmt = itemDict[Obj.GetId()]
1114            try:
1115                value = float(Obj.GetValue())
1116            except ValueError:
1117                value = -1.0
1118            Obj.SetValue(fmt%(value))
1119            data[fileKey][itemKey] = value
1120            auxPlot = ComputePDF(data)
1121            G2plt.PlotISFG(self,newPlot=True)
1122                       
1123        item = data[key]
1124        fileList = np.array(GetFileList('PWDR')).T[1]
1125        fileSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' '+key+' file:'),0,wx.ALIGN_CENTER_VERTICAL)
1126        fileName = wx.ComboBox(self.dataDisplay,value=item['Name'],choices=fileList,
1127            style=wx.CB_READONLY|wx.CB_DROPDOWN)
1128        itemDict[fileName.GetId()] = [key,'Name','%s']
1129        fileName.Bind(wx.EVT_COMBOBOX,OnSelectFile)       
1130        fileSizer.Add(fileName,0,)
1131        fileSizer.Add(wx.StaticText(parent=self.dataDisplay,label='Multiplier:'),0,wx.ALIGN_CENTER_VERTICAL)
1132        mult = wx.TextCtrl(self.dataDisplay,value='%.3f'%(item['Mult']),style=wx.TE_PROCESS_ENTER)
1133        itemDict[mult.GetId()] = [key,'Mult','%.3f']
1134        mult.Bind(wx.EVT_TEXT_ENTER,OnValueChange)       
1135        mult.Bind(wx.EVT_KILL_FOCUS,OnValueChange)
1136        fileSizer.Add(mult,0,)
1137        fileSizer.Add(wx.StaticText(parent=self.dataDisplay,label='Add:'),0,wx.ALIGN_CENTER_VERTICAL)
1138        add = wx.TextCtrl(self.dataDisplay,value='%.0f'%(item['Add']),style=wx.TE_PROCESS_ENTER)
1139        itemDict[add.GetId()] = [key,'Add','%.0f']
1140        add.Bind(wx.EVT_TEXT_ENTER,OnValueChange)       
1141        add.Bind(wx.EVT_KILL_FOCUS,OnValueChange)
1142        fileSizer.Add(add,0,)
1143       
1144    def SumElementVolumes():
1145        sumVol = 0.
1146        ElList = data['ElList']
1147        for El in ElList:
1148            Avol = (4.*math.pi/3.)*ElList[El]['Drad']**3
1149            sumVol += Avol*ElList[El]['FormulaNo']
1150        return sumVol
1151        auxPlot = ComputePDF(data)
1152        G2plt.PlotISFG(self,newPlot=False)       
1153       
1154    def FillElemSizer(elemSizer,ElData):
1155       
1156        def OnFractionChange(event):
1157            try:
1158                value = max(0.0,float(num.GetValue()))
1159            except ValueError:
1160                value = 0.0
1161            num.SetValue('%.3f'%(value))
1162            ElData['FormulaNo'] = value
1163            data['Form Vol'] = max(10.0,SumElementVolumes())
1164            formVol.SetValue('%.2f'%(data['Form Vol']))
1165            UpdatePDFGrid(self,data)
1166            auxPlot = ComputePDF(data)
1167            G2plt.PlotISFG(self,newPlot=False)       
1168       
1169        elemSizer.Add(wx.StaticText(parent=self.dataDisplay,
1170            label=' Element: '+'%2s'%(ElData['Symbol'])+' * '),0,wx.ALIGN_CENTER_VERTICAL)
1171        num = wx.TextCtrl(self.dataDisplay,value='%.3f'%(ElData['FormulaNo']),style=wx.TE_PROCESS_ENTER)
1172        num.Bind(wx.EVT_TEXT_ENTER,OnFractionChange)       
1173        num.Bind(wx.EVT_KILL_FOCUS,OnFractionChange)
1174        elemSizer.Add(num,0,wx.ALIGN_CENTER_VERTICAL)
1175        elemSizer.Add(wx.StaticText(parent=self.dataDisplay,
1176            label="f': %.3f"%(ElData['fp'])+' f": %.3f'%(ElData['fpp'])+' mu: %.2f barns'%(ElData['mu']) ),
1177            0,wx.ALIGN_CENTER_VERTICAL)
1178           
1179    def OnGeometry(event):
1180        data['Geometry'] = geometry.GetValue()
1181        UpdatePDFGrid(self,data)
1182        auxPlot = ComputePDF(data)
1183        G2plt.PlotISFG(self,newPlot=False)       
1184       
1185    def OnDetType(event):
1186        data['DetType'] = detType.GetValue()
1187        UpdatePDFGrid(self,data)
1188        auxPlot = ComputePDF(data)
1189        G2plt.PlotISFG(self,newPlot=False)       
1190       
1191    def OnFormVol(event):
1192        try:
1193            value = float(formVol.GetValue())
1194            if value <= 0.0:
1195                raise ValueError
1196        except ValueError:
1197            value = data['Form Vol']
1198        data['Form Vol'] = value
1199        UpdatePDFGrid(self,data)
1200        auxPlot = ComputePDF(data)
1201        G2plt.PlotISFG(self,newPlot=False)       
1202       
1203    def OnDiameter(event):
1204        try:
1205            value = float(diam.GetValue())
1206            if value <= 0.0:
1207                raise ValueError
1208        except ValueError:
1209            value = data['Diam']
1210        data['Diam'] = value
1211        UpdatePDFGrid(self,data)
1212        auxPlot = ComputePDF(data)
1213        G2plt.PlotISFG(self,newPlot=False)
1214       
1215    def OnPolaVal(event):
1216        try:
1217            value = float(polaVal.GetValue())
1218            if not (0.0 <= value <= 1.0):
1219                raise ValueError
1220        except ValueError:
1221            value = inst['Polariz.']
1222        inst['Polariz.'] = value
1223        polaVal.SetValue('%.2f'%(inst['Polariz.']))
1224        UpdatePDFGrid(self,data)
1225        auxPlot = ComputePDF(data)
1226        G2plt.PlotISFG(self,newPlot=False)
1227               
1228    def OnAzimVal(event):
1229        try:
1230            value = float(azimVal.GetValue())
1231            if not (0. <= value <= 360.):
1232                raise ValueError
1233        except ValueError:
1234            value = inst['Azimuth']
1235        inst['Azimuth'] = value
1236        azimVal.SetValue('%.1f'%(inst['Azimuth']))
1237        UpdatePDFGrid(self,data)
1238        auxPlot = ComputePDF(data)
1239        G2plt.PlotISFG(self,newPlot=False)
1240                       
1241    def OnObliqCoeff(event):
1242        try:
1243            value = float(obliqCoeff.GetValue())
1244            if value < 0.0:
1245                raise ValueError
1246            elif value > 1.0:
1247                value = 1.0
1248        except ValueError:
1249            value = data['ObliqCoeff']
1250        data['ObliqCoeff'] = value
1251        obliqCoeff.SetValue('%.3f'%(value))
1252        auxPlot = ComputePDF(data)
1253        G2plt.PlotISFG(self,newPlot=False)
1254       
1255    def OnRulandWdt(event):
1256        try:
1257            value = float(rulandWdt.GetValue())
1258            if value <= 0.001:
1259                raise ValueError
1260            elif value > 1.0:
1261                value = 1.0
1262        except ValueError:
1263            value = data['Ruland']
1264        data['Ruland'] = value
1265        rulandWdt.SetValue('%.3f'%(value))
1266        auxPlot = ComputePDF(data)
1267        G2plt.PlotISFG(self,newPlot=False)
1268       
1269    def OnLorch(event):
1270        data['Lorch'] = lorch.GetValue()
1271        auxPlot = ComputePDF(data)
1272        G2plt.PlotISFG(self,newPlot=False)       
1273                       
1274    def OnPacking(event):
1275        try:
1276            value = float(pack.GetValue())
1277            if value <= 0.0:
1278                raise ValueError
1279        except ValueError:
1280            value = data['Pack']
1281        data['Pack'] = value
1282        UpdatePDFGrid(self,data)
1283        G2plt.PlotISFG(self,newPlot=False)       
1284               
1285    def OnSQmin(event):
1286        try:
1287            value = float(SQmin.GetValue())
1288            if value < qLimits[0]:
1289                raise ValueError
1290        except ValueError:
1291            value = max(qLimits[0],data['QScaleLim'][0])
1292        data['QScaleLim'][0] = value
1293        SQmin.SetValue('%.1f'%(value))
1294        auxPlot = ComputePDF(data)
1295        G2plt.PlotISFG(self,newPlot=True)       
1296       
1297    def OnSQmax(event):
1298        try:
1299            value = float(SQmax.GetValue())
1300            if value > qLimits[1]:
1301                raise ValueError
1302        except ValueError:
1303            value = min(qLimits[1],data['QScaleLim'][1])
1304        data['QScaleLim'][1] = value
1305        if value < data['QScaleLim'][0]:
1306            data['QScaleLim'][0] = 0.90*value
1307            SQmin.SetValue('%.1f'%(data['QScaleLim'][0]))
1308        SQmax.SetValue('%.1f'%(value))
1309        auxPlot = ComputePDF(data)
1310        G2plt.PlotISFG(self,newPlot=True)
1311       
1312    def OnResetQ(event):
1313        data['QScaleLim'][1] = qLimits[1]
1314        SQmax.SetValue('%.1f'%(data['QScaleLim'][1]))
1315        data['QScaleLim'][0] = 0.9*qLimits[1]
1316        SQmin.SetValue('%.1f'%(data['QScaleLim'][0]))
1317        auxPlot = ComputePDF(data)
1318        G2plt.PlotISFG(self,newPlot=True)       
1319
1320    def GetFileList(fileType,skip=None):
1321        fileList = [[False,'',0]]
1322        Source = ''
1323        id, cookie = self.PatternTree.GetFirstChild(self.root)
1324        while id:
1325            name = self.PatternTree.GetItemText(id)
1326            if fileType in name:
1327                if id == skip:
1328                    Source = name
1329                else:
1330                    fileList.append([False,name,id])
1331            id, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1332        if skip:
1333            return fileList,Source
1334        else:
1335            return fileList
1336       
1337    def OnCopyPDFControls(event):
1338        import copy
1339        TextList,Source = GetFileList('PDF',skip=self.PatternId)
1340        TextList[0] = [False,'All PDF',0]
1341        if len(TextList) == 1:
1342            self.ErrorDialog('Nothing to copy controls to','There must be more than one "PDF" pattern')
1343            return
1344        dlg = self.CopyDialog(self,'Copy PDF controls','Copy controls from '+Source+' to:',TextList)
1345        try:
1346            if dlg.ShowModal() == wx.ID_OK:
1347                result = dlg.GetData()
1348                if result[0][0]:
1349                    result = TextList[1:]
1350                    for item in result: item[0] = True
1351                for i,item in enumerate(result):
1352                    ifcopy,name,id = item
1353                    if ifcopy:
1354                        olddata = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,id, 'PDF Controls'))
1355                        sample = olddata['Sample']
1356                        olddata.update(data)
1357                        olddata['Sample'] = sample
1358                        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,id, 'PDF Controls'),olddata)
1359                Status.SetStatusText('PDF controls copied')
1360        finally:
1361            dlg.Destroy()
1362               
1363    def OnSavePDFControls(event):
1364        print 'save PDF controls?'
1365       
1366    def OnLoadPDFControls(event):
1367        print 'Load PDF controls?'
1368       
1369    def OnAddElement(event):
1370        ElList = data['ElList']
1371        PE = G2elem.PickElement(self,oneOnly=True)
1372        if PE.ShowModal() == wx.ID_OK:
1373            El = PE.Elem
1374            if El not in ElList:
1375                ElemSym = El.strip().upper()               
1376                FpMu = G2elem.FPcalc(G2elem.GetXsectionCoeff(ElemSym), keV)
1377                ElData = G2elem.GetFormFactorCoeff(ElemSym)[0]
1378                ElData['FormulaNo'] = 0.0
1379                ElData.update(G2elem.GetAtomInfo(ElemSym))
1380                ElData.update(dict(zip(['fp','fpp','mu'],FpMu)))
1381                ElData.update(G2elem.GetFFC5(El))
1382                data['ElList'][El] = ElData
1383            data['Form Vol'] = max(10.0,SumElementVolumes())
1384        PE.Destroy()
1385        UpdatePDFGrid(self,data)
1386       
1387    def OnDeleteElement(event):
1388        ElList = data['ElList']
1389        choice = ElList.keys()
1390        dlg = G2elem.DeleteElement(self,choice=choice)
1391        if dlg.ShowModal() == wx.ID_OK:
1392            del ElList[dlg.GetDeleteElement()]
1393        dlg.Destroy()
1394        UpdatePDFGrid(self,data)
1395               
1396    def ComputePDF(Data):
1397        xydata = {}
1398        for key in ['Sample','Sample Bkg.','Container','Container Bkg.']:
1399            name = Data[key]['Name']
1400            if name:
1401                xydata[key] = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,self.root,name))
1402                PDFname = name
1403        powName = xydata['Sample'][2]
1404        powId = G2gd.GetPatternTreeItemId(self,self.root,powName)
1405        inst = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,powId,'Instrument Parameters'))
1406        inst = dict(zip(inst[3],inst[1]))
1407        auxPlot = G2pwd.CalcPDF(data,inst,xydata)
1408        PDFId = G2gd.GetPatternTreeItemId(self,self.root,'PDF '+powName[4:])
1409        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PDFId,'I(Q)'+powName[4:]),xydata['IofQ'])
1410        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PDFId,'S(Q)'+powName[4:]),xydata['SofQ'])
1411        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PDFId,'F(Q)'+powName[4:]),xydata['FofQ'])
1412        self.PatternTree.SetItemPyData(G2gd.GetPatternTreeItemId(self,PDFId,'G(R)'+powName[4:]),xydata['GofR'])
1413        return auxPlot
1414       
1415    def OnComputePDF(event):
1416        print 'Calculating PDF:'
1417        auxPlot = ComputePDF(data)
1418        Status.SetStatusText('PDF computed')
1419        for plot in auxPlot:
1420            G2plt.PlotXY(self,plot[:2],type=plot[2])
1421       
1422        G2plt.PlotISFG(self,newPlot=True,type='I(Q)')
1423        G2plt.PlotISFG(self,newPlot=True,type='S(Q)')
1424        G2plt.PlotISFG(self,newPlot=True,type='F(Q)')
1425        G2plt.PlotISFG(self,newPlot=True,type='G(R)')
1426       
1427    def OnComputeAllPDF(event):
1428        print 'Calculating PDFs:'
1429        if self.PatternTree.GetCount():
1430            id, cookie = self.PatternTree.GetFirstChild(self.root)
1431            while id:
1432                Name = self.PatternTree.GetItemText(id)
1433                if 'PDF' in Name:
1434                    Data = self.PatternTree.GetItemPyData(G2gd.GetPatternTreeItemId(self,id,'PDF Controls'))
1435                    auxPlot = ComputePDF(Data)                   
1436                id, cookie = self.PatternTree.GetNextChild(self.root, cookie)
1437            Status.SetStatusText('All PDFs computed')
1438            G2plt.PlotISFG(self,newPlot=True,type='G(R)')
1439       
1440    def OnShowTip(self,tip):
1441        print tip   
1442               
1443    if self.dataDisplay:
1444        self.dataFrame.Clear()
1445    self.dataFrame.SetMenuBar(self.dataFrame.PDFMenu)
1446    if not self.dataFrame.GetStatusBar():
1447        Status = self.dataFrame.CreateStatusBar()   
1448    self.dataDisplay = wx.Panel(self.dataFrame)
1449    self.dataFrame.Bind(wx.EVT_MENU, OnCopyPDFControls, id=G2gd.wxID_PDFCOPYCONTROLS)
1450    self.dataFrame.Bind(wx.EVT_MENU, OnSavePDFControls, id=G2gd.wxID_PDFSAVECONTROLS)
1451    self.dataFrame.Bind(wx.EVT_MENU, OnLoadPDFControls, id=G2gd.wxID_PDFLOADCONTROLS)
1452    self.dataFrame.Bind(wx.EVT_MENU, OnAddElement, id=G2gd.wxID_PDFADDELEMENT)
1453    self.dataFrame.Bind(wx.EVT_MENU, OnDeleteElement, id=G2gd.wxID_PDFDELELEMENT)
1454    self.dataFrame.Bind(wx.EVT_MENU, OnComputePDF, id=G2gd.wxID_PDFCOMPUTE)
1455    self.dataFrame.Bind(wx.EVT_MENU, OnComputeAllPDF, id=G2gd.wxID_PDFCOMPUTEALL)
1456    mainSizer = wx.BoxSizer(wx.VERTICAL)
1457    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' PDF data files: '),0,wx.ALIGN_CENTER_VERTICAL)
1458    mainSizer.Add((5,5),0)
1459    str = ' Sample file: PWDR %s   Wavelength, A: %.5f  Energy, keV: %.3f  Polariz.: %.2f '%(dataFile[3:],wave,keV,polariz)
1460    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=str),0,wx.ALIGN_CENTER_VERTICAL)
1461#    dataSizer = wx.BoxSizer(wx.HORIZONTAL)
1462#    dataSizer.Add(wx.StaticText(parent=self.dataDisplay,label='Azimuth'),0,wx.ALIGN_CENTER_VERTICAL)
1463#    azimVal = wx.TextCtrl(self.dataDisplay,value='%.2f'%(inst['Azimuth']))
1464#    azimVal.Bind(wx.EVT_TEXT_ENTER,OnAzimVal)       
1465#    azimVal.Bind(wx.EVT_KILL_FOCUS,OnAzimVal)
1466#    dataSizer.Add(azimVal,0)   
1467#    dataSizer.Add(wx.StaticText(parent=self.dataDisplay,label='Polarization'),0,wx.ALIGN_CENTER_VERTICAL)
1468#    polaVal = wx.TextCtrl(self.dataDisplay,value='%.2f'%(inst['Polariz.']))
1469#    polaVal.Bind(wx.EVT_TEXT_ENTER,OnPolaVal)       
1470#    polaVal.Bind(wx.EVT_KILL_FOCUS,OnPolaVal)
1471#    dataSizer.Add(polaVal,0)   
1472#    mainSizer.Add(dataSizer,0)
1473    mainSizer.Add((5,5),0)
1474    fileSizer = wx.FlexGridSizer(3,6,5,1)
1475    select = ['Sample Bkg.','Container']
1476    if data['Container']['Name']:
1477        select.append('Container Bkg.')
1478    for key in select:
1479        FillFileSizer(fileSizer,key)
1480    mainSizer.Add(fileSizer,0)
1481    mainSizer.Add((5,5),0)
1482    mainSizer.Add(wx.StaticText(self.dataDisplay,label=' Sample information: '),0,wx.ALIGN_CENTER_VERTICAL)
1483    mainSizer.Add((5,5),0)   
1484
1485    ElList = data['ElList']
1486    Abs = G2lat.CellAbsorption(ElList,data['Form Vol'])
1487    Trans = G2pwd.Transmission(data['Geometry'],Abs*data['Pack'],data['Diam'])
1488    elemSizer = wx.FlexGridSizer(3,3,5,1)
1489    for El in ElList:
1490        FillElemSizer(elemSizer,ElList[El])
1491    mainSizer.Add(elemSizer,0)
1492    mainSizer.Add((5,5),0)   
1493    midSizer = wx.BoxSizer(wx.HORIZONTAL)
1494    midSizer.Add(wx.StaticText(self.dataDisplay,label=' Formula volume: '),0,wx.ALIGN_CENTER_VERTICAL)
1495    formVol = wx.TextCtrl(self.dataDisplay,value='%.2f'%(data['Form Vol']))
1496    formVol.Bind(wx.EVT_TEXT_ENTER,OnFormVol)       
1497    formVol.Bind(wx.EVT_KILL_FOCUS,OnFormVol)
1498    midSizer.Add(formVol,0)
1499    midSizer.Add(wx.StaticText(self.dataDisplay,
1500        label=' Theoretical absorption: %.4f cm-1 Sample absorption: %.4f cm-1'%(Abs,Abs*data['Pack'])),
1501        0,wx.ALIGN_CENTER_VERTICAL)
1502    mainSizer.Add(midSizer,0)
1503    mainSizer.Add((5,5),0)   
1504
1505    geoBox = wx.BoxSizer(wx.HORIZONTAL)
1506    geoBox.Add(wx.StaticText(self.dataDisplay,label=' Sample geometry: '),0,wx.ALIGN_CENTER_VERTICAL)
1507    choice = ['Cylinder','Bragg-Brentano','Tilting flat plate in transmission','Fixed flat plate']
1508    geometry = wx.ComboBox(self.dataDisplay,value=data['Geometry'],choices=choice,
1509            style=wx.CB_READONLY|wx.CB_DROPDOWN)
1510    geometry.Bind(wx.EVT_COMBOBOX, OnGeometry)
1511    geoBox.Add(geometry,0)
1512    geoBox.Add(wx.StaticText(self.dataDisplay,label=' Sample diameter/thickness, mm: '),0,wx.ALIGN_CENTER_VERTICAL)
1513    diam = wx.TextCtrl(self.dataDisplay,value='%.3f'%(data['Diam']))
1514    diam.Bind(wx.EVT_TEXT_ENTER,OnDiameter)       
1515    diam.Bind(wx.EVT_KILL_FOCUS,OnDiameter)
1516#    diam.Bind(wx.EVT_SET_FOCUS,OnShowTip(self,'tip')) #this doesn't work - what would????
1517    geoBox.Add(diam,0)
1518    mainSizer.Add(geoBox,0)
1519    mainSizer.Add((5,5),0)   
1520    geoBox = wx.BoxSizer(wx.HORIZONTAL)
1521    geoBox.Add(wx.StaticText(self.dataDisplay,label=' Packing: '),0,wx.ALIGN_CENTER_VERTICAL)
1522    pack = wx.TextCtrl(self.dataDisplay,value='%.2f'%(data['Pack']))
1523    pack.Bind(wx.EVT_TEXT_ENTER,OnPacking)       
1524    pack.Bind(wx.EVT_KILL_FOCUS,OnPacking)
1525    geoBox.Add(pack,0)
1526    geoBox.Add(wx.StaticText(self.dataDisplay,label=' Sample transmission: %.3f %%'%(Trans)),0,wx.ALIGN_CENTER_VERTICAL)   
1527    mainSizer.Add(geoBox,0)
1528    mainSizer.Add((5,5),0)   
1529       
1530    mainSizer.Add(wx.StaticText(parent=self.dataDisplay,label=' S(Q)->F(Q)->G(R) controls: '),0,wx.ALIGN_CENTER_VERTICAL)
1531    mainSizer.Add((5,5),0)
1532    sqBox = wx.BoxSizer(wx.HORIZONTAL)
1533    sqBox.Add(wx.StaticText(self.dataDisplay,label=' Detector type: '),0,wx.ALIGN_CENTER_VERTICAL)
1534    choice = ['Image plate','Point detector']
1535    detType = wx.ComboBox(self.dataDisplay,value=data['DetType'],choices=choice,
1536            style=wx.CB_READONLY|wx.CB_DROPDOWN)
1537    detType.Bind(wx.EVT_COMBOBOX, OnDetType)
1538    sqBox.Add(detType,0)
1539    if data['DetType'] == 'Image plate':
1540        sqBox.Add(wx.StaticText(self.dataDisplay,label=' IP transmission coeff.: '),0,wx.ALIGN_CENTER_VERTICAL)
1541        obliqCoeff = wx.TextCtrl(self.dataDisplay,value='%.3f'%(data['ObliqCoeff']))
1542        obliqCoeff.Bind(wx.EVT_TEXT_ENTER,OnObliqCoeff)       
1543        obliqCoeff.Bind(wx.EVT_KILL_FOCUS,OnObliqCoeff)
1544        sqBox.Add(obliqCoeff,0)
1545    sqBox.Add(wx.StaticText(self.dataDisplay,label=' Ruland width: '),0,wx.ALIGN_CENTER_VERTICAL)
1546    rulandWdt = wx.TextCtrl(self.dataDisplay,value='%.3f'%(data['Ruland']))
1547    rulandWdt.Bind(wx.EVT_TEXT_ENTER,OnRulandWdt)       
1548    rulandWdt.Bind(wx.EVT_KILL_FOCUS,OnRulandWdt)
1549    sqBox.Add(rulandWdt,0)   
1550    mainSizer.Add(sqBox,0)
1551   
1552    sqBox = wx.BoxSizer(wx.HORIZONTAL)
1553    lorch = wx.CheckBox(parent=self.dataDisplay,label='Lorch damping?')
1554    lorch.SetValue(data['Lorch'])
1555    lorch.Bind(wx.EVT_CHECKBOX, OnLorch)
1556    sqBox.Add(lorch,0,wx.ALIGN_CENTER_VERTICAL)
1557    sqBox.Add(wx.StaticText(self.dataDisplay,label=' Scaling q-range: '),0,wx.ALIGN_CENTER_VERTICAL)
1558    SQmin = wx.TextCtrl(self.dataDisplay,value='%.1f'%(data['QScaleLim'][0]))
1559    SQmin.Bind(wx.EVT_TEXT_ENTER,OnSQmin)       
1560    SQmin.Bind(wx.EVT_KILL_FOCUS,OnSQmin)   
1561    sqBox.Add(SQmin,0)
1562    sqBox.Add(wx.StaticText(self.dataDisplay,label=' to '),0,wx.ALIGN_CENTER_VERTICAL)
1563    SQmax = wx.TextCtrl(self.dataDisplay,value='%.1f'%(data['QScaleLim'][1]))
1564    SQmax.Bind(wx.EVT_TEXT_ENTER,OnSQmax)       
1565    SQmax.Bind(wx.EVT_KILL_FOCUS,OnSQmax)
1566    sqBox.Add(SQmax,0)
1567    resetQ = wx.CheckBox(parent=self.dataDisplay,label='Reset?')
1568    sqBox.Add(resetQ,0)
1569    resetQ.Bind(wx.EVT_CHECKBOX, OnResetQ)
1570   
1571    mainSizer.Add(sqBox,0)
1572
1573    mainSizer.Layout()   
1574    self.dataDisplay.SetSizer(mainSizer)
1575    Size = mainSizer.Fit(self.dataFrame)
1576    self.dataDisplay.SetSize(Size)
1577    self.dataFrame.setSizePosLeft(Size)
1578   
Note: See TracBrowser for help on using the repository browser.