source: sasview/guitools/fitDialog.py @ 106ef4d

ESS_GUIESS_GUI_DocsESS_GUI_batch_fittingESS_GUI_bumps_abstractionESS_GUI_iss1116ESS_GUI_iss879ESS_GUI_iss959ESS_GUI_openclESS_GUI_orderingESS_GUI_sync_sascalccostrafo411magnetic_scattrelease-4.1.1release-4.1.2release-4.2.2release_4.0.1ticket-1009ticket-1094-headlessticket-1242-2d-resolutionticket-1243ticket-1249ticket885unittest-saveload
Last change on this file since 106ef4d was 106ef4d, checked in by Gervaise Alina <gervyh@…>, 16 years ago

fitDialog modified

  • Property mode set to 100644
File size: 9.8 KB
Line 
1#!/usr/bin/python
2
3# fitDialog.py
4
5import wx
6from PlotPanel import PlotPanel
7from plottables import Theory1D
8import math,pylab,fittings
9class LinearFit(wx.Dialog):
10    #def __init__(self, parent, id, title):
11    def __init__(self, parent, plottable, push_data,transform, id, title):
12        wx.Dialog.__init__(self, parent, id, title, size=(450, 300))
13        """
14            for the fit window
15        """
16        self.parent = parent
17        self.transform = transform
18        #dialog panel self call function to plot the fitting function
19        self.push_data = push_data
20        #dialog self plottable
21        self.plottable = plottable
22       
23        #Dialog interface
24        panel = wx.Panel(self, -1, style=wx.SIMPLE_BORDER)   
25        vbox  = wx.BoxSizer(wx.VERTICAL)
26        sizer = wx.GridBagSizer(5,5)
27       
28        vbox.Add(panel, 1, wx.EXPAND | wx.ALL)
29 
30        self.tcA = wx.TextCtrl(panel, -1,size=(120,20),style=wx.SIMPLE_BORDER)
31        self.tcErrA = wx.TextCtrl(panel, -1,size=(120,20),style=wx.SIMPLE_BORDER)
32        self.tcB = wx.TextCtrl(panel, -1,size=(120,20),style=wx.SIMPLE_BORDER)
33        self.tcErrB = wx.TextCtrl(panel, -1,size=(120,20),style=wx.SIMPLE_BORDER)
34        self.tcChi = wx.TextCtrl(panel, -1,size=(120,20),style=wx.SIMPLE_BORDER)
35        self.tcXmin = wx.TextCtrl(panel,-1,size=(120,20),style=wx.SIMPLE_BORDER)
36        self.tcXmax = wx.TextCtrl(panel,-1,size=(120,20),style=wx.SIMPLE_BORDER)
37        self.btFit =wx.Button(panel,-1,'Fit',size=(120, 30))
38        self.btClose =wx.Button(panel, wx.ID_CANCEL,'Close',size=(90, 30) )
39        self.static_line_1 = wx.StaticLine(panel, -1)
40        ix = 0
41        iy = 1
42       
43        sizer.Add(wx.StaticText(panel, -1, 'y = Ax +B'),(iy, ix),(1,1),\
44                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
45       
46        iy+=1
47        sizer.Add(wx.StaticText(panel, -1, 'Param A'),(iy, ix),\
48                 (1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
49        ix += 1
50        sizer.Add(self.tcA,(iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
51        ix += 1
52        sizer.Add(wx.StaticText(panel, -1, '+/-'),(iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
53        ix += 1
54        sizer.Add(self.tcErrA, (iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
55       
56        iy += 1
57        ix = 0
58        sizer.Add(wx.StaticText(panel, -1, 'Param B'),(iy, ix),(1,1),\
59                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
60        ix += 1
61        sizer.Add(self.tcB, (iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
62        ix += 1
63        sizer.Add(wx.StaticText(panel, -1, '+/-'),(iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
64        ix += 1
65        sizer.Add(self.tcErrB, (iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
66        iy += 1
67        ix = 0
68        sizer.Add(wx.StaticText(panel, -1, 'Chi ^{2}'),(iy, ix),(1,1),\
69                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
70        ix += 1
71        sizer.Add(self.tcChi, (iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
72        iy += 1
73        ix = 1
74        sizer.Add(wx.StaticText(panel, -1, 'Xmin'),(iy, ix),(1,1),\
75                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
76        ix += 2
77        sizer.Add(wx.StaticText(panel, -1, 'Xmax'),(iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
78        iy += 1
79        ix = 1
80        sizer.Add(self.tcXmin, (iy, ix),(1,1),\
81                   wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
82        ix += 2
83        sizer.Add(self.tcXmax, (iy, ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0)
84        iy += 1
85        ix = 1
86       
87        sizer.Add(self.btFit, (iy, ix),(1,1), wx.LEFT|wx.ADJUST_MINSIZE, 0)
88        self.btFit.Bind(wx.EVT_BUTTON, self._onFit)
89        ix += 2
90        sizer.Add(self.btClose, (iy, ix),(1,1),\
91                  wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 0)
92       
93       
94        panel.SetSizer(sizer)
95        self.SetSizer(vbox)
96        self.Centre()
97        # Receives the type of model for the fitting
98        from LineModel import LineModel
99        self.model  = LineModel()
100         
101         
102        #Display the fittings values
103        self.default_A = self.model.getParam('A') 
104        self.default_B = self.model.getParam('B') 
105        self.cstA = fittings.Parameter(self.model, 'A', self.default_A)
106        self.cstB  = fittings.Parameter(self.model, 'B', self.default_B)
107       
108        # Set default value of parameter in fit dialog
109        self.tcA.SetLabel(str(self.default_A))
110        self.tcB.SetLabel(str(self.default_B))
111        self.tcErrA.SetLabel(str(0.0))
112        self.tcErrB.SetLabel(str(0.0))
113        self.tcChi.SetLabel(str(0.0))
114       
115       
116       
117        # new data for the fit
118        self.file_data1 = Theory1D(x=[], y=[], dy=None)
119        self.file_data1.name = "Fit"
120       
121    def _onFit(self ,event):
122        """
123            Performs the fit. Receive an event when clicking on the button Fit.Computes chisqr ,
124            A and B parameters of the best linear fit y=Ax +B
125            Push a plottable to
126        """
127       
128        tempx=[]
129        tempy=[]
130        tempdy = []
131       
132        #Check if the field of Fit Dialog contain values and use the x max and min of the user
133        xmin = self._checkVal(self.tcXmin.GetValue())
134        xmax = self._checkVal(self.tcXmax.GetValue())
135       
136        #store the values of View in x,y, dx,dy
137        x,y,dx,dy=self.plottable.returnValuesOfView()
138        # Receive transformations of x and y
139        self.xtrans,self.ytrans= self.transform()
140       
141        # Check if View contains a x array .we online fit when x exits
142        # makes transformation for y as a line to fit
143        if x != []:               
144            if (xmin ==None)and (xmax == None):
145                #Display the min and the max of x on fit dialog fields
146                self.tcXmin.SetValue(str(min(x)))
147                self.tcXmax.SetValue(str(max(x)))
148         
149           
150            # Store the transformed values of view x, y,dy in variables  before the fit
151            if  self.ytrans == "Log(y)":
152                for y_i in y:
153                    tempy.append(math.log(y_i)) 
154            else:
155                tempy = y
156               
157            for y_i in y:
158                dy = 1/y_i
159                if dy >= y_i:
160                    dy = 0.9*y_i
161                tempdy.append(dy)
162                   
163           
164            if  self.xtrans == "Log(x)":
165                for x_i in x:
166                    tempx.append(math.log(x_i)) 
167            else:
168                tempx = x
169               
170            #Find the fitting parameters
171            if (xmin !=None and xmin >= min(tempx) ) and (xmax !=None and xmax <= max(tempx)):   
172                chisqr, out, cov = fittings.sansfit(self.model, 
173                            [self.cstA, self.cstB],tempx, tempy,tempdy,xmin,xmax)
174            else:
175                chisqr, out, cov = fittings.sansfit(self.model, 
176                            [self.cstA, self.cstB],tempx, tempy,tempdy,min(tempx),max(tempx))
177           
178            #Check that cov and out are iterable before displaying them
179            if cov ==None:
180                errA =0.0
181                errB =0.0
182            else:
183                errA= math.sqrt(cov[0][0])
184                errB= math.sqrt(cov[1][1])
185            if out==None:
186                cstA=0.0
187                cstB=0.0
188            else:
189                cstA=out[0]
190                cstB=out[1]
191            # Reset model with the right values of A and B
192            self.model.setParam('A', float(cstA))
193            self.model.setParam('B', float(cstB))
194            tempy = []
195            y_model = 0.0
196           
197            for j in range(len(x)): 
198                    if (xmin !=None)and (xmax != None):
199                        if (x[j] > xmin and x[j] < xmax):
200                            y_model = self.model.run(x[j])
201                    else:
202                        # x has a default value in case the user doesn't load data
203                        if self.xtrans == "Log(x)":
204                            y_model = self.model.run(math.log(x[j]))
205                        else:
206                            y_model = self.model.run(x[j])
207                   
208                    if self.ytrans == "Log(y)":
209                        tempy.append(math.exp(y_model))
210                    else:
211                        tempy.append(y_model)
212                       
213            # Create new data plottable with result
214            self.file_data1.x =x
215            self.file_data1.y =[] 
216            self.file_data1.y =tempy     
217            self.file_data1.dx=None
218            self.file_data1.dy=None
219           
220            #Load the view with the new values
221            self.file_data1.reset_view()
222           
223            #Send the data to display to the PlotPanel
224            self.push_data(self.file_data1)
225           
226            # Display the fitting value on the Fit Dialog
227            self._onsetValues(cstA, cstB, errA,errB,chisqr)
228   
229    def _onsetValues(self,cstA,cstB,errA,errB,Chi):
230         """
231              Display  the value on fit Dialog
232         """
233         self.tcA.SetValue(str(cstA))
234         self.tcB.SetValue(str(cstB))
235         self.tcErrA.SetValue(str(errA))
236         self.tcErrB.SetValue(str(errB))
237         self.tcChi.SetValue(str(Chi))
238         
239    def _returnPlottable(self):
240        return self.file_data1
241   
242    def _checkVal(self,value):
243        """
244                Ensure that fields parameter contains a value
245                before sending to fit in Plotter1D
246        """
247        try:
248            param = float(value)
249        except:
250            param = None
251        return param
252   
253if __name__ == "__main__": 
254    app = wx.App()
255    dialog=LinearFit(None, -1, 'Fitting')
256    dialog.ShowModal()
257    app.MainLoop()
258
259
Note: See TracBrowser for help on using the repository browser.