Exemplo n.º 1
0
class Viewer1DXRD(wx.Panel):
    '''
    Frame for housing all 1D XRD viewer widgets
    '''
    label='Viewer'
    def __init__(self,parent,owner=None,_larch=None):
        
        wx.Panel.__init__(self, parent)

        self.parent = parent
        self.owner = owner

        ## Default information
        self.data_name    = []
        self.xy_data      = []
        self.xy_plot      = []
        self.plotted_data = []
        self.xy_scale     = []
        self.wavelength   = None
        self.xlabel       = 'q (A^-1)'
        self.xunits        = ['q','d']

        self.cif_name     = []
        self.cif_data     = []
        self.cif_plot     = []
        self.plotted_cif  = []
        
        self.x_for_zoom = None


        self.Panel1DViewer()

##############################################
#### PANEL DEFINITIONS
    def Panel1DViewer(self):
        '''
        Frame for housing all 1D XRD viewer widgets
        '''
        leftside  = self.LeftSidePanel(self)
        rightside = self.RightSidePanel(self)        

        panel1D = wx.BoxSizer(wx.HORIZONTAL)
        panel1D.Add(leftside,flag=wx.ALL,border=10)
        panel1D.Add(rightside,proportion=1,flag=wx.EXPAND|wx.ALL,border=10)

        self.SetSizer(panel1D)
    
    def Toolbox(self,panel):
        '''
        Frame for visual toolbox
        '''
        
        tlbx = wx.StaticBox(self,label='PLOT TOOLBOX')
        vbox = wx.StaticBoxSizer(tlbx,wx.VERTICAL)

        ###########################
        ## X-Scale
        hbox_xaxis = wx.BoxSizer(wx.HORIZONTAL)
        ttl_xaxis = wx.StaticText(self, label='X-SCALE')
        self.ch_xaxis = wx.Choice(self,choices=self.xunits)

        self.ch_xaxis.Bind(wx.EVT_CHOICE, self.checkXaxis)
    
        hbox_xaxis.Add(ttl_xaxis, flag=wx.RIGHT, border=8)
        hbox_xaxis.Add(self.ch_xaxis, flag=wx.EXPAND, border=8)
        vbox.Add(hbox_xaxis, flag=wx.ALL, border=10)

        ###########################
        ## Y-Scale
        hbox_yaxis = wx.BoxSizer(wx.HORIZONTAL)
        ttl_yaxis = wx.StaticText(self, label='Y-SCALE')
        yscales = ['linear','log']
        self.ch_yaxis = wx.Choice(self,choices=yscales)

        self.ch_yaxis.Bind(wx.EVT_CHOICE,   None)
    
        hbox_yaxis.Add(ttl_yaxis, flag=wx.RIGHT, border=8)
        hbox_yaxis.Add(self.ch_yaxis, flag=wx.EXPAND, border=8)
        vbox.Add(hbox_yaxis, flag=wx.ALL, border=10)
        
        return vbox

    def DataBox(self,panel):
        '''
        Frame for data toolbox
        '''
        
        tlbx = wx.StaticBox(self,label='DATA TOOLBOX')
        vbox = wx.StaticBoxSizer(tlbx,wx.VERTICAL)


        ###########################
        ## DATA CHOICE

        self.ch_data = wx.Choice(self,choices=self.data_name)
        self.ch_data.Bind(wx.EVT_CHOICE,   self.onSELECT)
        vbox.Add(self.ch_data, flag=wx.EXPAND|wx.ALL, border=8)
    
        #self.ttl_data = wx.StaticText(self, label='')
        #vbox.Add(self.ttl_data, flag=wx.EXPAND|wx.ALL, border=8)

        ###########################

#         self.ck_bkgd = wx.CheckBox(self,label='BACKGROUND')
#         self.ck_smth = wx.CheckBox(self,label='SMOOTHING')
#         
#         self.ck_bkgd.Bind(wx.EVT_CHECKBOX,   None)
#         self.ck_smth.Bind(wx.EVT_CHECKBOX,   None)
# 
#         vbox.Add(self.ck_bkgd, flag=wx.ALL, border=8)
#         vbox.Add(self.ck_smth, flag=wx.ALL, border=8)
    
        ###########################
        ## Scale
        hbox_scl = wx.BoxSizer(wx.HORIZONTAL)
        ttl_scl = wx.StaticText(self, label='SCALE Y TO:')
        self.entr_scale = wx.TextCtrl(self,wx.TE_PROCESS_ENTER)
        btn_scale = wx.Button(self,label='set')

        btn_scale.Bind(wx.EVT_BUTTON, self.normalize1Ddata)
        
        hbox_scl.Add(ttl_scl, flag=wx.RIGHT, border=8)
        hbox_scl.Add(self.entr_scale, flag=wx.RIGHT, border=8)
        hbox_scl.Add(btn_scale, flag=wx.RIGHT, border=8)

        vbox.Add(hbox_scl, flag=wx.BOTTOM|wx.TOP, border=8)

        ###########################
        ## Hide/show and reset
        hbox_btns = wx.BoxSizer(wx.HORIZONTAL)
        
        btn_hide  = wx.Button(self,label='hide')
        btn_reset = wx.Button(self,label='reset')
        btn_rmv   = wx.Button(self,label='remove')
        
        btn_hide.Bind(wx.EVT_BUTTON,  self.hide1Ddata)
        btn_reset.Bind(wx.EVT_BUTTON, self.reset1Dscale)
        btn_rmv.Bind(wx.EVT_BUTTON,   self.remove1Ddata)

        btn_hide.Disable()
        btn_rmv.Disable()
        
        hbox_btns.Add(btn_reset, flag=wx.ALL, border=10)
        hbox_btns.Add(btn_hide,  flag=wx.ALL, border=10)
        hbox_btns.Add(btn_rmv,   flag=wx.ALL, border=10)
        vbox.Add(hbox_btns, flag=wx.ALL, border=10)
        return vbox   
        

        

    def AddPanel(self,panel):
    
        hbox = wx.BoxSizer(wx.HORIZONTAL)
        
        btn_data = wx.Button(panel,label='ADD NEW DATA SET')
        btn_data.Bind(wx.EVT_BUTTON, self.loadXYFILE)

        btn_cif = wx.Button(panel,label='ADD NEW CIF')
        btn_cif.Bind(wx.EVT_BUTTON, self.loadCIF)
    
        hbox.Add(btn_data, flag=wx.ALL, border=8)
        hbox.Add(btn_cif, flag=wx.ALL, border=8)
        return hbox

    def LeftSidePanel(self,panel):
        
        vbox = wx.BoxSizer(wx.VERTICAL)
        
        plttools = self.Toolbox(self)
        addbtns = self.AddPanel(self)
        dattools = self.DataBox(self)
        
        vbox.Add(plttools,flag=wx.ALL,border=10)
        vbox.Add(addbtns,flag=wx.ALL,border=10)
        vbox.Add(dattools,flag=wx.ALL,border=10)
        return vbox

    def RightSidePanel(self,panel):
        vbox = wx.BoxSizer(wx.VERTICAL)
        self.plot1DXRD(panel)
        btnbox = self.QuickButtons(panel)
        vbox.Add(self.plot1D,proportion=1,flag=wx.ALL|wx.EXPAND,border = 10)
        vbox.Add(btnbox,flag=wx.ALL|wx.ALIGN_RIGHT,border = 10)
        return vbox

    def QuickButtons(self,panel):
        buttonbox = wx.BoxSizer(wx.HORIZONTAL)
        btn_img = wx.Button(panel,label='SAVE FIGURE')
        btn_calib = wx.Button(panel,label='PLOT SETTINGS')
        btn_integ = wx.Button(panel,label='RESET PLOT')
        
        btn_img.Bind(wx.EVT_BUTTON,   self.onSAVEfig)
        btn_calib.Bind(wx.EVT_BUTTON, self.onPLOTset)
        btn_integ.Bind(wx.EVT_BUTTON, self.onRESETplot)
        
        buttonbox.Add(btn_img, flag=wx.ALL, border=8)
        buttonbox.Add(btn_calib, flag=wx.ALL, border=8)
        buttonbox.Add(btn_integ, flag=wx.ALL, border=8)
        return buttonbox


##############################################
#### PLOTPANEL FUNCTIONS
    def plot1DXRD(self,panel):
    
        self.plot1D = PlotPanel(panel,size=(1000, 500))
        self.plot1D.messenger = self.owner.write_message
        

        ## Set defaults for plotting  
        self.plot1D.set_ylabel('Intensity (a.u.)')
        self.plot1D.cursor_mode = 'zoom'
  
        ## trying to get this functionality into our gui
        ## mkak 2016.11.10      
#         interactive_legend().show()

    def onSAVEfig(self,event):
        self.plot1D.save_figure()
        
    def onPLOTset(self,event):
        self.plot1D.configure()
        
    def onRESETplot(self,event):
        self.plot1D.reset_config()



##############################################
#### XRD PLOTTING FUNCTIONS
       
    def add1Ddata(self,x,y,name=None,cif=False,wavelength=None):
        
        plt_no = len(self.data_name)
        
        if cif:
            if name is None:
                name = 'cif %i' % plt_no
            else:
               name = 'cif: %s' % name
        else:
            if name is None:
                name = 'dataset %i' % plt_no
            else:
                name = 'data: %s' % name
                
        if wavelength is not None:
            self.addLAMBDA(wavelength)

        ## Add to data array lists
        self.data_name.append(name)
        self.xy_scale.append(max(y))
        self.xy_data.extend([x,y])

        ## redefine x,y based on scales
        self.xy_plot.extend([x,y])
       
        ## Add to plot       
        self.plotted_data.append(self.plot1D.oplot(x,y,label=name,show_legend=True))#,xlabel=self.xlabel))

        ## Use correct x-axis units
        self.checkXaxis(None)

        self.ch_data.Set(self.data_name)
        self.ch_data.SetStringSelection(name)
        
        ## Update toolbox panel, scale all cif to 1000
        if cif is True:
            self.entr_scale.SetValue('1000')
            self.normalize1Ddata(None)
        else:
            self.entr_scale.SetValue(str(self.xy_scale[plt_no]))

    def addLAMBDA(self,wavelength,units='m'):
        
        ## convert to units A
        if units == 'm':
            self.wavelength = wavelength*1e10 
        elif units == 'cm':
            self.wavelength = wavelength*1e8
        elif units == 'mm':
            self.wavelength = wavelength*1e7        
        elif units == 'um':
            self.wavelength = wavelength*1e4
        elif units == 'nm':
            self.wavelength = wavelength*1e1
        else: ## units 'A'        
            self.wavelength = wavelength

        self.xunits.append(u'2\u03B8')
        self.ch_xaxis.Set(self.xunits)

    def normalize1Ddata(self,event):
    
        plt_no = self.ch_data.GetSelection()
        self.xy_scale[plt_no] = float(self.entr_scale.GetValue())
        if self.xy_scale[plt_no] <= 0:
            self.xy_scale[plt_no] = max(self.xy_data[(plt_no*2+1)])
            self.entr_scale.SetValue(str(self.xy_scale[plt_no]))

        y = self.xy_data[(plt_no*2+1)]
        self.xy_plot[(plt_no*2+1)] = y/np.max(y) * self.xy_scale[plt_no]

        self.updatePLOT()
        

    def remove1Ddata(self,event):
        
        ## Needs pop up warning: "Do you really want to delete this data set from plotter?
        ## Current settings will not be saved."
        ## mkak 2016.11.10
        
        plt_no = self.ch_data.GetSelection()        
        print('EVENTUALLY, button will remove plot: %s' % self.data_name[plt_no])

        ## removing name from list works... do not activate till rest is working
        ## mkak 2016.11.10
#         self.data_name.remove(self.data_name[plt_no])
#         self.ch_data.Set(self.data_name)

    def hide1Ddata(self,event):

        plt_no = self.ch_data.GetSelection()        
        print('EVENTUALLY, button will hide plot: %s' % self.data_name[plt_no])

    def onSELECT(self,event):
    
        data_str = self.ch_data.GetString(self.ch_data.GetSelection())
#         self.ttl_data.SetLabel('SELECTED: %s' % data_str)
        
        plt_no = self.ch_data.GetSelection()
        self.entr_scale.SetValue(str(self.xy_scale[plt_no]))

    def checkXaxis(self, event):
        
        if self.ch_xaxis.GetSelection() == 2:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = calc_q_to_2th(self.xy_data[plt_no*2],self.wavelength)
        elif self.ch_xaxis.GetSelection() == 1:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = calc_q_to_d(self.xy_data[plt_no*2])
        else:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = self.xy_data[plt_no*2]

        if self.ch_xaxis.GetSelection() == 2:
            self.xlabel = r'$2\Theta$'+r' $(^\circ)$'
        elif self.ch_xaxis.GetSelection() == 1:
            self.xlabel = 'd ($\AA$)'
        else:
            self.xlabel = 'q (1/$\AA$)'
         
        self.plot1D.set_xlabel(self.xlabel)
        self.updatePLOT()

    def updatePLOT(self):

        xmax,xmin,ymax,ymin = None,0,None,0
    
        if len(self.plotted_data) > 0:
            for plt_no in range(len(self.plotted_data)):

                i = plt_no*2
                j = i+1
 
                x = self.xy_plot[i]
                y = self.xy_plot[j]
                
                if xmax is None or xmax < max(x):
                    xmax = max(x)
                if xmin > min(x):
                    xmin = min(x)
                if ymax is None or ymax < max(y):
                    ymax = max(y)
                if ymin > min(y):
                    ymin = min(y)
                
                self.plot1D.update_line(plt_no,x,y)
            
            self.unzoom_all()
            self.plot1D.canvas.draw()
            
            if self.ch_xaxis.GetSelection() == 1:
                xmax = 5
            self.plot1D.set_xylims([xmin, xmax, ymin, ymax])

    def reset1Dscale(self,event):

        plt_no = self.ch_data.GetSelection()        
       
        self.xy_plot[(plt_no*2+1)] = self.xy_data[(plt_no*2+1)]
        self.plot1D.update_line(plt_no,self.xy_plot[(plt_no*2)],
                                       self.xy_plot[(plt_no*2+1)])
        self.plot1D.canvas.draw()
        self.unzoom_all()
        
        self.updatePLOT()
        self.xy_scale[plt_no] = max(self.xy_data[(plt_no*2+1)])
        self.entr_scale.SetValue(str(self.xy_scale[plt_no]))

####### BEGIN #######            
## THIS IS DIRECTLY FROM XRDDISPLAY.PY
## mkak 2016.11.11
    def unzoom_all(self, event=None):

        xmid, xrange, xmin, xmax = self._get1Dlims()

        self._set_xview(xmin, xmax)
        self.xview_range = None

    def _get1Dlims(self):
        xmin, xmax = self.plot1D.axes.get_xlim()
        xrange = xmax-xmin
        xmid   = (xmax+xmin)/2.0
        if self.x_for_zoom is not None:
            xmid = self.x_for_zoom
        return (xmid, xrange, xmin, xmax)

    def _set_xview(self, x1, x2, keep_zoom=False, pan=False):

        xmin,xmax = self.abs_limits()
        xrange = x2-x1
        x1 = max(xmin,x1)
        x2 = min(xmax,x2)

        if pan:
            if x2 == xmax:
                x1 = x2-xrange
            elif x1 == xmin:
                x2 = x1+xrange
        if not keep_zoom:
            self.x_for_zoom = (x1+x2)/2.0
        self.plot1D.axes.set_xlim((x1, x2))
        self.xview_range = [x1, x2]
        self.plot1D.canvas.draw()

    def abs_limits(self):
        if len(self.data_name) > 0:
            xmin, xmax = self.xy_plot[0].min(), self.xy_plot[0].max()
   
        return xmin,xmax
#######  END  #######
       

##############################################
#### XRD FILE OPENING/SAVING 
    def loadXYFILE(self,event):
    
        wildcards = 'XRD data file (*.xy)|*.xy|All files (*.*)|*.*'
        dlg = wx.FileDialog(self, message='Choose 1D XRD data file',
                           defaultDir=os.getcwd(),
                           wildcard=wildcards, style=wx.FD_OPEN)

        path, read = None, False
        if dlg.ShowModal() == wx.ID_OK:
            read = True
            path = dlg.GetPath().replace('\\', '/')
        dlg.Destroy()
        
        if read:
            try:
                x,y = xy_file_reader(path)

                self.add1Ddata(x,y,name=os.path.split(path)[-1])
            except:
               print('incorrect xy file format: %s' % os.path.split(path)[-1])



    def saveXYFILE(self,event):
        wildcards = 'XRD data file (*.xy)|*.xy|All files (*.*)|*.*'
        dlg = wx.FileDialog(self, 'Save data as...',
                           defaultDir=os.getcwd(),
                           wildcard=wildcards,
                           style=wx.SAVE|wx.OVERWRITE_PROMPT)

        path, save = None, False
        if dlg.ShowModal() == wx.ID_OK:
            save = True
            path = dlg.GetPath().replace('\\', '/')
        dlg.Destroy()
        
        if save:
            ## mkak 2016.11.16
            print('need to write something to save data - like pyFAI does?')

    def loadCIF(self,event):
    
        wildcards = 'XRD cifile (*.cif)|*.cif|All files (*.*)|*.*'
        dlg = wx.FileDialog(self, message='Choose CIF',
                           defaultDir=os.getcwd(),
                           wildcard=wildcards, style=wx.FD_OPEN)

        path, read = None, False
        if dlg.ShowModal() == wx.ID_OK:
            read = True
            path = dlg.GetPath().replace('\\', '/')
        dlg.Destroy()
        
        if read:
            cifile = os.path.split(path)[-1]

            try:
                cif = xu.materials.Crystal.fromCIF(path)
            except:
                print('incorrect file format: %s' % os.path.split(path)[-1])
                return

            ## generate hkl list
            hkllist = []
            maxhkl = 8
            for i in range(-maxhkl,maxhkl+1):
                for j in range(-maxhkl,maxhkl+1):
                    for k in range(-maxhkl,maxhkl+1):
                        if i+j+k > 0: # as long as h,k,l all positive, eliminates 0,0,0
                            hkllist.append([i,j,k])
            
            hc = constants.value(u'Planck constant in eV s') * \
                       constants.value(u'speed of light in vacuum') * 1e-3 ## units: keV-m

            if self.wavelength is not None:
                qlist = cif.Q(hkllist)
                Flist = cif.StructureFactorForQ(qlist,(hc/(self.wavelength*(1e-10))*1e3))
            
                Fall = []
                qall = []
                hklall = []
                for i,hkl in enumerate(hkllist):
                    if np.abs(Flist[i]) > 0.01:
                        Fadd = np.abs(Flist[i])
                        qadd = np.linalg.norm(qlist[i])
                        if qadd not in qall and qadd < 6:
                            Fall.extend((0,Fadd,0))
                            qall.extend((qadd,qadd,qadd))
                if np.shape(Fall)[0] > 0:
                    Fall = np.array(Fall)
                    qall = np.array(qall)
                    self.add1Ddata(qall,Fall,name=os.path.split(path)[-1],cif=True)
                else:
                    print('Could not calculate real structure factors.')
            else:
                print('Wavelength/energy must be specified for structure factor calculations.')

    def openPONI(self,event):
             
        wildcards = 'pyFAI calibration file (*.poni)|*.poni|All files (*.*)|*.*'
        dlg = wx.FileDialog(self, message='Choose pyFAI calibration file',
                           defaultDir=os.getcwd(),
                           wildcard=wildcards, style=wx.FD_OPEN)

        path, read = None, False
        if dlg.ShowModal() == wx.ID_OK:
            read = True
            path = dlg.GetPath().replace('\\', '/')
        dlg.Destroy()
        
        if read:

            try:
                print('Loading calibration file: %s' % path)
                ai = pyFAI.load(path)
            except:
                print('Not recognized as a pyFAI calibration file.')
                return

            self.addLAMBDA(ai._wavelength,units='m')

    def setLAMBDA(self,event):

        dlg = SetLambdaDialog()

        path, okay = None, False
        if dlg.ShowModal() == wx.ID_OK:
            okay = True
            wavelength = dlg.wavelength
        dlg.Destroy()
        
        if okay:
            self.addLAMBDA(wavelength,units='A')
Exemplo n.º 2
0
class Fitting1DXRD(wx.Panel):
    '''
    Frame for housing all 1D XRD fitting widgets
    '''
    label='Fitting'
    def __init__(self,parent,owner=None,_larch=None):
        
        wx.Panel.__init__(self, parent)

        self.parent = parent
        self.owner = owner

        ## Default information
        self.xlabel       = 'q (A^-1)'
        self.xunits        = ['q','d']

        self.Panel1DFitting()
    

     
##############################################
#### PANEL DEFINITIONS
    def Panel1DFitting(self):
        '''
        Frame for housing all 1D XRD viewer widgets
        '''
        leftside  = self.LeftSidePanel(self)
        rightside = self.RightSidePanel(self)        

        panel1D = wx.BoxSizer(wx.HORIZONTAL)
        panel1D.Add(leftside,flag=wx.ALL,border=10)
        panel1D.Add(rightside,proportion=1,flag=wx.EXPAND|wx.ALL,border=10)

        self.SetSizer(panel1D)
    
    def Toolbox(self,panel):
        '''
        Frame for visual toolbox
        '''
        
        tlbx = wx.StaticBox(self,label='PLOT TOOLBOX')
        vbox = wx.StaticBoxSizer(tlbx,wx.VERTICAL)

        ###########################
        ## X-Scale
        hbox_xaxis = wx.BoxSizer(wx.HORIZONTAL)
        ttl_xaxis = wx.StaticText(self, label='X-SCALE')
        self.ch_xaxis = wx.Choice(self,choices=self.xunits)

        self.ch_xaxis.Bind(wx.EVT_CHOICE, self.checkXaxis)
    
        hbox_xaxis.Add(ttl_xaxis, flag=wx.RIGHT, border=8)
        hbox_xaxis.Add(self.ch_xaxis, flag=wx.EXPAND, border=8)
        vbox.Add(hbox_xaxis, flag=wx.ALL, border=10)

        ###########################
        ## Y-Scale
        hbox_yaxis = wx.BoxSizer(wx.HORIZONTAL)
        ttl_yaxis = wx.StaticText(self, label='Y-SCALE')
        yscales = ['linear','log']
        self.ch_yaxis = wx.Choice(self,choices=yscales)

        self.ch_yaxis.Bind(wx.EVT_CHOICE,   None)
    
        hbox_yaxis.Add(ttl_yaxis, flag=wx.RIGHT, border=8)
        hbox_yaxis.Add(self.ch_yaxis, flag=wx.EXPAND, border=8)
        vbox.Add(hbox_yaxis, flag=wx.ALL, border=10)
        
        return vbox

    def LeftSidePanel(self,panel):
        
        vbox = wx.BoxSizer(wx.VERTICAL)
        
        plttools = self.Toolbox(self)
        
        vbox.Add(plttools,flag=wx.ALL,border=10)
        return vbox

    def RightSidePanel(self,panel):
        vbox = wx.BoxSizer(wx.VERTICAL)
        self.plot1DXRD(panel)
        btnbox = self.QuickButtons(panel)
        vbox.Add(self.plot1D,proportion=1,flag=wx.ALL|wx.EXPAND,border = 10)
        vbox.Add(btnbox,flag=wx.ALL|wx.ALIGN_RIGHT,border = 10)
        return vbox

    def QuickButtons(self,panel):
        buttonbox = wx.BoxSizer(wx.HORIZONTAL)
        btn_img = wx.Button(panel,label='SAVE FIGURE')
        btn_calib = wx.Button(panel,label='PLOT SETTINGS')
        btn_integ = wx.Button(panel,label='RESET PLOT')
        
        btn_img.Bind(wx.EVT_BUTTON,   self.onSAVEfig)
        btn_calib.Bind(wx.EVT_BUTTON, self.onPLOTset)
        btn_integ.Bind(wx.EVT_BUTTON, self.onRESETplot)
        
        buttonbox.Add(btn_img, flag=wx.ALL, border=8)
        buttonbox.Add(btn_calib, flag=wx.ALL, border=8)
        buttonbox.Add(btn_integ, flag=wx.ALL, border=8)
        return buttonbox


##############################################
#### PLOTPANEL FUNCTIONS
    def plot1DXRD(self,panel):
    
        self.plot1D = PlotPanel(panel,size=(1000, 500))
        self.plot1D.messenger = self.owner.write_message
        

        ## Set defaults for plotting  
        self.plot1D.set_ylabel('Intensity (a.u.)')
        self.plot1D.cursor_mode = 'zoom'
  
        ## trying to get this functionality into our gui
        ## mkak 2016.11.10      
#         interactive_legend().show()

    def onSAVEfig(self,event):
        self.plot1D.save_figure()
        
    def onPLOTset(self,event):
        self.plot1D.configure()
        
    def onRESETplot(self,event):
        self.plot1D.reset_config()

    def checkXaxis(self, event):
        
        if self.ch_xaxis.GetSelection() == 2:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = calc_q_to_2th(self.xy_data[plt_no*2],self.wavelength)
        elif self.ch_xaxis.GetSelection() == 1:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = calc_q_to_d(self.xy_data[plt_no*2])
        else:
            for plt_no in range(len(self.plotted_data)):
                self.xy_plot[plt_no*2] = self.xy_data[plt_no*2]

        if self.ch_xaxis.GetSelection() == 2:
            self.xlabel = r'$2\Theta$'+r' $(^\circ)$'
        elif self.ch_xaxis.GetSelection() == 1:
            self.xlabel = 'd ($\AA$)'
        else:
            self.xlabel = 'q (1/$\AA$)'
         
        self.plot1D.set_xlabel(self.xlabel)
        self.updatePLOT()

    def updatePLOT(self):

        xmax,xmin,ymax,ymin = None,0,None,0
    
        if len(self.plotted_data) > 0:
            for plt_no in range(len(self.plotted_data)):

                i = plt_no*2
                j = i+1
 
                x = self.xy_plot[i]
                y = self.xy_plot[j]
                
                if xmax is None or xmax < max(x):
                    xmax = max(x)
                if xmin > min(x):
                    xmin = min(x)
                if ymax is None or ymax < max(y):
                    ymax = max(y)
                if ymin > min(y):
                    ymin = min(y)
                
                self.plot1D.update_line(plt_no,x,y)
            
            self.unzoom_all()
            self.plot1D.canvas.draw()
            
            if self.ch_xaxis.GetSelection() == 1:
                xmax = 5
            self.plot1D.set_xylims([xmin, xmax, ymin, ymax])

    def reset1Dscale(self,event):

        plt_no = self.ch_data.GetSelection()        
       
        self.xy_plot[(plt_no*2+1)] = self.xy_data[(plt_no*2+1)]
        self.plot1D.update_line(plt_no,self.xy_plot[(plt_no*2)],
                                       self.xy_plot[(plt_no*2+1)])
        self.plot1D.canvas.draw()
        self.unzoom_all()
        
        self.updatePLOT()
        self.xy_scale[plt_no] = max(self.xy_data[(plt_no*2+1)])
        self.entr_scale.SetValue(str(self.xy_scale[plt_no]))

####### BEGIN #######            
## THIS IS DIRECTLY FROM XRDDISPLAY.PY
## mkak 2016.11.11
    def unzoom_all(self, event=None):

        xmid, xrange, xmin, xmax = self._get1Dlims()

        self._set_xview(xmin, xmax)
        self.xview_range = None

    def _get1Dlims(self):
        xmin, xmax = self.plot1D.axes.get_xlim()
        xrange = xmax-xmin
        xmid   = (xmax+xmin)/2.0
        if self.x_for_zoom is not None:
            xmid = self.x_for_zoom
        return (xmid, xrange, xmin, xmax)

    def _set_xview(self, x1, x2, keep_zoom=False, pan=False):

        xmin,xmax = self.abs_limits()
        xrange = x2-x1
        x1 = max(xmin,x1)
        x2 = min(xmax,x2)

        if pan:
            if x2 == xmax:
                x1 = x2-xrange
            elif x1 == xmin:
                x2 = x1+xrange
        if not keep_zoom:
            self.x_for_zoom = (x1+x2)/2.0
        self.plot1D.axes.set_xlim((x1, x2))
        self.xview_range = [x1, x2]
        self.plot1D.canvas.draw()

    def abs_limits(self):
        if len(self.data_name) > 0:
            xmin, xmax = self.xy_plot[0].min(), self.xy_plot[0].max()
   
        return xmin,xmax