Changeset 496


Ignore:
Timestamp:
Feb 24, 2012 3:12:00 PM (10 years ago)
Author:
vondreele
Message:

making 1st multiprocess version of GSAS-II

Location:
MPbranch
Files:
6 copied

Legend:

Unmodified
Added
Removed
  • MPbranch/GSASII.py

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

    r493 r496  
    743743        data['min dM/M'] = 0.0001
    744744        data['shift factor'] = 1.
    745         data['max cyc'] = 3       
     745        data['max cyc'] = 3
     746        data['max Hprocess'] = 1
     747        data['max Rprocess'] = 1       
    746748    if 'shift factor' not in data:
    747749        data['shift factor'] = 1.
    748750    if 'max cyc' not in data:
    749         data['max cyc'] = 3       
     751        data['max cyc'] = 3 
     752    if 'max Hprocess' not in data:     
     753        data['max Hprocess'] = 1
     754        data['max Rprocess'] = 1       
    750755    #end patch
    751756    def SeqSizer():
     
    805810            data['max cyc'] = int(maxCyc.GetValue())
    806811            maxCyc.SetValue(str(data['max cyc']))
     812
     813        def OnMaxHproc(event):
     814            if int(maxHproc.GetValue()) > 0:
     815                data['max Hprocess'] = int(maxHproc.GetValue())
     816
     817        def OnMaxRproc(event):
     818            if int(maxRproc.GetValue()) > 0:
     819                data['max Rprocess'] = int(maxRproc.GetValue())
    807820                       
    808821        def OnFactor(event):
     
    836849            maxCyc.Bind(wx.EVT_COMBOBOX, OnMaxCycles)
    837850            LSSizer.Add(maxCyc,0,wx.ALIGN_CENTER_VERTICAL)
     851            LSSizer.Add(wx.StaticText(G2frame.dataDisplay,label=' Max histogram proc: '),0,wx.ALIGN_CENTER_VERTICAL)
     852            maxHproc = wx.TextCtrl(G2frame.dataDisplay,-1,value='%d'%(data['max Hprocess']),style=wx.TE_PROCESS_ENTER)
     853            maxHproc.Bind(wx.EVT_TEXT_ENTER,OnMaxHproc)
     854            maxHproc.Bind(wx.EVT_KILL_FOCUS,OnMaxHproc)
     855            LSSizer.Add(maxHproc,0,wx.ALIGN_CENTER_VERTICAL)
     856            LSSizer.Add(wx.StaticText(G2frame.dataDisplay,label=' Max reflection proc: '),0,wx.ALIGN_CENTER_VERTICAL)
     857            maxRproc = wx.TextCtrl(G2frame.dataDisplay,-1,value='%d'%(data['max Rprocess']),style=wx.TE_PROCESS_ENTER)
     858            maxRproc.Bind(wx.EVT_TEXT_ENTER,OnMaxRproc)
     859            maxRproc.Bind(wx.EVT_KILL_FOCUS,OnMaxRproc)
     860            LSSizer.Add(maxRproc,0,wx.ALIGN_CENTER_VERTICAL)
    838861        else:
    839862            LSSizer.Add(wx.StaticText(G2frame.dataDisplay,label=' Initial shift factor: '),0,wx.ALIGN_CENTER_VERTICAL)
     
    860883    mainSizer.Add((5,5),0)
    861884       
    862     mainSizer.Add(wx.StaticText(G2frame.dataDisplay,label=' Density Map Controls:'),0,wx.ALIGN_CENTER_VERTICAL)
    863 
    864885    mainSizer.Layout()   
    865886    G2frame.dataDisplay.SetSizer(mainSizer)
  • MPbranch/GSASIIstruct.py

    r495 r496  
    26752675    if MaxProcess > 1:
    26762676        mpPool = mp.Pool(processes=MaxProcess)
    2677         results = mpPool.map(ComputePowderHessian,argList)
    2678         for Vec,Hess in results:
     2677        #results = mpPool.map(ComputePowderHessian,argList)
     2678        #for Vec,Hess in results:
     2679        for Vec,Hess in mpPool.imap_unordered(ComputePowderHessian,argList):
    26792680            VecSum += Vec
    26802681            HessSum += Hess
     
    27652766    if MaxProcess > 1:
    27662767        mpPool = mp.Pool(processes=MaxProcess)
    2767         results = mpPool.map(ComputePowderProfile,argList)
    2768         for arg,res in zip(argList,results):
     2768        #results = mpPool.map(ComputePowderProfile,argList)
     2769        #for arg,res in zip(argList,results):
     2770        #results = mpPool.map(ComputePowderProfile,argList)
     2771        #for i,res in enumerate(results):
     2772        for i,res in enumerate(
     2773            mpPool.imap_unordered(ComputePowderProfile,argList)
     2774            ):
     2775            print 'process',i
    27692776            xB,xF,ycSect,ybSect,RL = res
    2770             Histogram = arg[0]
     2777            Histogram = argList[i][0]
    27712778            Histogram['Reflection Lists'] = RL
    27722779            x,y,w,yc,yb,yd = Histogram['Data']
Note: See TracChangeset for help on using the changeset viewer.