Index: sansview/perspectives/fitting/fitpage.py
===================================================================
--- sansview/perspectives/fitting/fitpage.py	(revision 00353b47ce0686a8ee38cdfcc60234853346bc27)
+++ 	(revision )
@@ -1,615 +1,0 @@
-import sys
-import wx
-import wx.lib
-import numpy,math
-import copy
-
-from sans.guicomm.events import StatusEvent   
-(ModelEventbox, EVT_MODEL_BOX) = wx.lib.newevent.NewEvent()
-_BOX_WIDTH = 80
-
-def format_number(value, high=False):
-    """
-        Return a float in a standardized, human-readable formatted string 
-    """
-    try: 
-        value = float(value)
-    except:
-        print "returning 0"
-        return "0"
-    
-    if high:
-        return "%-6.4g" % value
-    else:
-        return "%-5.3g" % value
-
-    
-class FitPage(wx.Panel):
-    """
-        FitPanel class contains fields allowing to display results when
-        fitting  a model and one data
-        @note: For Fit to be performed the user should check at least one parameter
-        on fit Panel window.
-  
-    """
-    ## Internal name for the AUI manager
-    window_name = "Fit page"
-    ## Title to appear on top of the window
-    window_caption = "Fit Page"
-    
-    
-    def __init__(self, parent, *args, **kwargs):
-        wx.Panel.__init__(self, parent, *args, **kwargs)
-        """ 
-            Initialization of the Panel
-        """
-        self.manager = None
-        self.parent  = parent
-        self.event_owner=None
-        #panel interface
-        self.vbox  = wx.BoxSizer(wx.VERTICAL)
-        self.sizer4 = wx.GridBagSizer(5,5)
-        self.sizer3 = wx.GridBagSizer(5,5)
-        self.sizer2 = wx.GridBagSizer(5,5)
-        self.sizer1 = wx.GridBagSizer(5,5)
-        self.DataSource      = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
-        self.DataSource.SetToolTipString("name of data to fit")
-        self.modelbox = wx.ComboBox(self, -1)
-        id = wx.NewId()
-        self.btFit =wx.Button(self,id,'Fit')
-        self.btFit.Bind(wx.EVT_BUTTON, self.onFit,id=id)
-        self.btFit.SetToolTipString("Perform fit.")
-        self.vbox.Add(self.sizer3)
-        self.vbox.Add(self.sizer2)
-        self.vbox.Add(self.sizer4)
-        self.vbox.Add(self.sizer1)
-        
-        id = wx.NewId()
-        self.btClose =wx.Button(self,id,'Close')
-        self.btClose.Bind(wx.EVT_BUTTON, self.onClose,id=id)
-        self.btClose.SetToolTipString("Close page.")
-        ix = 0
-        iy = 1
-        self.sizer3.Add(wx.StaticText(self, -1, 'Data Source'),(iy,ix),\
-                 (1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        ix += 1
-        self.sizer3.Add(self.DataSource,(iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        ix += 1
-        self.sizer3.Add((20,20),(iy,ix),(1,1),wx.RIGHT|wx.EXPAND|wx.ADJUST_MINSIZE,0)
-        ix = 0
-        iy += 1
-        self.sizer3.Add(wx.StaticText(self,-1,'Model'),(iy,ix),(1,1)\
-                  , wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        ix += 1
-        self.sizer3.Add(self.modelbox,(iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        ix = 1
-        iy = 1
-        self.text4_1 = wx.StaticText(self, -1, 'Min')
-        self.sizer4.Add(self.text4_1,(iy, ix),(1,1),\
-                            wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        self.text4_1.Hide()
-        ix += 2
-        self.text4_2 = wx.StaticText(self, -1, 'Max')
-        self.sizer4.Add(self.text4_2,(iy, ix),(1,1),\
-                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        self.text4_2.Hide()
-        ix = 0
-        iy += 1
-        #set maximum range for x in linear scale
-        self.text4_3 = wx.StaticText(self, -1, 'Maximum Data\n Range (Linear)', style=wx.ALIGN_LEFT)
-        self.sizer4.Add(self.text4_3,(iy,ix),(1,1),\
-                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        self.text4_3.Hide()
-        ix += 1
-        self.xmin    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
-        self.xmin.SetToolTipString("Minimun value of x in linear scale.")
-        self.sizer4.Add(self.xmin,(iy, ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        self.xmin.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
-        self.xmin.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
-        self.xmin.Hide()
-        ix += 2
-        self.xmax    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
-        self.xmax.SetToolTipString("Maximum value of x in linear scale.")
-        self.sizer4.Add(self.xmax,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        self.xmax.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
-        self.xmax.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
-        self.xmax.Hide()
-        #Set chisqr  result into TextCtrl
-        ix = 0
-        iy = 1
-        self.text1_1 = wx.StaticText(self, -1, 'Chi2/dof', style=wx.ALIGN_LEFT)
-        self.sizer1.Add(self.text1_1,(iy,ix),(1,1),\
-                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        ix += 1
-        self.tcChi    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
-        self.tcChi.SetToolTipString("Chi^2 over degrees of freedom.")
-        self.sizer1.Add(self.tcChi,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        ix +=2
-        self.sizer1.Add(self.btFit,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        iy+= 1
-        ix = 3
-        self.sizer1.Add( self.btClose,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        # contains link between  model ,all its parameters, and panel organization
-        self.parameters=[]
-        #contains link between a model and selected parameters to fit 
-        self.param_toFit=[]
-        # model on which the fit would be performed
-        self.model=None
-        # preview selected model name
-        self.prevmodel_name=None
-        # flag to check if the user has selected a new model in the combox box
-        self.model_hasChanged=False
-        
-        #dictionary of model name and model class
-        self.model_list_box={}
-        #  comparison between 2 group_id for checking data changes
-        self.prev_group_id= None
-        
-        self.data=None
-        self.vbox.Layout()
-        self.vbox.Fit(self) 
-        self.SetSizer(self.vbox)
-        self.Centre()
-        
-        
-    def set_owner(self,owner):
-        """ 
-            set owner of fitpage
-            @param owner: the class responsible of plotting
-        """
-        self.event_owner=owner    
-   
-  
-    def set_manager(self, manager):
-        """
-             set panel manager
-             @param manager: instance of plugin fitting
-        """
-        self.manager = manager
- 
-         
-    def _DataNameEnter(self):
-        """
-            reset the panel when a new data is selected
-        """
-        if len(self.parameters )>0:
-            for item in self.parameters:
-                item[0].SetValue(False)
-                wx.EVT_CHECKBOX(self, item[0].GetId(), self.select_param)
-                item[2].Hide()
-                item[3].Clear()
-                item[3].Hide()
-                self.xmax.Disable()
-                self.xmin.Disable()
-                self.text1_1.Hide()
-                self.tcChi.Clear()
-                self.vbox.Layout() 
-                self.GrandParent.GetSizer().Layout()
-                
-  
-        
-    def onClose(self,event):
-        """ close the page associated with this panel"""
-        self.GrandParent.onClose()
-        
-        
-    def compute_chisqr(self):
-        """ @param fn: function that return model value
-            @return residuals
-        """
-        flag=self.checkFitRange()
-        if flag== True:
-            try:
-                qmin = float(self.xmin.GetValue())
-                qmax = float(self.xmax.GetValue())
-                #x,y,dy = [numpy.asarray(v) for v in (self.data.x,self.data.y,self.data.dy)]
-                #if qmin==None and qmax==None: 
-                #    fx =numpy.asarray([self.model.run(v) for v in x])
-                #    res=(y - fx)/dy
-                #else:
-                #    idx = (x>= qmin) & (x <=qmax)
-                #    fx = numpy.asarray([self.model.run(item)for item in x[idx ]])
-                #    res= (y[idx] - fx)/dy[idx]  
-                self.data.setFitRange(qmin,qmax)
-                res=self.data.residuals(self.model.runXY)
-                sum=0
-                for item in res:
-                    if numpy.isfinite(item):
-                        sum +=item
-                self.tcChi.SetValue(format_number(math.fabs(sum)))
-            except:
-                wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
-                            "Chisqr cannot be compute: %s"% sys.exc_value))
-            
-            
-    def onFit(self,event):
-        """ signal for fitting"""
-         
-        flag=self.checkFitRange()
-        self.set_manager(self.manager)
-     
-        qmin=float(self.xmin.GetValue())
-        qmax =float( self.xmax.GetValue())
-        if len(self.param_toFit) >0 and flag==True:
-            self.manager.schedule_for_fit( value=1,fitproblem =None) 
-            self.manager._on_single_fit(qmin=qmin,qmax=qmax)
-        else:
-              wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
-                            "Select at least on parameter to fit "))
-    def populate_box(self, dict):
-        """
-            Populate each combox box of each page
-            @param page: the page to populate
-        """
-        id=0
-        self.model_list_box=dict
-        list_name=[]
-        for item in  self.model_list_box.itervalues():
-            name = item.__name__
-            if hasattr(item, "name"):
-                name = item.name
-            list_name.append(name)
-        list_name.sort()   
-        for name in list_name:
-            self.modelbox.Insert(name,int(id))
-            id+=1
-        wx.EVT_COMBOBOX(self.modelbox,-1, self._on_select_model) 
-        return 0
-    
-    
-    def _on_select_model(self,event):
-        """
-            react when a model is selected from page's combo box
-            post an event to its owner to draw an appropriate theory
-        """
-        
-        for item in self.model_list_box.itervalues():
-            name = item.__name__
-            if hasattr(item, "name"):
-                name = item.name
-            #print "fitpage: _on_select_model model name",name ,event.GetString()
-            if name ==event.GetString():
-                try:
-                    evt = ModelEventbox(model=item(),name=name)
-                    wx.PostEvent(self.event_owner, evt)
-                except:
-                    raise #ValueError,"model.name is not equal to model class name"
-                break
-    
-    def _onTextEnter(self,event):
-        """
-            set a flag to determine if the fitting range entered by the user is valid
-        """
-      
-        try:
-            flag=self.checkFitRange()
-            if flag==True and self.model!=None:
-                print"fit page",self.xmin.GetValue(),self.xmax.GetValue()
-                self.manager.redraw_model(float(self.xmin.GetValue())\
-                                               ,float(self.xmax.GetValue()))
-        except:
-
-            wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
-                            "Drawing  Error:wrong value entered %s"% sys.exc_value))
-        
-    def checkFitRange(self):
-        """
-            Check the validity of fitting range
-            @note: xmin should always be less than xmax or else each control box
-            background is colored in pink.
-        """
-       
-        flag = True
-        valueMin = self.xmin.GetValue()
-        valueMax = self.xmax.GetValue()
-        # Check for possible values entered
-        print "fitpage: checkfitrange:",valueMin,valueMax
-        try:
-            if (float(valueMax)> float(valueMin)):
-                self.xmax.SetBackgroundColour(wx.WHITE)
-                self.xmin.SetBackgroundColour(wx.WHITE)
-            else:
-                flag = False
-                self.xmin.SetBackgroundColour("pink")
-                self.xmax.SetBackgroundColour("pink")      
-        except:
-            flag = False
-            self.xmin.SetBackgroundColour("pink")
-            self.xmax.SetBackgroundColour("pink")
-            
-        self.xmin.Refresh()
-        self.xmax.Refresh()
-        return flag
-    
-   
-                    
-    def set_data_name(self,dataset):
-        """ 
-            set data's name.if data has changed reset the panel and xmin and xmax
-            @param name: data 's name
-            @attention:  still  haven't find a better way to display Q name and unit
-            for xmin and xmax range sizer
-        """
-        
-        if self.prev_group_id !=dataset.data.group_id:
-            self._DataNameEnter()
-        self.data = dataset
-        self.prev_group_id=dataset.data.group_id
-        #Displaying Data information
-        self.DataSource.SetValue(str(dataset.data.name))
-        self._xaxis,self._xunit=dataset.data.get_xaxis()
-        self.text4_3.SetLabel(self._xaxis+"["+self._xunit+"]")
-        self.text4_1.Show()
-        self.text4_2.Show()
-        self.text4_3.Show()
-        if not hasattr(dataset.data,'image'):
-            self.xmin.SetValue(format_number(min(dataset.data.x)))
-            self.xmin.Show()
-            self.xmax.SetValue(format_number(max(dataset.data.x)))
-            self.xmax.Show()
-        else:
-            self.xmin.SetValue(format_number(numpy.min(dataset.data.image)))
-            self.xmin.Show()
-            self.xmax.SetValue(format_number(numpy.max(dataset.data.image)))
-            self.xmax.Show()
-        if ((len(self.param_toFit ) >0) and self.DataSource.GetValue()and \
-            self.modelbox.GetValue() and (self.model_hasChanged ==False)):
-            self.xmin.Enable()
-            self.xmax.Enable()
-        else:
-            self.xmin.Disable()
-            self.xmax.Disable()
-            
-        self.vbox.Layout()
-        self.GrandParent.GetSizer().Layout()
-        
-        
-    def set_model_name(self,name):
-        """ 
-            set model name. set also self.model_hasChanged to true is the model 
-            type has changed or false if it didn't
-            @param name: model 's name
-        """
-        self.model_hasChanged=False
-        if (name != self.prevmodel_name):
-            self.model_hasChanged=True
-        self.tcChi.Clear()
-        #self.modelbox.SetValue(str(name))
-        self.prevmodel_name=self.modelbox.GetValue()
-       
-            
-    def get_model_box(self): 
-        """ return reference to combox box self.model"""
-        return self.modelbox
-
-    
-    def get_param_list(self):
-        """
-            @return self.param_toFit: list containing  references to TextCtrl
-            checked.Theses TextCtrl will allow reference to parameters to fit.
-            @raise: if return an empty list of parameter fit will nnote work 
-            properly so raise ValueError,"missing parameter to fit"
-        """
-        if self.param_toFit !=[]:
-            return self.param_toFit
-        else:
-            raise ValueError,"missing parameter to fit"
-        
-        
-    def set_panel(self,model):
-        """
-            Build the panel from the model content
-            @param model: the model selected in combo box for fitting purpose
-        """
-    
-        self.sizer2.Clear(True)
-        self.parameters = []
-        self.param_toFit=[]
-        self.model = model
-        keys = self.model.getParamList()
-        keys.sort()
-        iy = 1
-        ix = 0
-        self.cb1 = wx.CheckBox(self, -1,'Parameters', (10, 10))
-        wx.EVT_CHECKBOX(self, self.cb1.GetId(), self.select_all_param)
-        self.sizer2.Add(self.cb1,(iy, ix),(1,1),\
-                          wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-        ix +=1
-        self.text2_2 = wx.StaticText(self, -1, 'Values')
-        self.sizer2.Add(self.text2_2,(iy, ix),(1,1),\
-                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
-        ix +=2
-        self.text2_3 = wx.StaticText(self, -1, 'Errors')
-        self.sizer2.Add(self.text2_3,(iy, ix),(1,1),\
-                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-        self.text2_3.Hide() 
-        ix +=1
-        self.text2_4 = wx.StaticText(self, -1, 'Units')
-        self.sizer2.Add(self.text2_4,(iy, ix),(1,1),\
-                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
-        self.text2_4.Hide()
-        for item in keys:
-            iy += 1
-            ix = 0
-
-            cb = wx.CheckBox(self, -1, item, (10, 10))
-            cb.SetValue(False)
-            self.sizer2.Add( cb,( iy, ix),(1,1),  wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
-            wx.EVT_CHECKBOX(self, cb.GetId(), self.select_param)
-            
-            ix += 1
-            value= self.model.getParam(item)
-            ctl1 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
-            ctl1.SetValue(str (format_number(value)))
-            ctl1.Bind(wx.EVT_KILL_FOCUS, self._onparamEnter)
-            ctl1.Bind(wx.EVT_TEXT_ENTER,self._onparamEnter)
-            self.sizer2.Add(ctl1, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-            ix += 1
-            text2=wx.StaticText(self, -1, '+/-')
-            self.sizer2.Add(text2,(iy, ix),(1,1),\
-                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
-            text2.Hide()  
-            ix += 1
-            ctl2 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
-            self.sizer2.Add(ctl2, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-            ctl2.Hide()
-            ix +=1
-            # Units
-            try:
-                units = wx.StaticText(self, -1, self.model.details[item][0], style=wx.ALIGN_LEFT)
-            except:
-                units = wx.StaticText(self, -1, "", style=wx.ALIGN_LEFT)
-             
-            self.sizer2.Add(units, (iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
-            #save data
-            self.parameters.append([cb,ctl1,text2,ctl2])
-        #Display units text on panel
-        for item in keys:   
-            if self.model.details[item][0]!='':
-                self.text2_4.Show()
-                break
-            else:
-                self.text2_4.Hide()
-        #Disable or enable fit button
-        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
-            if not (len(self.param_toFit ) >0):
-                self.xmin.Disable()
-                self.xmax.Disable()
-            else:
-                self.xmin.Enable()
-                self.xmax.Enable()
-        else:
-            self.xmin.Disable()
-            self.xmax.Disable()
-        self.compute_chisqr()
-        self.vbox.Layout()
-        self.GrandParent.GetSizer().Layout()
-        
-    
-        
-    def _onparamEnter(self,event):
-        """ 
-            when enter value on panel redraw model according to changed
-        """
-        self.set_model_parameter()
-        self.compute_chisqr()
-     
-    def set_model_parameter(self):
-        """
-            this method redraws the model according to parameters values changes
-            and the reset model according to paramaters changes
-        """
-        if len(self.parameters) !=0 and self.model !=None:
-            for item in self.parameters:
-                try:
-                     name=str(item[0].GetLabelText())
-                     value= float(item[1].GetValue())
-                     self.model.setParam(name,value) 
-                except:
-                     wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
-                            "Drawing  Error:wrong value entered : %s"% sys.exc_value))
-            self.manager.redraw_model(float(self.xmin.GetValue())\
-                                               ,float(self.xmax.GetValue()))      
-                     
-    def select_all_param(self,event): 
-        """
-             set to true or false all checkBox given the main checkbox value cb1
-        """
-        self.param_toFit=[]
-        if  self.parameters !=[]:
-            if  self.cb1.GetValue()==True:
-                for item in self.parameters:
-                    item[0].SetValue(True)
-                    list= [item[0],item[1],item[2],item[3]]
-                    self.param_toFit.append(list )
-                if (self.modelbox.GetValue() and self.DataSource.GetValue()):
-                    if not (len(self.param_toFit ) >0):
-                        self.xmin.Disable()
-                        self.xmax.Disable()
-                    else:
-                        self.xmin.Enable()
-                        self.xmax.Enable()
-            else:
-                for item in self.parameters:
-                    item[0].SetValue(False)
-                self.param_toFit=[]
-              
-                self.xmin.Disable()
-                self.xmax.Disable()
-                
-                
-    def select_param(self,event):
-        """ 
-            Select TextCtrl  checked for fitting purpose and stores them
-            in  self.param_toFit=[] list
-        """
-        self.param_toFit=[]
-        for item in self.parameters:
-            if item[0].GetValue()==True:
-                list= [item[0],item[1],item[2],item[3]]
-                self.param_toFit.append(list )  
-            else:
-                if item in self.param_toFit:
-                    self.param_toFit.remove(item)
-        if len(self.parameters)==len(self.param_toFit):
-            self.cb1.SetValue(True)
-        else:
-            self.cb1.SetValue(False)
-        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
-            if not (len(self.param_toFit ) >0):
-                self.xmin.Disable()
-                self.xmax.Disable()
-            else:
-                self.xmin.Enable()
-                self.xmax.Enable()
-        else:
-            self.xmin.Disable()
-            self.xmax.Disable()
-   
-       
-  
-    def onsetValues(self,chisqr, out,cov):
-        """
-            Build the panel from the fit result
-            @param chisqr:Value of the goodness of fit metric
-            @param out:list of parameter with the best value found during fitting
-            @param cov:Covariance matrix
-       
-        """
-        #print "fitting : onsetvalues out",out
-        self.tcChi.Clear()
-        self.tcChi.SetValue(format_number(chisqr))
-        params = {}
-        is_modified = False
-        has_error = False
-        if out.__class__==numpy.float64:
-            self.param_toFit[0][1].SetValue(format_number(out))
-            self.param_toFit[0][1].Refresh()
-            if cov !=None :
-                self.text2_3.Show()
-                self.param_toFit[0][2].Show()
-                self.param_toFit[0][3].Clear()
-                self.param_toFit[0][3].SetValue(format_number(cov[0]))
-                self.param_toFit[0][3].Show()
-        #out is a list : set parameters and errors in TextCtrl
-        else:
-            i=0
-            #print "fitpage: list param  model",list
-            #for item in self.param_toFit:
-            #    print "fitpage: list display",item[0].GetLabelText()
-            for item in self.param_toFit:
-                if( out != None ) and len(out)<=len(self.param_toFit)and i < len(out):
-                    #item[1].SetValue(format_number(out[i]))
-                    item[1].SetValue(format_number(self.model.getParam(item[0].GetLabelText())))
-                    item[1].Refresh() 
-                if (cov !=None)and len(cov)<=len(self.param_toFit)and i < len(cov):
-                    self.text2_3.Show() 
-                    item[2].Show()
-                    item[3].Clear()
-                    item[3].SetValue(format_number(cov[i]))
-                    item[3].Show()   
-                i+=1
-        
-        self.vbox.Layout()
-        self.GrandParent.GetSizer().Layout()
-    
Index: sansview/perspectives/fitting/fitpage1D.py
===================================================================
--- sansview/perspectives/fitting/fitpage1D.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
+++ sansview/perspectives/fitting/fitpage1D.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
@@ -0,0 +1,614 @@
+import sys
+import wx
+import wx.lib
+import numpy,math
+import copy
+
+from sans.guicomm.events import StatusEvent   
+(ModelEventbox, EVT_MODEL_BOX) = wx.lib.newevent.NewEvent()
+_BOX_WIDTH = 80
+
+def format_number(value, high=False):
+    """
+        Return a float in a standardized, human-readable formatted string 
+    """
+    try: 
+        value = float(value)
+    except:
+        print "returning 0"
+        return "0"
+    
+    if high:
+        return "%-6.4g" % value
+    else:
+        return "%-5.3g" % value
+
+    
+class FitPage1D(wx.Panel):
+    """
+        FitPanel class contains fields allowing to display results when
+        fitting  a model and one data
+        @note: For Fit to be performed the user should check at least one parameter
+        on fit Panel window.
+  
+    """
+    ## Internal name for the AUI manager
+    window_name = "Fit page"
+    ## Title to appear on top of the window
+    window_caption = "Fit Page"
+    
+    
+    def __init__(self, parent, *args, **kwargs):
+        wx.Panel.__init__(self, parent, *args, **kwargs)
+        """ 
+            Initialization of the Panel
+        """
+        self.manager = None
+        self.parent  = parent
+        self.event_owner=None
+        #panel interface
+        self.vbox  = wx.BoxSizer(wx.VERTICAL)
+        self.sizer4 = wx.GridBagSizer(5,5)
+        self.sizer3 = wx.GridBagSizer(5,5)
+        self.sizer2 = wx.GridBagSizer(5,5)
+        self.sizer1 = wx.GridBagSizer(5,5)
+        self.DataSource      = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.DataSource.SetToolTipString("name of data to fit")
+        self.modelbox = wx.ComboBox(self, -1)
+        id = wx.NewId()
+        self.btFit =wx.Button(self,id,'Fit')
+        self.btFit.Bind(wx.EVT_BUTTON, self.onFit,id=id)
+        self.btFit.SetToolTipString("Perform fit.")
+        self.vbox.Add(self.sizer3)
+        self.vbox.Add(self.sizer2)
+        self.vbox.Add(self.sizer4)
+        self.vbox.Add(self.sizer1)
+        
+        id = wx.NewId()
+        self.btClose =wx.Button(self,id,'Close')
+        self.btClose.Bind(wx.EVT_BUTTON, self.onClose,id=id)
+        self.btClose.SetToolTipString("Close page.")
+        ix = 0
+        iy = 1
+        self.sizer3.Add(wx.StaticText(self, -1, 'Data Source'),(iy,ix),\
+                 (1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.sizer3.Add(self.DataSource,(iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix += 1
+        self.sizer3.Add((20,20),(iy,ix),(1,1),wx.RIGHT|wx.EXPAND|wx.ADJUST_MINSIZE,0)
+        ix = 0
+        iy += 1
+        self.sizer3.Add(wx.StaticText(self,-1,'Model'),(iy,ix),(1,1)\
+                  , wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.sizer3.Add(self.modelbox,(iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix = 1
+        iy = 1
+        self.text4_1 = wx.StaticText(self, -1, 'Min')
+        self.sizer4.Add(self.text4_1,(iy, ix),(1,1),\
+                            wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        self.text4_1.Hide()
+        ix += 2
+        self.text4_2 = wx.StaticText(self, -1, 'Max')
+        self.sizer4.Add(self.text4_2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.text4_2.Hide()
+        ix = 0
+        iy += 1
+        #set maximum range for x in linear scale
+        self.text4_3 = wx.StaticText(self, -1, 'Maximum Data\n Range (Linear)', style=wx.ALIGN_LEFT)
+        self.sizer4.Add(self.text4_3,(iy,ix),(1,1),\
+                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        self.text4_3.Hide()
+        ix += 1
+        self.xmin    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.xmin.SetToolTipString("Minimun value of x in linear scale.")
+        self.sizer4.Add(self.xmin,(iy, ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.xmin.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
+        self.xmin.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
+        self.xmin.Hide()
+        ix += 2
+        self.xmax    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.xmax.SetToolTipString("Maximum value of x in linear scale.")
+        self.sizer4.Add(self.xmax,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.xmax.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
+        self.xmax.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
+        self.xmax.Hide()
+        #Set chisqr  result into TextCtrl
+        ix = 0
+        iy = 1
+        self.text1_1 = wx.StaticText(self, -1, 'Chi2/dof', style=wx.ALIGN_LEFT)
+        self.sizer1.Add(self.text1_1,(iy,ix),(1,1),\
+                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.tcChi    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.tcChi.SetToolTipString("Chi^2 over degrees of freedom.")
+        self.sizer1.Add(self.tcChi,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix +=2
+        self.sizer1.Add(self.btFit,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        iy+= 1
+        ix = 3
+        self.sizer1.Add( self.btClose,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        # contains link between  model ,all its parameters, and panel organization
+        self.parameters=[]
+        #contains link between a model and selected parameters to fit 
+        self.param_toFit=[]
+        # model on which the fit would be performed
+        self.model=None
+        # preview selected model name
+        self.prevmodel_name=None
+        # flag to check if the user has selected a new model in the combox box
+        self.model_hasChanged=False
+        
+        #dictionary of model name and model class
+        self.model_list_box={}
+        #  comparison between 2 group_id for checking data changes
+        self.prev_group_id= None
+        
+        self.data=None
+        self.vbox.Layout()
+        self.vbox.Fit(self) 
+        self.SetSizer(self.vbox)
+        self.Centre()
+        
+        
+    def set_owner(self,owner):
+        """ 
+            set owner of fitpage
+            @param owner: the class responsible of plotting
+        """
+        self.event_owner=owner    
+   
+  
+    def set_manager(self, manager):
+        """
+             set panel manager
+             @param manager: instance of plugin fitting
+        """
+        self.manager = manager
+ 
+         
+    def _DataNameEnter(self):
+        """
+            reset the panel when a new data is selected
+        """
+        if len(self.parameters )>0:
+            for item in self.parameters:
+                item[0].SetValue(False)
+                wx.EVT_CHECKBOX(self, item[0].GetId(), self.select_param)
+                item[2].Hide()
+                item[3].Clear()
+                item[3].Hide()
+                self.xmax.Disable()
+                self.xmin.Disable()
+                self.text1_1.Hide()
+                self.tcChi.Clear()
+                self.vbox.Layout() 
+                self.GrandParent.GetSizer().Layout()
+                
+  
+        
+    def onClose(self,event):
+        """ close the page associated with this panel"""
+        self.GrandParent.onClose()
+        
+        
+    def compute_chisqr(self):
+        """ @param fn: function that return model value
+            @return residuals
+        """
+        flag=self.checkFitRange()
+        if flag== True:
+            try:
+                qmin = float(self.xmin.GetValue())
+                qmax = float(self.xmax.GetValue())
+                x,y,dy = [numpy.asarray(v) for v in (self.data.x,self.data.y,self.data.dy)]
+                if qmin==None and qmax==None: 
+                    fx =numpy.asarray([self.model.run(v) for v in x])
+                    res=(y - fx)/dy
+                else:
+                    idx = (x>= qmin) & (x <=qmax)
+                    fx = numpy.asarray([self.model.run(item)for item in x[idx ]])
+                    res= (y[idx] - fx)/dy[idx]  
+                
+               
+                sum=0
+                for item in res:
+                    if numpy.isfinite(item):
+                        sum +=item
+                self.tcChi.SetValue(format_number(math.fabs(sum)))
+            except:
+                wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Chisqr cannot be compute: %s"% sys.exc_value))
+            
+            
+    def onFit(self,event):
+        """ signal for fitting"""
+         
+        flag=self.checkFitRange()
+        self.set_manager(self.manager)
+     
+        qmin=float(self.xmin.GetValue())
+        qmax =float( self.xmax.GetValue())
+        if len(self.param_toFit) >0 and flag==True:
+            self.manager.schedule_for_fit( value=1,fitproblem =None) 
+            self.manager._on_single_fit(qmin=qmin,qmax=qmax)
+        else:
+              wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Select at least on parameter to fit "))
+    def populate_box(self, dict):
+        """
+            Populate each combox box of each page
+            @param page: the page to populate
+        """
+        id=0
+        self.model_list_box=dict
+        list_name=[]
+        for item in  self.model_list_box.itervalues():
+            name = item.__name__
+            if hasattr(item, "name"):
+                name = item.name
+            list_name.append(name)
+        list_name.sort()   
+        for name in list_name:
+            self.modelbox.Insert(name,int(id))
+            id+=1
+        wx.EVT_COMBOBOX(self.modelbox,-1, self._on_select_model) 
+        return 0
+    
+    
+    def _on_select_model(self,event):
+        """
+            react when a model is selected from page's combo box
+            post an event to its owner to draw an appropriate theory
+        """
+        
+        for item in self.model_list_box.itervalues():
+            name = item.__name__
+            if hasattr(item, "name"):
+                name = item.name
+            #print "fitpage: _on_select_model model name",name ,event.GetString()
+            if name ==event.GetString():
+                try:
+                    evt = ModelEventbox(model=item(),name=name)
+                    wx.PostEvent(self.event_owner, evt)
+                except:
+                    raise #ValueError,"model.name is not equal to model class name"
+                break
+    
+    def _onTextEnter(self,event):
+        """
+            set a flag to determine if the fitting range entered by the user is valid
+        """
+      
+        try:
+            flag=self.checkFitRange()
+            if flag==True and self.model!=None:
+                print"fit page",self.xmin.GetValue(),self.xmax.GetValue()
+                self.manager.redraw_model(float(self.xmin.GetValue())\
+                                               ,float(self.xmax.GetValue()))
+        except:
+
+            wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Drawing  Error:wrong value entered %s"% sys.exc_value))
+        
+    def checkFitRange(self):
+        """
+            Check the validity of fitting range
+            @note: xmin should always be less than xmax or else each control box
+            background is colored in pink.
+        """
+       
+        flag = True
+        valueMin = self.xmin.GetValue()
+        valueMax = self.xmax.GetValue()
+        # Check for possible values entered
+        print "fitpage: checkfitrange:",valueMin,valueMax
+        try:
+            if (float(valueMax)> float(valueMin)):
+                self.xmax.SetBackgroundColour(wx.WHITE)
+                self.xmin.SetBackgroundColour(wx.WHITE)
+            else:
+                flag = False
+                self.xmin.SetBackgroundColour("pink")
+                self.xmax.SetBackgroundColour("pink")      
+        except:
+            flag = False
+            self.xmin.SetBackgroundColour("pink")
+            self.xmax.SetBackgroundColour("pink")
+            
+        self.xmin.Refresh()
+        self.xmax.Refresh()
+        return flag
+    
+   
+                    
+    def set_data_name(self,dataset):
+        """ 
+            set data's name.if data has changed reset the panel and xmin and xmax
+            @param name: data 's name
+            @attention:  still  haven't find a better way to display Q name and unit
+            for xmin and xmax range sizer
+        """
+        
+        if self.prev_group_id !=dataset.group_id:
+            self._DataNameEnter()
+        self.data = dataset
+        self.prev_group_id=dataset.group_id
+        #Displaying Data information
+        self.DataSource.SetValue(str(dataset.name))
+        self._xaxis,self._xunit=dataset.get_xaxis()
+        self.text4_3.SetLabel(self._xaxis+"["+self._xunit+"]")
+        self.text4_1.Show()
+        self.text4_2.Show()
+        self.text4_3.Show()
+       
+        self.xmin.SetValue(format_number(min(dataset.x)))
+        self.xmin.Show()
+        self.xmax.SetValue(format_number(max(dataset.x)))
+        self.xmax.Show()
+        
+        if ((len(self.param_toFit ) >0) and self.DataSource.GetValue()and \
+            self.modelbox.GetValue() and (self.model_hasChanged ==False)):
+            self.xmin.Enable()
+            self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+            
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+        
+        
+    def set_model_name(self,name):
+        """ 
+            set model name. set also self.model_hasChanged to true is the model 
+            type has changed or false if it didn't
+            @param name: model 's name
+        """
+        self.model_hasChanged=False
+        if (name != self.prevmodel_name):
+            self.model_hasChanged=True
+        self.tcChi.Clear()
+        #self.modelbox.SetValue(str(name))
+        self.prevmodel_name=self.modelbox.GetValue()
+       
+            
+    def get_model_box(self): 
+        """ return reference to combox box self.model"""
+        return self.modelbox
+
+    
+    def get_param_list(self):
+        """
+            @return self.param_toFit: list containing  references to TextCtrl
+            checked.Theses TextCtrl will allow reference to parameters to fit.
+            @raise: if return an empty list of parameter fit will nnote work 
+            properly so raise ValueError,"missing parameter to fit"
+        """
+        if self.param_toFit !=[]:
+            return self.param_toFit
+        else:
+            raise ValueError,"missing parameter to fit"
+        
+        
+    def set_panel(self,model):
+        """
+            Build the panel from the model content
+            @param model: the model selected in combo box for fitting purpose
+        """
+        
+        self.sizer2.Clear(True)
+        self.parameters = []
+        self.param_toFit=[]
+        self.model = model
+        keys = self.model.getParamList()
+        keys.sort()
+        iy = 1
+        ix = 0
+        self.cb1 = wx.CheckBox(self, -1,'Parameters', (10, 10))
+        wx.EVT_CHECKBOX(self, self.cb1.GetId(), self.select_all_param)
+        self.sizer2.Add(self.cb1,(iy, ix),(1,1),\
+                          wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix +=1
+        self.text2_2 = wx.StaticText(self, -1, 'Values')
+        self.sizer2.Add(self.text2_2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+        ix +=2
+        self.text2_3 = wx.StaticText(self, -1, 'Errors')
+        self.sizer2.Add(self.text2_3,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.text2_3.Hide() 
+        ix +=1
+        self.text2_4 = wx.StaticText(self, -1, 'Units')
+        self.sizer2.Add(self.text2_4,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+        self.text2_4.Hide()
+        for item in keys:
+            iy += 1
+            ix = 0
+
+            cb = wx.CheckBox(self, -1, item, (10, 10))
+            cb.SetValue(False)
+            self.sizer2.Add( cb,( iy, ix),(1,1),  wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+            wx.EVT_CHECKBOX(self, cb.GetId(), self.select_param)
+            
+            ix += 1
+            value= self.model.getParam(item)
+            ctl1 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
+            ctl1.SetValue(str (format_number(value)))
+            ctl1.Bind(wx.EVT_KILL_FOCUS, self._onparamEnter)
+            ctl1.Bind(wx.EVT_TEXT_ENTER,self._onparamEnter)
+            self.sizer2.Add(ctl1, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            ix += 1
+            text2=wx.StaticText(self, -1, '+/-')
+            self.sizer2.Add(text2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+            text2.Hide()  
+            ix += 1
+            ctl2 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
+            self.sizer2.Add(ctl2, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            ctl2.Hide()
+            ix +=1
+            
+            # Units
+ 
+            try:
+                units = wx.StaticText(self, -1, self.model.details[item][0], style=wx.ALIGN_LEFT)
+            except:
+                units = wx.StaticText(self, -1, "", style=wx.ALIGN_LEFT)
+             
+            self.sizer2.Add(units, (iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            #save data
+            self.parameters.append([cb,ctl1,text2,ctl2])
+        #Display units text on panel
+        for item in keys:   
+            if self.model.details[item][0]!='':
+                self.text2_4.Show()
+                break
+            else:
+                self.text2_4.Hide()
+        #Disable or enable fit button
+        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+            if not (len(self.param_toFit ) >0):
+                self.xmin.Disable()
+                self.xmax.Disable()
+            else:
+                self.xmin.Enable()
+                self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+        
+        self.compute_chisqr()
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+        
+       
+        
+    def _onparamEnter(self,event):
+        """ 
+            when enter value on panel redraw model according to changed
+        """
+        self.set_model_parameter()
+        self.compute_chisqr()
+     
+    def set_model_parameter(self):
+        """
+            this method redraws the model according to parameters values changes
+            and the reset model according to paramaters changes
+        """
+        if len(self.parameters) !=0 and self.model !=None:
+            for item in self.parameters:
+                try:
+                     name=str(item[0].GetLabelText())
+                     value= float(item[1].GetValue())
+                     self.model.setParam(name,value) 
+                except:
+                     wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Drawing  Error:wrong value entered : %s"% sys.exc_value))
+            self.manager.redraw_model(float(self.xmin.GetValue())\
+                                               ,float(self.xmax.GetValue()))      
+                     
+    def select_all_param(self,event): 
+        """
+             set to true or false all checkBox given the main checkbox value cb1
+        """
+        self.param_toFit=[]
+        if  self.parameters !=[]:
+            if  self.cb1.GetValue()==True:
+                for item in self.parameters:
+                    item[0].SetValue(True)
+                    list= [item[0],item[1],item[2],item[3]]
+                    self.param_toFit.append(list )
+                if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+                    if not (len(self.param_toFit ) >0):
+                        self.xmin.Disable()
+                        self.xmax.Disable()
+                    else:
+                        self.xmin.Enable()
+                        self.xmax.Enable()
+            else:
+                for item in self.parameters:
+                    item[0].SetValue(False)
+                self.param_toFit=[]
+              
+                self.xmin.Disable()
+                self.xmax.Disable()
+                
+                
+    def select_param(self,event):
+        """ 
+            Select TextCtrl  checked for fitting purpose and stores them
+            in  self.param_toFit=[] list
+        """
+        self.param_toFit=[]
+        for item in self.parameters:
+            if item[0].GetValue()==True:
+                list= [item[0],item[1],item[2],item[3]]
+                self.param_toFit.append(list )  
+            else:
+                if item in self.param_toFit:
+                    self.param_toFit.remove(item)
+        if len(self.parameters)==len(self.param_toFit):
+            self.cb1.SetValue(True)
+        else:
+            self.cb1.SetValue(False)
+        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+            if not (len(self.param_toFit ) >0):
+                self.xmin.Disable()
+                self.xmax.Disable()
+            else:
+                self.xmin.Enable()
+                self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+   
+       
+  
+    def onsetValues(self,chisqr, out,cov):
+        """
+            Build the panel from the fit result
+            @param chisqr:Value of the goodness of fit metric
+            @param out:list of parameter with the best value found during fitting
+            @param cov:Covariance matrix
+       
+        """
+        #print "fitting : onsetvalues out",out
+        self.tcChi.Clear()
+        self.tcChi.SetValue(format_number(chisqr))
+        params = {}
+        is_modified = False
+        has_error = False
+        if out.__class__==numpy.float64:
+            self.param_toFit[0][1].SetValue(format_number(out))
+            self.param_toFit[0][1].Refresh()
+            if cov !=None :
+                self.text2_3.Show()
+                self.param_toFit[0][2].Show()
+                self.param_toFit[0][3].Clear()
+                self.param_toFit[0][3].SetValue(format_number(cov[0]))
+                self.param_toFit[0][3].Show()
+        #out is a list : set parameters and errors in TextCtrl
+        else:
+            i=0
+            #print "fitpage: list param  model",list
+            #for item in self.param_toFit:
+            #    print "fitpage: list display",item[0].GetLabelText()
+            for item in self.param_toFit:
+                if( out != None ) and len(out)<=len(self.param_toFit)and i < len(out):
+                    #item[1].SetValue(format_number(out[i]))
+                    item[1].SetValue(format_number(self.model.getParam(item[0].GetLabelText())))
+                    item[1].Refresh() 
+                if (cov !=None)and len(cov)<=len(self.param_toFit)and i < len(cov):
+                    self.text2_3.Show() 
+                    item[2].Show()
+                    item[3].Clear()
+                    item[3].SetValue(format_number(cov[i]))
+                    item[3].Show()   
+                i+=1
+        
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+    
Index: sansview/perspectives/fitting/fitpage2D.py
===================================================================
--- sansview/perspectives/fitting/fitpage2D.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
+++ sansview/perspectives/fitting/fitpage2D.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
@@ -0,0 +1,615 @@
+import sys
+import wx
+import wx.lib
+import numpy,math
+import copy
+
+from sans.guicomm.events import StatusEvent   
+(ModelEventbox, EVT_MODEL_BOX) = wx.lib.newevent.NewEvent()
+_BOX_WIDTH = 80
+
+def format_number(value, high=False):
+    """
+        Return a float in a standardized, human-readable formatted string 
+    """
+    try: 
+        value = float(value)
+    except:
+        print "returning 0"
+        return "0"
+    
+    if high:
+        return "%-6.4g" % value
+    else:
+        return "%-5.3g" % value
+
+    
+class FitPage2D(wx.Panel):
+    """
+        FitPanel class contains fields allowing to display results when
+        fitting  a model and one data
+        @note: For Fit to be performed the user should check at least one parameter
+        on fit Panel window.
+  
+    """
+    ## Internal name for the AUI manager
+    window_name = "Fit page"
+    ## Title to appear on top of the window
+    window_caption = "Fit Page"
+    
+    
+    def __init__(self, parent, *args, **kwargs):
+        wx.Panel.__init__(self, parent, *args, **kwargs)
+        """ 
+            Initialization of the Panel
+        """
+        self.manager = None
+        self.parent  = parent
+        self.event_owner=None
+        #panel interface
+        self.vbox  = wx.BoxSizer(wx.VERTICAL)
+        self.sizer4 = wx.GridBagSizer(5,5)
+        self.sizer3 = wx.GridBagSizer(5,5)
+        self.sizer2 = wx.GridBagSizer(5,5)
+        self.sizer1 = wx.GridBagSizer(5,5)
+        self.DataSource      = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.DataSource.SetToolTipString("name of data to fit")
+        self.modelbox = wx.ComboBox(self, -1)
+        id = wx.NewId()
+        self.btFit =wx.Button(self,id,'Fit')
+        self.btFit.Bind(wx.EVT_BUTTON, self.onFit,id=id)
+        self.btFit.SetToolTipString("Perform fit.")
+        self.vbox.Add(self.sizer3)
+        self.vbox.Add(self.sizer2)
+        self.vbox.Add(self.sizer4)
+        self.vbox.Add(self.sizer1)
+        
+        id = wx.NewId()
+        self.btClose =wx.Button(self,id,'Close')
+        self.btClose.Bind(wx.EVT_BUTTON, self.onClose,id=id)
+        self.btClose.SetToolTipString("Close page.")
+        ix = 0
+        iy = 1
+        self.sizer3.Add(wx.StaticText(self, -1, 'Data Source'),(iy,ix),\
+                 (1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.sizer3.Add(self.DataSource,(iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix += 1
+        self.sizer3.Add((20,20),(iy,ix),(1,1),wx.RIGHT|wx.EXPAND|wx.ADJUST_MINSIZE,0)
+        ix = 0
+        iy += 1
+        self.sizer3.Add(wx.StaticText(self,-1,'Model'),(iy,ix),(1,1)\
+                  , wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.sizer3.Add(self.modelbox,(iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix = 1
+        iy = 1
+        self.text4_1 = wx.StaticText(self, -1, 'Min')
+        self.sizer4.Add(self.text4_1,(iy, ix),(1,1),\
+                            wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        self.text4_1.Hide()
+        ix += 2
+        self.text4_2 = wx.StaticText(self, -1, 'Max')
+        self.sizer4.Add(self.text4_2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.text4_2.Hide()
+        ix = 0
+        iy += 1
+        #set maximum range for x in linear scale
+        self.text4_3 = wx.StaticText(self, -1, 'Maximum Data\n Range (Linear)', style=wx.ALIGN_LEFT)
+        self.sizer4.Add(self.text4_3,(iy,ix),(1,1),\
+                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        self.text4_3.Hide()
+        ix += 1
+        self.xmin    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.xmin.SetToolTipString("Minimun value of x in linear scale.")
+        self.sizer4.Add(self.xmin,(iy, ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.xmin.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
+        self.xmin.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
+        self.xmin.Hide()
+        ix += 2
+        self.xmax    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.xmax.SetToolTipString("Maximum value of x in linear scale.")
+        self.sizer4.Add(self.xmax,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.xmax.Bind(wx.EVT_KILL_FOCUS, self._onTextEnter)
+        self.xmax.Bind(wx.EVT_TEXT_ENTER, self._onTextEnter)
+        self.xmax.Hide()
+        #Set chisqr  result into TextCtrl
+        ix = 0
+        iy = 1
+        self.text1_1 = wx.StaticText(self, -1, 'Chi2/dof', style=wx.ALIGN_LEFT)
+        self.sizer1.Add(self.text1_1,(iy,ix),(1,1),\
+                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix += 1
+        self.tcChi    = wx.TextCtrl(self, -1,size=(_BOX_WIDTH,20))
+        self.tcChi.SetToolTipString("Chi^2 over degrees of freedom.")
+        self.sizer1.Add(self.tcChi,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        ix +=2
+        self.sizer1.Add(self.btFit,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        iy+= 1
+        ix = 3
+        self.sizer1.Add( self.btClose,(iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        # contains link between  model ,all its parameters, and panel organization
+        self.parameters=[]
+        #contains link between a model and selected parameters to fit 
+        self.param_toFit=[]
+        # model on which the fit would be performed
+        self.model=None
+        # preview selected model name
+        self.prevmodel_name=None
+        # flag to check if the user has selected a new model in the combox box
+        self.model_hasChanged=False
+        
+        #dictionary of model name and model class
+        self.model_list_box={}
+        #  comparison between 2 group_id for checking data changes
+        self.prev_group_id= None
+        
+        self.data=None
+        self.vbox.Layout()
+        self.vbox.Fit(self) 
+        self.SetSizer(self.vbox)
+        self.Centre()
+        
+        
+    def set_owner(self,owner):
+        """ 
+            set owner of fitpage
+            @param owner: the class responsible of plotting
+        """
+        self.event_owner=owner    
+   
+  
+    def set_manager(self, manager):
+        """
+             set panel manager
+             @param manager: instance of plugin fitting
+        """
+        self.manager = manager
+ 
+         
+    def _DataNameEnter(self):
+        """
+            reset the panel when a new data is selected
+        """
+        if len(self.parameters )>0:
+            for item in self.parameters:
+                item[0].SetValue(False)
+                wx.EVT_CHECKBOX(self, item[0].GetId(), self.select_param)
+                item[2].Hide()
+                item[3].Clear()
+                item[3].Hide()
+                self.xmax.Disable()
+                self.xmin.Disable()
+                self.text1_1.Hide()
+                self.tcChi.Clear()
+                self.vbox.Layout() 
+                self.GrandParent.GetSizer().Layout()
+                
+  
+        
+    def onClose(self,event):
+        """ close the page associated with this panel"""
+        self.GrandParent.onClose()
+        
+        
+    def compute_chisqr(self):
+        """ @param fn: function that return model value
+            @return residuals
+        """
+        flag=self.checkFitRange()
+        if flag== True:
+            try:
+                qmin = float(self.xmin.GetValue())
+                qmax = float(self.xmax.GetValue())
+                #x,y,dy = [numpy.asarray(v) for v in (self.data.x,self.data.y,self.data.dy)]
+                #if qmin==None and qmax==None: 
+                #    fx =numpy.asarray([self.model.run(v) for v in x])
+                #    res=(y - fx)/dy
+                #else:
+                #    idx = (x>= qmin) & (x <=qmax)
+                #    fx = numpy.asarray([self.model.run(item)for item in x[idx ]])
+                #    res= (y[idx] - fx)/dy[idx]  
+                self.data.setFitRange(qmin,qmax)
+                res=self.data.residuals(self.model.runXY)
+                sum=0
+                for item in res:
+                    if numpy.isfinite(item):
+                        sum +=item
+                self.tcChi.SetValue(format_number(math.fabs(sum)))
+            except:
+                wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Chisqr cannot be compute: %s"% sys.exc_value))
+            
+            
+    def onFit(self,event):
+        """ signal for fitting"""
+         
+        flag=self.checkFitRange()
+        self.set_manager(self.manager)
+     
+        qmin=float(self.xmin.GetValue())
+        qmax =float( self.xmax.GetValue())
+        if len(self.param_toFit) >0 and flag==True:
+            self.manager.schedule_for_fit( value=1,fitproblem =None) 
+            self.manager._on_single_fit(qmin=qmin,qmax=qmax)
+        else:
+              wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Select at least on parameter to fit "))
+    def populate_box(self, dict):
+        """
+            Populate each combox box of each page
+            @param page: the page to populate
+        """
+        id=0
+        self.model_list_box=dict
+        list_name=[]
+        for item in  self.model_list_box.itervalues():
+            name = item.__name__
+            if hasattr(item, "name"):
+                name = item.name
+            list_name.append(name)
+        list_name.sort()   
+        for name in list_name:
+            self.modelbox.Insert(name,int(id))
+            id+=1
+        wx.EVT_COMBOBOX(self.modelbox,-1, self._on_select_model) 
+        return 0
+    
+    
+    def _on_select_model(self,event):
+        """
+            react when a model is selected from page's combo box
+            post an event to its owner to draw an appropriate theory
+        """
+        
+        for item in self.model_list_box.itervalues():
+            name = item.__name__
+            if hasattr(item, "name"):
+                name = item.name
+            #print "fitpage: _on_select_model model name",name ,event.GetString()
+            if name ==event.GetString():
+                try:
+                    evt = ModelEventbox(model=item(),name=name)
+                    wx.PostEvent(self.event_owner, evt)
+                except:
+                    raise #ValueError,"model.name is not equal to model class name"
+                break
+    
+    def _onTextEnter(self,event):
+        """
+            set a flag to determine if the fitting range entered by the user is valid
+        """
+      
+        try:
+            flag=self.checkFitRange()
+            if flag==True and self.model!=None:
+                print"fit page",self.xmin.GetValue(),self.xmax.GetValue()
+                self.manager.redraw_model(float(self.xmin.GetValue())\
+                                               ,float(self.xmax.GetValue()))
+        except:
+
+            wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Drawing  Error:wrong value entered %s"% sys.exc_value))
+        
+    def checkFitRange(self):
+        """
+            Check the validity of fitting range
+            @note: xmin should always be less than xmax or else each control box
+            background is colored in pink.
+        """
+       
+        flag = True
+        valueMin = self.xmin.GetValue()
+        valueMax = self.xmax.GetValue()
+        # Check for possible values entered
+        print "fitpage: checkfitrange:",valueMin,valueMax
+        try:
+            if (float(valueMax)> float(valueMin)):
+                self.xmax.SetBackgroundColour(wx.WHITE)
+                self.xmin.SetBackgroundColour(wx.WHITE)
+            else:
+                flag = False
+                self.xmin.SetBackgroundColour("pink")
+                self.xmax.SetBackgroundColour("pink")      
+        except:
+            flag = False
+            self.xmin.SetBackgroundColour("pink")
+            self.xmax.SetBackgroundColour("pink")
+            
+        self.xmin.Refresh()
+        self.xmax.Refresh()
+        return flag
+    
+   
+                    
+    def set_data_name(self,dataset):
+        """ 
+            set data's name.if data has changed reset the panel and xmin and xmax
+            @param name: data 's name
+            @attention:  still  haven't find a better way to display Q name and unit
+            for xmin and xmax range sizer
+        """
+        
+        if self.prev_group_id !=dataset.data.group_id:
+            self._DataNameEnter()
+        self.data = dataset
+        self.prev_group_id=dataset.data.group_id
+        #Displaying Data information
+        self.DataSource.SetValue(str(dataset.data.name))
+        self._xaxis,self._xunit=dataset.data.get_xaxis()
+        self.text4_3.SetLabel(self._xaxis+"["+self._xunit+"]")
+        self.text4_1.Show()
+        self.text4_2.Show()
+        self.text4_3.Show()
+        if not hasattr(dataset.data,'image'):
+            self.xmin.SetValue(format_number(min(dataset.data.x)))
+            self.xmin.Show()
+            self.xmax.SetValue(format_number(max(dataset.data.x)))
+            self.xmax.Show()
+        else:
+            self.xmin.SetValue(format_number(numpy.min(dataset.data.image)))
+            self.xmin.Show()
+            self.xmax.SetValue(format_number(numpy.max(dataset.data.image)))
+            self.xmax.Show()
+        if ((len(self.param_toFit ) >0) and self.DataSource.GetValue()and \
+            self.modelbox.GetValue() and (self.model_hasChanged ==False)):
+            self.xmin.Enable()
+            self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+            
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+        
+        
+    def set_model_name(self,name):
+        """ 
+            set model name. set also self.model_hasChanged to true is the model 
+            type has changed or false if it didn't
+            @param name: model 's name
+        """
+        self.model_hasChanged=False
+        if (name != self.prevmodel_name):
+            self.model_hasChanged=True
+        self.tcChi.Clear()
+        #self.modelbox.SetValue(str(name))
+        self.prevmodel_name=self.modelbox.GetValue()
+       
+            
+    def get_model_box(self): 
+        """ return reference to combox box self.model"""
+        return self.modelbox
+
+    
+    def get_param_list(self):
+        """
+            @return self.param_toFit: list containing  references to TextCtrl
+            checked.Theses TextCtrl will allow reference to parameters to fit.
+            @raise: if return an empty list of parameter fit will nnote work 
+            properly so raise ValueError,"missing parameter to fit"
+        """
+        if self.param_toFit !=[]:
+            return self.param_toFit
+        else:
+            raise ValueError,"missing parameter to fit"
+        
+        
+    def set_panel(self,model):
+        """
+            Build the panel from the model content
+            @param model: the model selected in combo box for fitting purpose
+        """
+    
+        self.sizer2.Clear(True)
+        self.parameters = []
+        self.param_toFit=[]
+        self.model = model
+        keys = self.model.getParamList()
+        keys.sort()
+        iy = 1
+        ix = 0
+        self.cb1 = wx.CheckBox(self, -1,'Parameters', (10, 10))
+        wx.EVT_CHECKBOX(self, self.cb1.GetId(), self.select_all_param)
+        self.sizer2.Add(self.cb1,(iy, ix),(1,1),\
+                          wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+        ix +=1
+        self.text2_2 = wx.StaticText(self, -1, 'Values')
+        self.sizer2.Add(self.text2_2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+        ix +=2
+        self.text2_3 = wx.StaticText(self, -1, 'Errors')
+        self.sizer2.Add(self.text2_3,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+        self.text2_3.Hide() 
+        ix +=1
+        self.text2_4 = wx.StaticText(self, -1, 'Units')
+        self.sizer2.Add(self.text2_4,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+        self.text2_4.Hide()
+        for item in keys:
+            iy += 1
+            ix = 0
+
+            cb = wx.CheckBox(self, -1, item, (10, 10))
+            cb.SetValue(False)
+            self.sizer2.Add( cb,( iy, ix),(1,1),  wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
+            wx.EVT_CHECKBOX(self, cb.GetId(), self.select_param)
+            
+            ix += 1
+            value= self.model.getParam(item)
+            ctl1 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
+            ctl1.SetValue(str (format_number(value)))
+            ctl1.Bind(wx.EVT_KILL_FOCUS, self._onparamEnter)
+            ctl1.Bind(wx.EVT_TEXT_ENTER,self._onparamEnter)
+            self.sizer2.Add(ctl1, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            ix += 1
+            text2=wx.StaticText(self, -1, '+/-')
+            self.sizer2.Add(text2,(iy, ix),(1,1),\
+                            wx.EXPAND|wx.ADJUST_MINSIZE, 0) 
+            text2.Hide()  
+            ix += 1
+            ctl2 = wx.TextCtrl(self, -1, size=(_BOX_WIDTH,20), style=wx.TE_PROCESS_ENTER)
+            self.sizer2.Add(ctl2, (iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            ctl2.Hide()
+            ix +=1
+            # Units
+            try:
+                units = wx.StaticText(self, -1, self.model.details[item][0], style=wx.ALIGN_LEFT)
+            except:
+                units = wx.StaticText(self, -1, "", style=wx.ALIGN_LEFT)
+             
+            self.sizer2.Add(units, (iy,ix),(1,1),  wx.EXPAND|wx.ADJUST_MINSIZE, 0)
+            #save data
+            self.parameters.append([cb,ctl1,text2,ctl2])
+        #Display units text on panel
+        for item in keys:   
+            if self.model.details[item][0]!='':
+                self.text2_4.Show()
+                break
+            else:
+                self.text2_4.Hide()
+        #Disable or enable fit button
+        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+            if not (len(self.param_toFit ) >0):
+                self.xmin.Disable()
+                self.xmax.Disable()
+            else:
+                self.xmin.Enable()
+                self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+        self.compute_chisqr()
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+        
+    
+        
+    def _onparamEnter(self,event):
+        """ 
+            when enter value on panel redraw model according to changed
+        """
+        self.set_model_parameter()
+        self.compute_chisqr()
+     
+    def set_model_parameter(self):
+        """
+            this method redraws the model according to parameters values changes
+            and the reset model according to paramaters changes
+        """
+        if len(self.parameters) !=0 and self.model !=None:
+            for item in self.parameters:
+                try:
+                     name=str(item[0].GetLabelText())
+                     value= float(item[1].GetValue())
+                     self.model.setParam(name,value) 
+                except:
+                     wx.PostEvent(self.parent.GrandParent, StatusEvent(status=\
+                            "Drawing  Error:wrong value entered : %s"% sys.exc_value))
+            self.manager.redraw_model(float(self.xmin.GetValue())\
+                                               ,float(self.xmax.GetValue()))      
+                     
+    def select_all_param(self,event): 
+        """
+             set to true or false all checkBox given the main checkbox value cb1
+        """
+        self.param_toFit=[]
+        if  self.parameters !=[]:
+            if  self.cb1.GetValue()==True:
+                for item in self.parameters:
+                    item[0].SetValue(True)
+                    list= [item[0],item[1],item[2],item[3]]
+                    self.param_toFit.append(list )
+                if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+                    if not (len(self.param_toFit ) >0):
+                        self.xmin.Disable()
+                        self.xmax.Disable()
+                    else:
+                        self.xmin.Enable()
+                        self.xmax.Enable()
+            else:
+                for item in self.parameters:
+                    item[0].SetValue(False)
+                self.param_toFit=[]
+              
+                self.xmin.Disable()
+                self.xmax.Disable()
+                
+                
+    def select_param(self,event):
+        """ 
+            Select TextCtrl  checked for fitting purpose and stores them
+            in  self.param_toFit=[] list
+        """
+        self.param_toFit=[]
+        for item in self.parameters:
+            if item[0].GetValue()==True:
+                list= [item[0],item[1],item[2],item[3]]
+                self.param_toFit.append(list )  
+            else:
+                if item in self.param_toFit:
+                    self.param_toFit.remove(item)
+        if len(self.parameters)==len(self.param_toFit):
+            self.cb1.SetValue(True)
+        else:
+            self.cb1.SetValue(False)
+        if (self.modelbox.GetValue() and self.DataSource.GetValue()):
+            if not (len(self.param_toFit ) >0):
+                self.xmin.Disable()
+                self.xmax.Disable()
+            else:
+                self.xmin.Enable()
+                self.xmax.Enable()
+        else:
+            self.xmin.Disable()
+            self.xmax.Disable()
+   
+       
+  
+    def onsetValues(self,chisqr, out,cov):
+        """
+            Build the panel from the fit result
+            @param chisqr:Value of the goodness of fit metric
+            @param out:list of parameter with the best value found during fitting
+            @param cov:Covariance matrix
+       
+        """
+        #print "fitting : onsetvalues out",out
+        self.tcChi.Clear()
+        self.tcChi.SetValue(format_number(chisqr))
+        params = {}
+        is_modified = False
+        has_error = False
+        if out.__class__==numpy.float64:
+            self.param_toFit[0][1].SetValue(format_number(out))
+            self.param_toFit[0][1].Refresh()
+            if cov !=None :
+                self.text2_3.Show()
+                self.param_toFit[0][2].Show()
+                self.param_toFit[0][3].Clear()
+                self.param_toFit[0][3].SetValue(format_number(cov[0]))
+                self.param_toFit[0][3].Show()
+        #out is a list : set parameters and errors in TextCtrl
+        else:
+            i=0
+            #print "fitpage: list param  model",list
+            #for item in self.param_toFit:
+            #    print "fitpage: list display",item[0].GetLabelText()
+            for item in self.param_toFit:
+                if( out != None ) and len(out)<=len(self.param_toFit)and i < len(out):
+                    #item[1].SetValue(format_number(out[i]))
+                    item[1].SetValue(format_number(self.model.getParam(item[0].GetLabelText())))
+                    item[1].Refresh() 
+                if (cov !=None)and len(cov)<=len(self.param_toFit)and i < len(cov):
+                    self.text2_3.Show() 
+                    item[2].Show()
+                    item[3].Clear()
+                    item[3].SetValue(format_number(cov[i]))
+                    item[3].Show()   
+                i+=1
+        
+        self.vbox.Layout()
+        self.GrandParent.GetSizer().Layout()
+    
Index: sansview/perspectives/fitting/fitpanel.py
===================================================================
--- sansview/perspectives/fitting/fitpanel.py	(revision 2139c3fdedc4921d43180a3cc053ef2748786879)
+++ sansview/perspectives/fitting/fitpanel.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
@@ -66,5 +66,5 @@
       
         
-    def add_fit_page( self,page_title ):
+    def add_fit_page( self,data ):
         """ 
             Add a fitting page on the notebook contained by fitpanel
@@ -73,12 +73,20 @@
             @return panel : page just added for futher used. is used by fitting module
         """     
-        if self.fit_page_name != page_title:
-            from fitpage import FitPage
-            panel = FitPage(self.nb, -1)
+        try:
+            name = data.group_id # item in Data1D
+        except:
+            name = 'Fit'
+        if self.fit_page_name != name:
+            if data.__class__.__name__=='MetaData2D':
+                 from fitpage2D import FitPage2D
+                 panel = FitPage2D(self.nb, -1)
+            else:
+                from fitpage1D import FitPage1D
+                panel = FitPage1D(self.nb, -1)
             panel.set_manager(self.manager)
             panel.set_owner(self.event_owner)
-            self.nb.AddPage(page=panel,text=page_title,select=True)
+            self.nb.AddPage(page=panel,text=name,select=True)
             panel.populate_box( self.model_list_box)
-            self.fit_page_name = page_title
+            self.fit_page_name = name
             return panel
         
Index: sansview/perspectives/fitting/fitting.py
===================================================================
--- sansview/perspectives/fitting/fitting.py	(revision 00353b47ce0686a8ee38cdfcc60234853346bc27)
+++ sansview/perspectives/fitting/fitting.py	(revision bcd6d51ec9434da3082881dfdfb88a73950d810c)
@@ -14,5 +14,5 @@
 
 import models
-import fitpage
+import fitpage1D
 import park
 
@@ -64,5 +64,5 @@
         self.fit_panel.set_owner(owner)
         self.fit_panel.set_model_list(self.menu_mng.get_model_list())
-        owner.Bind(fitpage.EVT_MODEL_BOX,self._on_model_panel)
+        owner.Bind(fitpage1D.EVT_MODEL_BOX,self._on_model_panel)
         #create  menubar items
         return [(id, self.menu1, "Fitting"),(id2, menu2, "Model")]
@@ -146,17 +146,11 @@
             if item.name == self.panel.graph.selected_plottable or item.__class__.__name__ is "MetaData2D":
                 #find a name for the page created for notebook
+                
                 try:
-                    name = item.group_id # item in Data1D
-                except:
-                    name = 'Fit'
-                try:
-                    page = self.fit_panel.add_fit_page(name)
+                    page = self.fit_panel.add_fit_page(item)
                     # add data associated to the page created
-                    if item.__class__.__name__=='MetaData1D' or item.__class__.__name__=='Data1D' :
-                        new_item=FitData1D(item)
-                    else:
-                        new_item=FitData2D(item)
+                    
                     if page !=None:    
-                        page.set_data_name(new_item)
+                        page.set_data_name(item)
                         #create a fitproblem storing all link to data,model,page creation
                         self.page_finder[page]= FitProblem()
@@ -164,7 +158,6 @@
                         #datap = PlottableData(data=data_for_park,data1d=item)
                         #self.page_finder[page].add_data(datap)
-                        self.page_finder[page].add_data(new_item)
+                        self.page_finder[page].add_data(item)
                 except:
-                    raise
                     wx.PostEvent(self.parent, StatusEvent(status="Creating Fit page: %s"\
                     %sys.exc_value))
@@ -201,5 +194,5 @@
                 list=value.get_model()
                 model=list[0]
-                print "fitting",model.name,modelname
+                #print "fitting",model.name,modelname
                 if model.name== modelname:
                     value.set_model_param(names,values)
@@ -437,4 +430,5 @@
             react to model selection on any combo box or model menu.plot the model  
         """
+        
         model = evt.model
         name = evt.name
@@ -444,9 +438,9 @@
             current_pg.set_model_name(name)
             current_pg.set_panel(model)
+            
             try:
-                fitdata=self.page_finder[current_pg].get_data()
-                M_name="M"+str(self.index_model)+"= "+name+"("+fitdata.data.group_id+")"
+                metadata=self.page_finder[current_pg].get_data()
+                M_name="M"+str(self.index_model)+"= "+name+"("+metadata.group_id+")"
             except:
-                raise 
                 M_name="M"+str(self.index_model)+"= "+name
             model.name="M"+str(self.index_model)
@@ -479,9 +473,8 @@
             for page in self.page_finder.iterkeys():
                 if  page==currpage :  
+                    data=self.page_finder[page].get_data()
+                    list=self.page_finder[page].get_model()
+                    model=list[0]
                     break 
-            fitdata=self.page_finder[page].get_data()
-            list=self.page_finder[page].get_model()
-            model=list[0]
-            data=fitdata.data
             
             if data!=None and data.__class__.__name__ != 'MetaData2D':
