- Timestamp:
- Feb 28, 2011 4:04:10 PM (14 years ago)
- Branches:
- master, ESS_GUI, ESS_GUI_Docs, ESS_GUI_batch_fitting, ESS_GUI_bumps_abstraction, ESS_GUI_iss1116, ESS_GUI_iss879, ESS_GUI_iss959, ESS_GUI_opencl, ESS_GUI_ordering, ESS_GUI_sync_sascalc, costrafo411, magnetic_scatt, release-4.1.1, release-4.1.2, release-4.2.2, release_4.0.1, ticket-1009, ticket-1094-headless, ticket-1242-2d-resolution, ticket-1243, ticket-1249, ticket885, unittest-saveload
- Children:
- a07e72f
- Parents:
- 1584fff
- Location:
- sansview/perspectives/fitting
- Files:
-
- 9 edited
Legend:
- Unmodified
- Added
- Removed
-
sansview/perspectives/fitting/basepage.py
r01b6bd0 r6bbeacd4 21 21 22 22 _BOX_WIDTH = 76 23 _QMIN_DEFAULT = 0.00 124 _QMAX_DEFAULT = 0. 1323 _QMIN_DEFAULT = 0.0005 24 _QMAX_DEFAULT = 0.5 25 25 _NPTS_DEFAULT = 50 26 26 #Control panel width … … 33 33 FONT_VARIANT = 1 34 34 ON_MAC = True 35 35 36 37 36 38 class BasicPage(ScrolledPanel, PanelBase): 37 39 """ … … 39 41 """ 40 42 ## Internal name for the AUI manager 41 window_name = " BasicPage"43 window_name = "Fit Page" 42 44 ## Title to appear on top of the window 43 window_caption = " Basic page "44 45 def __init__(self, parent, page_info, **kwargs):45 window_caption = "Fit Page " 46 47 def __init__(self, parent,color='blue', **kwargs): 46 48 """ 47 49 """ … … 51 53 #Set window's font size 52 54 self.SetWindowVariant(variant=FONT_VARIANT) 53 55 56 self.SetBackgroundColour(color) 54 57 ## parent of the page 55 58 self.parent = parent … … 62 65 self.data = None 63 66 self.mask = None 67 self.id = None 64 68 ## Q range 65 self.qmax_x = None66 self.qmin_x = None67 self.n um_points= _NPTS_DEFAULT69 self.qmax_x = _QMAX_DEFAULT 70 self.qmin_x = _QMIN_DEFAULT 71 self.npts_x = _NPTS_DEFAULT 68 72 ## total number of point: float 69 73 self.npts = None … … 86 90 self.state = PageState(parent=parent) 87 91 ## dictionary containing list of models 88 self.model_list_box = None89 self.set_page_info(page_info=page_info)92 self.model_list_box = {} 93 90 94 ## Data member to store the dispersion object created 91 95 self._disp_obj_dict = {} … … 136 140 ## Create context menu for page 137 141 self.popUpMenu = wx.Menu() 138 #id = wx.NewId() 139 #self._undo = wx.MenuItem(self.popUpMenu,id, "Undo", 140 #"cancel the previous action") 141 #self.popUpMenu.AppendItem(self._undo) 142 #self._undo.Enable(False) 143 #wx.EVT_MENU(self, id, self.onUndo) 144 145 #id = wx.NewId() 146 #self._redo = wx.MenuItem(self.popUpMenu,id,"Redo", 147 #" Restore the previous action") 148 #self.popUpMenu.AppendItem(self._redo) 149 #self._redo.Enable(False) 150 #wx.EVT_MENU(self, id, self.onRedo) 151 #self.popUpMenu.AppendSeparator() 152 #if sys.platform.count("win32")>0: 142 153 143 id = wx.NewId() 154 144 self._keep = wx.MenuItem(self.popUpMenu,id,"BookMark", … … 174 164 ## layout 175 165 self.set_layout() 166 167 176 168 177 169 def on_set_focus(self, event): … … 305 297 Cancel the previous action 306 298 """ 307 #print "enable undo"308 299 event = PreviousStateEvent(page = self) 309 300 wx.PostEvent(self.parent, event) … … 313 304 Restore the previous action cancelled 314 305 """ 315 #print "enable redo"316 306 event = NextStateEvent(page= self) 317 307 wx.PostEvent(self.parent, event) … … 394 384 self.model_list_box = dict 395 385 self.state.model_list_box = self.model_list_box 386 self.initialize_combox() 396 387 397 388 def initialize_combox(self): … … 1254 1245 Reset the plotting range to a given state 1255 1246 """ 1256 if self.check_invalid_panel():1257 return1258 self.qmin .SetValue(str(state.qmin))1247 # if self.check_invalid_panel(): 1248 # return 1249 self.qmin_tctrl.SetValue(str(state.qmin)) 1259 1250 self.qmax.SetValue(str(state.qmax)) 1260 1251 … … 1281 1272 self.state.qmin = self.qmin_x 1282 1273 self.state.qmax = self.qmax_x 1283 if self.npts != None: 1284 self.state.npts = self.num_points 1274 self.state.npts = self.npts_x 1285 1275 1286 1276 def _onparamEnter_helper(self): … … 1312 1302 # If qmin and qmax have been modified, update qmin and qmax and 1313 1303 # set the is_modified flag to True 1314 if self._validate_qrange(self.qmin , self.qmax):1315 tempmin = float(self.qmin .GetValue())1304 if self._validate_qrange(self.qmin_tcrl, self.qmax): 1305 tempmin = float(self.qmin_tcrl.GetValue()) 1316 1306 if tempmin != self.qmin_x: 1317 1307 self.qmin_x = tempmin … … 1367 1357 # If qmin and qmax have been modified, update qmin and qmax and 1368 1358 # set the is_modified flag to True 1369 self.fitrange = self._validate_qrange(self.qmin , self.qmax)1359 self.fitrange = self._validate_qrange(self.qmin_tcrl, self.qmax) 1370 1360 if self.fitrange: 1371 tempmin = float(self.qmin .GetValue())1361 tempmin = float(self.qmin_tcrl.GetValue()) 1372 1362 if tempmin != self.qmin_x: 1373 1363 self.qmin_x = tempmin … … 1385 1375 flag = self.update_pinhole_smear() 1386 1376 else: 1387 self._manager.set_smearer_nodraw(smearer=temp_smearer, 1377 self._manager.set_smearer(smearer=temp_smearer, 1378 id=self.id, 1388 1379 qmin=float(self.qmin_x), 1389 qmax=float(self.qmax_x)) 1380 qmax=float(self.qmax_x), 1381 draw=False) 1390 1382 elif not self._is_2D(): 1391 1383 self._manager.set_smearer(smearer=temp_smearer, 1392 1384 qmin=float(self.qmin_x), 1385 id=self.id, 1393 1386 qmax= float(self.qmax_x)) 1394 1387 index_data = ((self.qmin_x <= self.data.x)&\ … … 1646 1639 to build a call to the fitting perspective manager. 1647 1640 """ 1648 if self.check_invalid_panel():1649 return1641 #if self.check_invalid_panel(): 1642 # return 1650 1643 if self.model !=None: 1651 1644 temp_smear=None … … 1653 1646 if not self.disable_smearer.GetValue(): 1654 1647 temp_smear= self.current_smearer 1655 1656 1648 self._manager.draw_model(self.model, 1657 1649 data=self.data, … … 1659 1651 qmin=float(self.qmin_x), 1660 1652 qmax=float(self.qmax_x), 1661 qstep= float(self.num_points), 1653 qstep= float(self.npts_x), 1654 id=self.id, 1662 1655 enable2D=self.enable2D) 1663 1656 … … 1843 1836 Show combox box associate with type of model selected 1844 1837 """ 1845 if self.check_invalid_panel():1846 self.shape_rbutton.SetValue(True)1847 return1838 #if self.check_invalid_panel(): 1839 # self.shape_rbutton.SetValue(True) 1840 # return 1848 1841 1849 1842 self._show_combox_helper() … … 1871 1864 combobox.Append(name,models) 1872 1865 return 0 1873 1866 1874 1867 def _onQrangeEnter(self, event): 1868 """ 1869 Check validity of value enter in the Q range field 1870 1871 """ 1872 tcrtl = event.GetEventObject() 1873 #Clear msg if previously shown. 1874 msg = "" 1875 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1876 # Flag to register when a parameter has changed. 1877 is_modified = False 1878 if tcrtl.GetValue().lstrip().rstrip() != "": 1879 try: 1880 value = float(tcrtl.GetValue()) 1881 tcrtl.SetBackgroundColour(wx.WHITE) 1882 # If qmin and qmax have been modified, update qmin and qmax 1883 if self._validate_qrange(self.qmin_tcrl, self.qmax): 1884 tempmin = float(self.qmin_tcrl.GetValue()) 1885 if tempmin != self.qmin_x: 1886 self.qmin_x = tempmin 1887 tempmax = float(self.qmax.GetValue()) 1888 if tempmax != self.qmax_x: 1889 self.qmax_x = tempmax 1890 else: 1891 tcrtl.SetBackgroundColour("pink") 1892 msg = "Model Error:wrong value entered : %s" % sys.exc_value 1893 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1894 return 1895 except: 1896 tcrtl.SetBackgroundColour("pink") 1897 msg = "Model Error:wrong value entered : %s" % sys.exc_value 1898 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1899 return 1900 #Check if # of points for theory model are valid(>0). 1901 if self.npts != None: 1902 if check_float(self.npts): 1903 temp_npts = float(self.npts.GetValue()) 1904 if temp_npts != self.num_points: 1905 self.num_points = temp_npts 1906 is_modified = True 1907 else: 1908 msg = "Cannot Plot :No npts in that Qrange!!! " 1909 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1910 else: 1911 tcrtl.SetBackgroundColour("pink") 1912 msg = "Model Error:wrong value entered!!!" 1913 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1914 #self._undo.Enable(True) 1915 self.save_current_state() 1916 event = PageInfoEvent(page=self) 1917 wx.PostEvent(self.parent, event) 1918 self.state_change = False 1919 #Draw the model for a different range 1920 self._draw_model() 1921 1922 def _theory_qrange_enter(self, event): 1875 1923 """ 1876 1924 Check validity of value enter in the Q range field … … 1889 1937 1890 1938 # If qmin and qmax have been modified, update qmin and qmax 1891 if self._validate_qrange( self.qmin, self.qmax):1892 tempmin = float(self. qmin.GetValue())1893 if tempmin != self. qmin_x:1894 self. qmin_x = tempmin1895 tempmax = float(self. qmax.GetValue())1939 if self._validate_qrange(self.theory_qmin, self.theory_qmax): 1940 tempmin = float(self.theory_qmin.GetValue()) 1941 if tempmin != self.theory_qmin_x: 1942 self.theory_qmin_x = tempmin 1943 tempmax = float(self.theory_qmax.GetValue()) 1896 1944 if tempmax != self.qmax_x: 1897 self. qmax_x = tempmax1945 self.theory_qmax_x = tempmax 1898 1946 else: 1899 1947 tcrtl.SetBackgroundColour("pink") 1900 1948 msg= "Model Error:wrong value entered : %s"% sys.exc_value 1901 wx.PostEvent(self. parent.parent, StatusEvent(status = msg ))1949 wx.PostEvent(self._manager.parent, StatusEvent(status = msg )) 1902 1950 return 1903 1951 except: 1904 1952 tcrtl.SetBackgroundColour("pink") 1905 1953 msg= "Model Error:wrong value entered : %s"% sys.exc_value 1906 wx.PostEvent(self. parent.parent, StatusEvent(status = msg ))1954 wx.PostEvent(self._manager.parent, StatusEvent(status = msg )) 1907 1955 return 1908 1956 #Check if # of points for theory model are valid(>0). 1909 if self. npts != None:1910 if check_float(self. npts):1911 temp_npts = float(self. npts.GetValue())1957 if self.theory_npts != None: 1958 if check_float(self.theory_npts): 1959 temp_npts = float(self.theory_npts.GetValue()) 1912 1960 if temp_npts != self.num_points: 1913 1961 self.num_points = temp_npts … … 1918 1966 else: 1919 1967 tcrtl.SetBackgroundColour("pink") 1920 msg = "Model Error:wrong value entered!!!"1968 msg = "Model Error:wrong value entered!!!" 1921 1969 wx.PostEvent(self.parent.parent, StatusEvent(status=msg)) 1922 1970 #self._undo.Enable(True) … … 2068 2116 self.data.qy_data * self.data.qy_data ) 2069 2117 #get unmasked index 2070 index_data = (float(self.qmin .GetValue()) <= radius) & \2118 index_data = (float(self.qmin_tcrl.GetValue()) <= radius) & \ 2071 2119 (radius <= float(self.qmax.GetValue())) 2072 2120 index_data = (index_data) & (self.data.mask) … … 2075 2123 if len(index_data[index_data]) < 10: 2076 2124 # change the color pink. 2077 self.qmin .SetBackgroundColour("pink")2078 self.qmin .Refresh()2125 self.qmin_tcrl.SetBackgroundColour("pink") 2126 self.qmin_tcrl.Refresh() 2079 2127 self.qmax.SetBackgroundColour("pink") 2080 2128 self.qmax.Refresh() … … 2188 2236 Redraw the model with the default dispersity (Gaussian) 2189 2237 """ 2190 if self.check_invalid_panel():2191 return2238 #if self.check_invalid_panel(): 2239 # return 2192 2240 ## On selction if no model exists. 2193 2241 if self.model ==None: … … 2412 2460 event = PageInfoEvent(page = self) 2413 2461 wx.PostEvent(self.parent, event) 2414 2415 def _set_range_sizer(self, title, box_sizer=None, object1=None,object=None): 2416 """ 2417 Fill the Q range sizer 2418 """ 2419 #2D data? default 2420 is_2Ddata = False 2421 2422 #check if it is 2D data 2423 if self.data.__class__.__name__ == 'Data2D': 2424 is_2Ddata = True 2425 2426 self.sizer5.Clear(True) 2427 #-------------------------------------------------------------- 2428 if box_sizer == None: 2429 box_description= wx.StaticBox(self, -1,str(title)) 2430 boxsizer1 = wx.StaticBoxSizer(box_description, wx.VERTICAL) 2431 else: 2432 #for MAC 2433 boxsizer1 = box_sizer 2434 2435 self.qmin = self.ModelTextCtrl(self, -1,size=(_BOX_WIDTH,20),style=wx.TE_PROCESS_ENTER, 2436 text_enter_callback = self._onQrangeEnter) 2437 self.qmin.SetValue(str(self.qmin_x)) 2438 self.qmin.SetToolTipString("Minimun value of Q in linear scale.") 2439 2440 self.qmax = self.ModelTextCtrl(self, -1,size=(_BOX_WIDTH,20),style=wx.TE_PROCESS_ENTER, 2441 text_enter_callback = self._onQrangeEnter) 2442 self.qmax.SetValue(str(self.qmax_x)) 2443 self.qmax.SetToolTipString("Maximum value of Q in linear scale.") 2444 2445 id = wx.NewId() 2446 self.reset_qrange =wx.Button(self,id,'Reset',size=(77,20)) 2447 2448 self.reset_qrange.Bind(wx.EVT_BUTTON, self.on_reset_clicked,id=id) 2449 self.reset_qrange.SetToolTipString("Reset Q range to the default values") 2450 2451 sizer_horizontal=wx.BoxSizer(wx.HORIZONTAL) 2452 sizer= wx.GridSizer(2, 4,2, 6) 2453 2454 self.btEditMask = wx.Button(self,wx.NewId(),'Editor', size=(88,23)) 2455 self.btEditMask.Bind(wx.EVT_BUTTON, self._onMask,id= self.btEditMask.GetId()) 2456 self.btEditMask.SetToolTipString("Edit Mask.") 2457 self.EditMask_title = wx.StaticText(self, -1, ' Masking(2D)') 2458 2459 sizer.Add(wx.StaticText(self, -1, ' Q range')) 2460 sizer.Add(wx.StaticText(self, -1, ' Min[1/A]')) 2461 sizer.Add(wx.StaticText(self, -1, ' Max[1/A]')) 2462 sizer.Add(self.EditMask_title) 2463 sizer.Add(self.reset_qrange) 2464 2465 sizer.Add(self.qmin) 2466 sizer.Add(self.qmax) 2467 sizer.Add(self.btEditMask) 2468 2469 if object1!=None: 2470 2471 boxsizer1.Add(object1) 2472 boxsizer1.Add((10,10)) 2473 boxsizer1.Add(sizer) 2474 if object!=None: 2475 boxsizer1.Add((10,15)) 2476 boxsizer1.Add(object) 2477 if is_2Ddata: 2478 self.btEditMask.Enable() 2479 self.EditMask_title.Enable() 2480 else: 2481 self.btEditMask.Disable() 2482 self.EditMask_title.Disable() 2483 ## save state 2484 self.save_current_state() 2485 #---------------------------------------------------------------- 2486 self.sizer5.Add(boxsizer1,0, wx.EXPAND | wx.ALL, 10) 2487 self.sizer5.Layout() 2488 2462 2489 2463 def _lay_out(self): 2490 2464 """ … … 2511 2485 """ 2512 2486 flag = True 2513 if self.check_invalid_panel():2514 return2487 #if self.check_invalid_panel(): 2488 # return 2515 2489 ##For 3 different cases: Data2D, Data1D, and theory 2516 2490 if self.data.__class__.__name__ == "Data2D": … … 2552 2526 else: 2553 2527 # set relative text ctrs. 2554 self.qmin .SetValue(str(self.qmin_x))2528 self.qmin_tcrl.SetValue(str(self.qmin_x)) 2555 2529 self.qmax.SetValue(str(self.qmax_x)) 2556 2530 self.set_npts2fit() … … 2569 2543 self._draw_model() 2570 2544 2571 2572 2545 def on_model_help_clicked(self,event): 2573 2546 """ … … 2575 2548 """ 2576 2549 from help_panel import HelpWindow 2577 import sans.models as models 2578 2579 # Get models help model_function path 2580 path = models.get_data_path(media='media') 2581 model_path = os.path.join(path,"model_functions.html") 2550 2582 2551 if self.model == None: 2583 2552 name = 'FuncHelp' … … 2585 2554 name = self.model.origin_name 2586 2555 2587 frame = HelpWindow(None, -1, pageToOpen= model_path)2556 frame = HelpWindow(None, -1, pageToOpen="media/model_functions.html") 2588 2557 frame.Show(True) 2589 2558 if frame.rhelp.HasAnchor(name): … … 2592 2561 msg= "Model does not contains an available description " 2593 2562 msg +="Please try searching in the Help window" 2594 wx.PostEvent(self.parent.parent, StatusEvent(status = msg )) 2595 2563 wx.PostEvent(self.parent.parent, StatusEvent(status = msg )) 2596 2564 -
sansview/perspectives/fitting/fit_thread.py
r5062bbf r6bbeacd4 10 10 handler, 11 11 pars=None, 12 cpage=None,13 12 completefn = None, 14 13 updatefn = None, … … 23 22 self.handler = handler 24 23 self.fitter = fn 25 self.cpage= cpage26 24 self.pars = pars 27 25 self.starttime = 0 … … 49 47 self.updatefn() 50 48 self.complete(result= result, 51 pars = self.pars, 52 cpage= self.cpage) 49 pars = self.pars) 53 50 54 51 except KeyboardInterrupt, msg: -
sansview/perspectives/fitting/fitpage.py
r2b0f822 r6bbeacd4 38 38 """ 39 39 40 def __init__(self,parent, page_info):40 def __init__(self,parent, color='rand'): 41 41 """ 42 42 Initialization of the Panel 43 43 """ 44 BasicPage.__init__(self, parent, page_info)44 BasicPage.__init__(self, parent, color=color) 45 45 46 46 ## draw sizer … … 51 51 self._get_defult_custom_smear() 52 52 self._fill_range_sizer() 53 54 if self.data is None: 55 self.formfactorbox.Disable() 56 self.structurebox.Disable() 57 else: 58 self.smearer = smear_selection(self.data, self.model) 59 if self.smearer ==None: 60 self.enable_smearer.Disable() 53 self._set_smear(self.data) 61 54 ## to update the panel according to the fit engine type selected 62 55 self.Bind(EVT_FITTER_TYPE,self._on_engine_change) … … 158 151 self.Layout() 159 152 self.Refresh() 160 153 154 155 161 156 def _fill_range_sizer(self): 162 157 """ … … 267 262 self.Npts_total.SetToolTipString(" Total Npts : total number of data points") 268 263 box_description_1= wx.StaticText(self, -1,' Chi2/Npts') 269 box_description_2= wx.StaticText(self, -1,' 270 box_description_3= wx.StaticText(self, -1,' TotalNpts')264 box_description_2= wx.StaticText(self, -1,'Fitted Npts') 265 box_description_3= wx.StaticText(self, -1,'Data Npts') 271 266 box_description_4= wx.StaticText(self, -1,' ') 272 267 … … 357 352 else: self._show_smear_sizer() 358 353 boxsizer_range.Add(self.sizer_set_masking) 359 360 #Set sizer for Fitting section 361 self._set_range_sizer( title=title,box_sizer=boxsizer_range, object1=sizer_chi2, object= sizer_fit) 362 354 #2D data? default 355 is_2Ddata = False 356 357 #check if it is 2D data 358 if self.data.__class__.__name__ == 'Data2D': 359 is_2Ddata = True 360 361 self.sizer5.Clear(True) 362 363 self.qmin_tcrl = self.ModelTextCtrl(self, -1,size=(_BOX_WIDTH,20), 364 style=wx.TE_PROCESS_ENTER, 365 text_enter_callback = self._onQrangeEnter) 366 self.qmin_tcrl.SetValue(str(self.qmin_x)) 367 self.qmin_tcrl.SetToolTipString("Minimun value of Q in linear scale.") 368 369 self.qmax = self.ModelTextCtrl(self, -1,size=(_BOX_WIDTH,20), 370 style=wx.TE_PROCESS_ENTER, 371 text_enter_callback=self._onQrangeEnter) 372 self.qmax.SetValue(str(self.qmax_x)) 373 self.qmax.SetToolTipString("Maximum value of Q in linear scale.") 374 375 self.theory_npts_tcrtl = self.ModelTextCtrl(self, -1, size=(_BOX_WIDTH, 20), 376 style=wx.TE_PROCESS_ENTER, 377 text_enter_callback=self._onQrangeEnter) 378 self.theory_npts_tcrtl.SetValue(format_number(self.npts_x)) 379 self.theory_npts_tcrtl.SetToolTipString("Number of point to plot.") 380 id = wx.NewId() 381 self.reset_qrange =wx.Button(self,id,'Reset',size=(77,20)) 382 383 self.reset_qrange.Bind(wx.EVT_BUTTON, self.on_reset_clicked,id=id) 384 self.reset_qrange.SetToolTipString("Reset Q range to the default values") 385 386 sizer_horizontal=wx.BoxSizer(wx.HORIZONTAL) 387 sizer= wx.GridSizer(2, 5,0, 0) 388 389 self.btEditMask = wx.Button(self,wx.NewId(),'Editor', size=(88,23)) 390 self.btEditMask.Bind(wx.EVT_BUTTON, self._onMask,id= self.btEditMask.GetId()) 391 self.btEditMask.SetToolTipString("Edit Mask.") 392 self.EditMask_title = wx.StaticText(self, -1, ' Masking(2D)') 393 394 sizer.Add(wx.StaticText(self, -1, 'Q range')) 395 sizer.Add(wx.StaticText(self, -1, ' Min[1/A]')) 396 sizer.Add(wx.StaticText(self, -1, ' Max[1/A]')) 397 sizer.Add(wx.StaticText(self, -1, ' Theory Npts')) 398 sizer.Add(self.EditMask_title) 399 sizer.Add(self.reset_qrange) 400 sizer.Add(self.qmin_tcrl) 401 sizer.Add(self.qmax) 402 sizer.Add(self.theory_npts_tcrtl) 403 sizer.Add(self.btEditMask) 404 boxsizer_range.Add(sizer_chi2) 405 boxsizer_range.Add((10,10)) 406 boxsizer_range.Add(sizer) 407 408 boxsizer_range.Add((10,15)) 409 boxsizer_range.Add(sizer_fit) 410 if is_2Ddata: 411 self.btEditMask.Enable() 412 self.EditMask_title.Enable() 413 else: 414 self.btEditMask.Disable() 415 self.EditMask_title.Disable() 416 ## save state 417 self.save_current_state() 418 self.sizer5.Add(boxsizer_range,0, wx.EXPAND | wx.ALL, 10) 419 self.sizer5.Layout() 420 363 421 def _fill_datainfo_sizer(self): 364 422 """ … … 385 443 ## Maximum value of data 386 444 data_max = math.sqrt(x*x + y*y) 387 445 ## set q range to plot 446 self.qmin_x = data_min 447 self.qmax_x = data_max 388 448 box_description= wx.StaticBox(self, -1, 'Data') 389 449 boxsizer1 = wx.StaticBoxSizer(box_description, wx.VERTICAL) … … 416 476 sizer_range.Add(self.maximum_q,0, wx.LEFT, 10) 417 477 418 ## set q range to plot 419 self.qmin_x = data_min 420 self.qmax_x = data_max 478 421 479 422 480 boxsizer1.Add(sizer_data,0, wx.ALL, 10) … … 800 858 """ 801 859 #make sure all parameter values are updated. 802 if self.check_invalid_panel():803 return860 #if self.check_invalid_panel(): 861 # return 804 862 if self.model ==None: 805 863 msg="Please select a Model first..." … … 828 886 # Remove or do not allow fitting on the Q=0 point, especially 829 887 # when y(q=0)=None at x[0]. 830 self.qmin_x = float(self.qmin .GetValue())888 self.qmin_x = float(self.qmin_tcrl.GetValue()) 831 889 self.qmax_x = float( self.qmax.GetValue()) 832 self._manager._reset_schedule_problem( value=0)833 self._manager.schedule_for_fit( 834 self._manager.set_fit_range( page= self,qmin= self.qmin_x,890 self._manager._reset_schedule_problem(id=self.id, value=0) 891 self._manager.schedule_for_fit(id=id,value=1,page=self,fitproblem =None) 892 self._manager.set_fit_range(id=self.id,qmin= self.qmin_x, 835 893 qmax= self.qmax_x) 836 894 … … 889 947 self._set_save_flag(True) 890 948 # Reset smearer, model and data 891 self.set_data(self.data) 892 # update smearer sizer 893 self.onSmear(None) 949 self._set_smear(self.data) 894 950 try: 951 # update smearer sizer 952 self.onSmear(None) 895 953 temp_smear = None 896 954 if self.enable_smearer.GetValue(): 897 955 # Set the smearer environments 898 temp_smear= self.smearer 899 #self.compute_chisqr(temp_smear) 956 temp_smear = self.smearer 900 957 except: 901 958 ## error occured on chisqr computation … … 903 960 ## event to post model to fit to fitting plugins 904 961 (ModelEventbox, EVT_MODEL_BOX) = wx.lib.newevent.NewEvent() 905 if self.data is not None and \ 906 self.data.__class__.__name__ !="Data2D": 907 ## set smearing value whether or not 908 # the data contain the smearing info 909 evt = ModelEventbox(model = self.model, 910 smearer = temp_smear, 911 qmin = float(self.qmin_x), 912 qmax = float(self.qmax_x)) 913 else: 914 evt = ModelEventbox(model = self.model) 915 916 self._manager._on_model_panel(evt = evt) 962 963 ## set smearing value whether or not 964 # the data contain the smearing info 965 evt = ModelEventbox(model=self.model, 966 smearer=temp_smear, 967 qmin=float(self.qmin_x), 968 id=self.id, 969 qmax=float(self.qmax_x)) 970 971 self._manager._on_model_panel(evt=evt) 917 972 self.state.model = self.model.clone() 918 973 self.state.model.name = self.model.name 919 974 if event is not None: 920 975 self._draw_model() 921 if event != None:922 #self._undo.Enable(True)976 if event != None: 977 923 978 ## post state to fit panel 924 979 event = PageInfoEvent(page = self) … … 965 1020 elif self.data.__class__.__name__ !="Data2D": 966 1021 self._manager.set_smearer(smearer=temp_smearer, 1022 id=self.id, 967 1023 qmin= float(self.qmin_x), 968 qmax= float(self.qmax_x)) 1024 qmax= float(self.qmax_x), 1025 draw=True) 969 1026 if flag: 970 1027 #self.compute_chisqr(smearer= temp_smearer) … … 992 1049 Check validity of value enter in the parameters range field 993 1050 """ 994 if self.check_invalid_panel():995 return1051 #if self.check_invalid_panel(): 1052 # return 996 1053 tcrtl= event.GetEventObject() 997 1054 #Clear msg if previously shown. … … 1025 1082 Check validity of value enter in the Q range field 1026 1083 """ 1027 if self.check_invalid_panel():1028 return1084 #if self.check_invalid_panel(): 1085 # return 1029 1086 tcrtl= event.GetEventObject() 1030 1087 #Clear msg if previously shown. … … 1039 1096 1040 1097 # If qmin and qmax have been modified, update qmin and qmax 1041 if self._validate_qrange( self.qmin , self.qmax):1042 tempmin = float(self.qmin .GetValue())1098 if self._validate_qrange( self.qmin_tcrl, self.qmax): 1099 tempmin = float(self.qmin_tcrl.GetValue()) 1043 1100 if tempmin != self.qmin_x: 1044 1101 self.qmin_x = tempmin … … 1077 1134 self.set_npts2fit() 1078 1135 else: 1079 index_data = ((self.qmin_x <= self.data.x)& \ 1080 (self.data.x <= self.qmax_x)) 1081 self.Npts_fit.SetValue(str(len(self.data.x[index_data]))) 1136 if self.data is not None: 1137 1138 index_data = ((self.qmin_x <= self.data.x)& \ 1139 (self.data.x <= self.qmax_x)) 1140 self.Npts_fit.SetValue(str(len(self.data.x[index_data]))) 1082 1141 1083 1142 … … 1373 1432 self.panel.ShowMessage(msg) 1374 1433 1434 def _set_smear(self, data): 1435 """ 1436 """ 1437 if data is None: 1438 return 1439 self.smearer = smear_selection(self.data, self.model) 1440 self.disable_smearer.SetValue(True) 1441 if self.smearer == None: 1442 self.enable_smearer.Disable() 1443 else: 1444 self.enable_smearer.Enable() 1445 1375 1446 def set_data(self, data): 1376 1447 """ 1377 1448 reset the current data 1378 1449 """ 1450 flag = False 1451 if self.data is None and data is not None: 1452 self.window_name = str(data.name) 1453 ## Title to appear on top of the window 1454 self.window_caption = str(data.name) 1455 flag = True 1379 1456 self.data = data 1380 1457 if self.data is None: … … 1382 1459 data_max = "" 1383 1460 data_name = "" 1384 self.formfactorbox.Disable()1385 self.structurebox.Disable()1386 1461 self._set_bookmark_flag(False) 1387 1462 self._set_save_flag(False) … … 1389 1464 self._set_bookmark_flag(True) 1390 1465 self._set_save_flag(True) 1391 self.smearer = smear_selection(self.data, self.model) 1392 self.disable_smearer.SetValue(True) 1393 if self.smearer == None: 1394 self.enable_smearer.Disable() 1395 else: 1396 self.enable_smearer.Enable() 1397 1466 self._set_smear(data) 1398 1467 # more disables for 2D 1399 1468 if self.data.__class__.__name__ =="Data2D": … … 1434 1503 self.minimum_q.SetValue(str(data_min)) 1435 1504 self.maximum_q.SetValue(str(data_max)) 1436 self.qmin .SetValue(str(data_min))1505 self.qmin_tcrl.SetValue(str(data_min)) 1437 1506 self.qmax.SetValue(str(data_max)) 1438 self.qmin .SetBackgroundColour("white")1507 self.qmin_tcrl.SetBackgroundColour("white") 1439 1508 self.qmax.SetBackgroundColour("white") 1440 1509 self.state.data = data 1441 1510 self.state.qmin = self.qmin_x 1442 1511 self.state.qmax = self.qmax_x 1512 #update model plot with new data information 1513 if flag: 1514 self._draw_model() 1443 1515 1444 1516 def reset_page(self, state,first=False): … … 1473 1545 1474 1546 """ 1547 if self.data is None: 1548 return 1475 1549 npts2fit = 0 1476 1550 qmin,qmax = self.get_range() … … 1653 1727 """ 1654 1728 1655 if self.check_invalid_panel():1656 return1729 #if self.check_invalid_panel(): 1730 # return 1657 1731 if self.model ==None: 1658 1732 self.disable_smearer.SetValue(True) … … 1799 1873 get_pin_max.SetBackgroundColour("white") 1800 1874 ## set smearing value whether or not the data contain the smearing info 1801 self._manager.set_smearer(smearer=self.current_smearer, qmin= \ 1802 float(self.qmin_x),qmax= float(self.qmax_x)) 1875 self._manager.set_smearer(smearer=self.current_smearer, 1876 qmin=float(self.qmin_x), 1877 qmax= float(self.qmax_x), 1878 id=self.id) 1803 1879 return msg 1804 1880 … … 1830 1906 """ 1831 1907 1832 if self.check_invalid_panel():1833 return1908 #if self.check_invalid_panel(): 1909 # return 1834 1910 1835 1911 if self.model ==None: … … 1969 2045 #temp_smearer = self.current_smearer 1970 2046 ## set smearing value whether or not the data contain the smearing info 1971 self._manager.set_smearer(smearer=self.current_smearer, qmin= \ 1972 float(self.qmin_x), qmax= float(self.qmax_x)) 2047 self._manager.set_smearer(smearer=self.current_smearer, 2048 qmin=float(self.qmin_x), 2049 qmax= float(self.qmax_x), 2050 id=self.id) 1973 2051 return msg 1974 2052 … … 2001 2079 if event != None: 2002 2080 event.Skip() 2003 if self. check_invalid_panel():2081 if self.data is None: 2004 2082 return 2083 2005 2084 if self.model == None: 2006 2085 self.disable_smearer.SetValue(True) … … 2013 2092 # Need update param values 2014 2093 self._update_paramv_on_fit() 2015 2094 2016 2095 temp_smearer = None 2017 2096 self._get_smear_info() … … 2054 2133 self.Layout() 2055 2134 ## set smearing value whether or not the data contain the smearing info 2056 self._manager.set_smearer( smearer=temp_smearer, qmin= float(self.qmin_x),2057 qmax= float(self.qmax_x))2058 2135 self._manager.set_smearer(id=self.id, smearer=temp_smearer, qmin= float(self.qmin_x), 2136 qmax= float(self.qmax_x), draw=True) 2137 2059 2138 ##Calculate chi2 2060 2139 #self.compute_chisqr(smearer= temp_smearer) -
sansview/perspectives/fitting/fitpanel.py
r90a7bbd r6bbeacd4 3 3 import string 4 4 import wx 5 import wx. aui5 import wx.lib.flatnotebook as fnb 6 6 7 7 from sans.guiframe.panel_base import PanelBase 8 8 from sans.guiframe.events import PanelOnFocusEvent 9 from sans.guiframe.events import StatusEvent 9 10 import basepage 10 11 import models 11 12 _BOX_WIDTH = 80 12 13 13 14 14 class PageInfo(object): 15 """ 16 this class contains the minimum numbers of data members 17 a fitpage or model page need to be initialized. 18 """ 19 data = None 20 model = None 21 manager = None 22 event_owner= None 23 model_list_box = None 24 name = None 25 ## Internal name for the AUI manager 26 window_name = "Page" 27 ## Title to appear on top of the window 28 window_caption = "Page" 29 #type of page can be real data , theory 1D or therory2D 30 type = "Data" 31 def __init__(self, model=None, data=None, manager=None, 32 event_owner=None, model_list_box=None, name=None): 33 """ 34 Initialize data members 35 """ 36 self.data = data 37 self.model= model 38 self._manager= manager 39 self.event_owner= event_owner 40 self.model_list_box = model_list_box 41 self.name=None 42 self.window_name = "Page" 43 self.window_caption = "Page" 44 self.type = "Data" 45 46 class FitPanel(wx.aui.AuiNotebook, PanelBase): 15 class FitPanel(fnb.FlatNotebook, PanelBase): 47 16 48 17 """ … … 59 28 CENTER_PANE = True 60 29 61 def __init__(self, parent, *args, **kwargs):62 """ 63 """ 64 wx.aui.AuiNotebook.__init__(self, parent, -1,30 def __init__(self, parent, manager=None, *args, **kwargs): 31 """ 32 """ 33 fnb.FlatNotebook.__init__(self, parent, -1, 65 34 style= wx.aui.AUI_NB_WINDOWLIST_BUTTON| 66 35 wx.aui.AUI_NB_DEFAULT_STYLE| 67 36 wx.CLIP_CHILDREN) 68 37 PanelBase.__init__(self, parent) 69 70 self._manager = None38 self.SetWindowStyleFlag(style=fnb.FNB_FANCY_TABS) 39 self._manager = manager 71 40 self.parent = parent 72 41 self.event_owner = None 73 74 pageClosedEvent = wx.aui.EVT_AUINOTEBOOK_PAGE_CLOSE75 self.Bind(wx.aui.EVT_AUINOTEBOOK_PAGE_CLOSE, self.on_close_page)76 77 42 #dictionary of miodel {model class name, model class} 78 self.model_list_box = {} 79 ## save the title of the last page tab added 43 self.menu_mng = models.ModelManager() 44 self.model_list_box = self.menu_mng.get_model_list().get_list() 45 #pageClosedEvent = fnb.EVT_FLATNOTEBOOK_PAGE_CLOSING 46 self.Bind(fnb.EVT_FLATNOTEBOOK_PAGE_CLOSING , self.on_close_page) 47 ## save the title of the last page tab added 80 48 self.fit_page_name = {} 81 49 ## list of existing fit page … … 91 59 #add default pages 92 60 self.add_default_pages() 93 94 # increment number for model name 95 self.count = 0 96 #updating the panel 97 self.Update() 98 self.Center() 61 62 def get_page_by_id(self, id): 63 """ 64 """ 65 if id not in self.opened_pages: 66 msg = "Fitpanel cannot find ID: %s in self.opened_pages" % str(id) 67 raise ValueError, msg 68 else: 69 return self.opened_pages[id] 99 70 100 71 def on_page_changing(self, event): 72 """ 73 """ 101 74 pos = self.GetSelection() 102 75 if pos != -1: 103 76 selected_page = self.GetPage(pos) 104 77 wx.PostEvent(self.parent, PanelOnFocusEvent(panel=selected_page)) 78 105 79 def on_set_focus(self, event): 106 80 """ … … 136 110 from hint_fitpage import HintFitPage 137 111 self.hint_page = HintFitPage(self) 138 self.AddPage( page=self.hint_page, caption="Hint")112 self.AddPage(self.hint_page,"Hint") 139 113 self.hint_page.set_manager(self._manager) 140 #Add the first fit page 141 self.add_empty_page() 142 143 114 144 115 def close_all(self): 145 116 """ … … 170 141 page_is_opened = False 171 142 if state is not None: 172 page_info = self.get_page_info(data=state.data) 173 for name, panel in self.opened_pages.values(): 143 for id, panel in self.opened_pages.values(): 174 144 #Don't return any panel is the exact same page is created 175 if name == page_info.window_name:145 if id == panel.id: 176 146 # the page is still opened 177 147 panel.reset_page(state=state) … … 182 152 # add data associated to the page created 183 153 if panel is not None: 184 self._manager.store_page(page=panel , data=state.data)154 self._manager.store_page(page=panel.id, data=state.data) 185 155 panel.reset_page(state=state) 186 156 panel.save_current_state() … … 241 211 page.set_manager(self._manager) 242 212 243 244 def set_owner(self,owner):245 """246 set and owner for fitpanel247 248 :param owner: the class responsible of plotting249 250 """251 self.event_owner = owner252 253 213 def set_model_list(self, dict): 254 214 """ … … 265 225 266 226 """ 267 return self.GetPage(self.GetSelection() 227 return self.GetPage(self.GetSelection()) 268 228 269 229 def add_sim_page(self): … … 274 234 page_finder= self._manager.get_page_finder() 275 235 self.sim_page = SimultaneousFitPage(self,page_finder=page_finder, id=-1) 276 277 self.AddPage(self.sim_page, caption="Simultaneous Fit",select=True)236 self.sim_page.id = wx.NewId() 237 self.AddPage(self.sim_page,"Simultaneous Fit", True) 278 238 self.sim_page.set_manager(self._manager) 279 239 return self.sim_page 280 240 281 def get_page_info(self, data=None): 282 """ 283 fill information required to add a page in the fit panel 284 """ 285 name = "Fit Page" 286 type = 'empty' 287 if data is not None: 288 if data.is_data: 289 name = data.name 290 type = 'Data' 291 else: 292 if data.__class__.__name__ == "Data2D": 293 name = 'Model 2D Fit' 294 type = 'Theory2D' 295 else: 296 name = 'Model 1D Fit' 297 type = 'Theory1D' 298 page_info = PageInfo(data=data, name=name) 299 page_info.event_owner = self.event_owner 300 page_info.manager = self._manager 301 page_info.window_name = name 302 page_info.window_caption = name 303 page_info.type = type 304 return page_info 241 242 def add_empty_page(self): 243 """ 244 add an empty page 245 """ 246 from fitpage import FitPage 247 panel = FitPage(parent=self) 248 panel.id = wx.NewId() 249 panel.populate_box(dict=self.model_list_box) 250 panel.set_manager(self._manager) 251 self.AddPage(panel, panel.window_name, select=True) 252 self.opened_pages[panel.id] = panel 253 return panel 305 254 306 def add_empty_page(self): 307 """ 308 add an empty page 309 """ 310 page_info = self.get_page_info() 311 from fitpage import FitPage 312 panel = FitPage(parent=self, page_info=page_info) 313 panel.set_manager(self._manager) 314 self.AddPage(page=panel, caption=page_info.window_name, select=True) 315 self.opened_pages[page_info.type] = [page_info.window_name, panel] 316 return panel 317 318 def add_page(self, page_info): 319 """ 320 add a new page 321 """ 322 from fitpage import FitPage 323 panel = FitPage(parent=self, page_info=page_info) 324 panel.set_manager(self._manager) 325 self.AddPage(page=panel, caption=page_info.window_name, select=True) 326 index = self.GetPageIndex(panel) 327 self.change_page_content(data=page_info.data, index=index) 328 return panel 329 330 def change_page_content(self, data, index): 331 """ 332 replace the contains of an existing page 333 """ 334 page_info = self.get_page_info(data=data) 335 self.SetPageText(index, page_info.window_name) 336 panel = self.GetPage(index) 337 panel.set_data(data) 338 if panel.model_list_box is None or len(panel.model_list_box) == 0: 339 page_info.model_list_box = self.model_list_box.get_list() 340 panel.populate_box(dict=page_info.model_list_box) 341 panel.initialize_combox() 342 panel.set_page_info(page_info=page_info) 343 self.opened_pages[page_info.type] = [page_info.window_name, panel] 344 return panel 345 346 def replace_page(self, index, page_info, type): 347 """ 348 replace an existing page 349 """ 350 self.DeletePage(index) 351 del self.opened_pages[type] 352 return self.add_page(page_info=page_info) 353 354 def add_fit_page(self, data, reset=False): 255 256 def set_data(self, data): 355 257 """ 356 258 Add a fitting page on the notebook contained by fitpanel … … 363 265 if data is None: 364 266 return None 365 page_info = self.get_page_info(data=data) 366 type = page_info.type 367 npages = len(self.opened_pages.keys()) 368 #check if only and empty page is opened 369 if len(self.opened_pages.keys()) > 0: 370 first_page_type = self.opened_pages.keys()[0] 371 if npages == 1 and first_page_type in ['empty']: 372 #replace the first empty page 373 name, panel = self.opened_pages[first_page_type] 374 index = self.GetPageIndex(panel) 375 panel = self.change_page_content(data=data, index=index) 376 del self.opened_pages[first_page_type] 377 return panel 378 if type in self.opened_pages.keys(): 379 #this type of page is already created but it is a theory 380 # meaning the same page is just to fit different data 381 if not type.lower() in ['data']: 382 #delete the previous theory page and add a new one 383 name, panel = self.opened_pages[type] 384 #self._manager.reset_plot_panel(panel.get_data()) 385 #delete the existing page and replace it 386 index = self.GetPageIndex(panel) 387 panel = self.replace_page(index=index, page_info=page_info, type=type) 388 return panel 389 else: 390 for name, panel in self.opened_pages.values(): 391 #Don't return any panel is the exact same page is created 392 if name == page_info.window_name: 393 return None 394 else: 395 panel = self.add_page(page_info=page_info) 396 return panel 397 else: 398 #a new type of page is created 399 panel = self.add_page(page_info=page_info) 400 return panel 401 402 def _onGetstate(self, event): 267 for page in self.opened_pages.values(): 268 #check if the selected data existing in the fitpanel 269 pos = self.GetPageIndex(page) 270 if page.get_data() is None: 271 page.set_data(data) 272 self.SetPageText(pos, str(data.name)) 273 self.SetSelection(pos) 274 return page 275 elif page.get_data().id == data.id: 276 msg = "Data already existing in the fitting panel" 277 wx.PostEvent(self._manager.parent, 278 StatusEvent(status=msg, info='warning')) 279 self.SetSelection(pos) 280 return page 281 282 page = self.add_empty_page() 283 page.id = wx.NewId() 284 page.set_data(data) 285 self.SetPageText(pos, str(data.name)) 286 self.opened_pages[page.id] = page 287 return page 288 289 def _onGetstate(self, event): 403 290 """ 404 291 copy the state of a page 405 292 """ 406 page = event.page407 if page. window_namein self.fit_page_name:408 self.fit_page_name[page.window_name].appendItem(page.createMemento())293 page = event.page 294 if page.id in self.fit_page_name: 295 self.fit_page_name[page.id].appendItem(page.createMemento()) 409 296 410 297 def _onUndo(self, event ): … … 413 300 """ 414 301 page = event.page 415 if page. window_namein self.fit_page_name:416 if self.fit_page_name[page. window_name].getCurrentPosition()==0:302 if page.id in self.fit_page_name: 303 if self.fit_page_name[page.id].getCurrentPosition()==0: 417 304 state = None 418 305 else: 419 state = self.fit_page_name[page. window_name].getPreviousItem()306 state = self.fit_page_name[page.id].getPreviousItem() 420 307 page._redo.Enable(True) 421 308 page.reset_page(state) … … 426 313 """ 427 314 page = event.page 428 if page. window_namein self.fit_page_name:429 length= len(self.fit_page_name[page. window_name])430 if self.fit_page_name[page. window_name].getCurrentPosition()== length -1:315 if page.id in self.fit_page_name: 316 length= len(self.fit_page_name[page.id]) 317 if self.fit_page_name[page.id].getCurrentPosition()== length -1: 431 318 state = None 432 319 page._redo.Enable(False) 433 320 page._redo.Enable(True) 434 321 else: 435 state = self.fit_page_name[page.window_name].getNextItem()322 state =self.fit_page_name[page.id].getNextItem() 436 323 page.reset_page(state) 437 324 … … 441 328 """ 442 329 #remove hint page 443 if selected_page == self.hint_page:330 if selected_page.id == self.hint_page.id: 444 331 return 445 332 ## removing sim_page … … 461 348 if selected_page in page_finder: 462 349 #Delete the name of the page into the list of open page 463 for type, list in self.opened_pages.iteritems():350 for id, list in self.opened_pages.iteritems(): 464 351 #Don't return any panel is the exact same page is created 465 name = str(list[0]) 466 if flag and selected_page.window_name == name: 467 if type.lower() in ['theory1d', 'theory2d']: 468 self._manager.remove_plot(selected_page, theory=True) 469 else: 470 self._manager.remove_plot(selected_page, theory=False) 352 353 if flag and selected_page.id == id: 354 self._manager.remove_plot(id, theory=False) 471 355 break 472 356 del page_finder[selected_page] … … 480 364 481 365 #Delete the name of the page into the list of open page 482 for type, list in self.opened_pages.iteritems():366 for id, list in self.opened_pages.iteritems(): 483 367 #Don't return any panel is the exact same page is created 484 name = str(list[0])485 if selected_page. window_name == name:368 369 if selected_page.id == id: 486 370 del self.opened_pages[type] 487 371 break -
sansview/perspectives/fitting/fitproblem.py
r5062bbf r6bbeacd4 11 11 """ 12 12 ## data used for fitting 13 self.fit_data=None 13 self.fit_data = None 14 self.theory_data = None 14 15 ## the current model 15 16 self.model = None … … 17 18 ## if 1 this fit problem will be selected to fit , if 0 18 19 ## it will not be selected for fit 19 self.schedule =020 self.schedule = 0 20 21 ##list containing parameter name and value 21 self.list_param =[]22 self.list_param = [] 22 23 ## smear object to smear or not data1D 23 self.smearer= None 24 ## same as fit_data but with more info for plotting 25 ## axis unit info and so on see plottables definition 26 self.plotted_data=None 24 self.smearer = None 25 self.fit_tab_caption = '' 27 26 ## fitting range 28 27 self.qmin = None … … 40 39 obj.model = model 41 40 obj.fit_data = copy.deepcopy(self.fit_data) 41 obj.theory_data = copy.deepcopy(self.theory_data) 42 42 obj.model = copy.deepcopy(self.model) 43 43 obj.schedule = copy.deepcopy(self.schedule) … … 103 103 return self.model_index 104 104 105 def add_plotted_data(self,data):105 def set_theory_data(self, data): 106 106 """ 107 107 save a copy of the data select to fit … … 110 110 111 111 """ 112 self. plotted_data = data112 self.theory_data = data 113 113 114 114 115 def get_ plotted_data(self):115 def get_theory_data(self): 116 116 """ 117 117 :return: list of data dList 118 118 119 119 """ 120 return self. plotted_data120 return self.theory_data 121 121 122 def add_fit_data(self,data):122 def set_fit_data(self,data): 123 123 """ 124 124 save a copy of the data select to fit … … 181 181 """ 182 182 self.list_param=[] 183 184 def set_fit_tab_caption(self, caption): 185 """ 186 """ 187 self.fit_tab_caption = str(caption) 188 189 def get_fit_tab_caption(self): 190 """ 191 """ 192 return self.fit_tab_caption 183 193 194 -
sansview/perspectives/fitting/fitting.py
r81f00d7 r6bbeacd4 29 29 from sans.guiframe.dataFitting import Data2D 30 30 from sans.guiframe.dataFitting import Data1D 31 from sans.guiframe. dataFitting import Theory1D32 from sans.guiframe.events import NewPlotEvent,StatusEvent31 from sans.guiframe.events import NewPlotEvent 32 from sans.guiframe.events import StatusEvent 33 33 from sans.guiframe.events import EVT_SLICER_PANEL 34 34 from sans.guiframe.events import EVT_REMOVE_DATA 35 from sans.guiframe.events import ERR_DATA36 35 from sans.guiframe.events import EVT_SLICER_PARS_UPDATE 36 from sans.guiframe.gui_style import GUIFRAME_ID 37 from sans.guiframe.plugin_base import PluginBase 37 38 38 39 … … 50 51 MAX_NBR_DATA = 4 51 52 53 52 54 (PageInfoEvent, EVT_PAGE_INFO) = wx.lib.newevent.NewEvent() 53 55 54 55 class PlotInfo: 56 """ 57 store some plotting field 58 """ 59 _xunit = 'A^{-1}' 60 _xaxis= "\\rm{Q}" 61 _yunit = "cm^{-1}" 62 _yaxis= "\\rm{Intensity} " 63 id = "Model" 64 group_id = "Model" 65 title= None 66 info= None 67 68 from sans.guiframe.plugin_base import PluginBase 56 69 57 70 58 class Plugin(PluginBase): … … 105 93 #keep reference of the simultaneous fit page 106 94 self.sim_page = None 107 #dictionary containing data name and error on dy of that data 108 self.err_dy = {} 109 self.theory_data = None 95 110 96 #Create a reader for fit page's state 111 97 self.state_reader = None … … 114 100 self.state_index = 0 115 101 self.sfile_ext = None 102 # take care of saving data, model and page associated with each other 103 self.page_finder = {} 116 104 # Log startup 117 105 logging.info("Fitting plug-in started") … … 146 134 self.menu1.AppendSeparator() 147 135 id1 = wx.NewId() 148 simul_help = " Allow to edit fit engine with multiple model and data"136 simul_help = "Simultaneous Fit" 149 137 self.menu1.Append(id1, '&Simultaneous Page',simul_help) 150 138 wx.EVT_MENU(owner, id1, self.on_add_sim_page) 151 152 #menu for model 153 menu2 = wx.Menu() 154 self.menu_mng.populate_menu(menu2, owner) 155 id2 = wx.NewId() 156 owner.Bind(models.EVT_MODEL,self._on_model_menu) 157 158 self.fit_panel.set_owner(owner) 159 self.fit_panel.set_model_list(self.menu_mng.get_model_list()) 139 140 id1 = wx.NewId() 141 simul_help = "Add new fit page" 142 self.menu1.Append(id1, '&Create New Page',simul_help) 143 wx.EVT_MENU(owner, id1, self.on_add_new_page) 144 145 #self.fit_panel.set_model_list(self.menu_mng.get_model_list()) 160 146 161 147 #create menubar items … … 181 167 frame.Show(True) 182 168 183 def get_context_menu(self, graph=None):169 def get_context_menu(self, plotpanel=None): 184 170 """ 185 171 Get the context menu items available for P(r).them allow fitting option … … 194 180 195 181 """ 196 self.graph =graph182 graph = plotpanel.graph 197 183 fit_option = "Select data for fitting" 198 184 fit_hint = "Dialog with fitting parameters " 199 200 for item in graph.plottables: 201 if item.__class__.__name__ is "Data2D": 202 203 if hasattr(item,"is_data"): 204 if item.is_data: 205 return [[fit_option, fit_hint, self._onSelect]] 206 else: 207 return [] 208 return [[fit_option, fit_hint, self._onSelect]] 209 else: 210 if item.name == graph.selected_plottable : 211 if item.name in ["$I_{obs}(q)$","$I_{fit}(q)$", 212 "$P_{fit}(r)$"]: 213 return [] 214 if hasattr(item, "group_id"): 215 # if is_data is true , this in an actual data loaded 216 #else it is a data created from a theory model 217 if hasattr(item,"is_data"): 218 if item.is_data: 219 return [[fit_option, fit_hint, 220 self._onSelect]] 221 else: 222 return [] 223 else: 224 return [[fit_option, fit_hint, self._onSelect]] 185 186 if graph.selected_plottable not in plotpanel.plots: 187 return [] 188 item = plotpanel.plots[graph.selected_plottable] 189 if item.__class__.__name__ is "Data2D": 190 if hasattr(item,"is_data"): 191 if item.is_data: 192 return [[fit_option, fit_hint, self._onSelect]] 193 else: 194 return [] 195 return [[fit_option, fit_hint, self._onSelect]] 196 else: 197 198 # if is_data is true , this in an actual data loaded 199 #else it is a data created from a theory model 200 if hasattr(item,"is_data"): 201 if item.is_data: 202 return [[fit_option, fit_hint, 203 self._onSelect]] 204 else: 205 return [] 225 206 return [] 226 207 … … 233 214 #self.parent.Bind(EVT_FITSTATE_UPDATE, self.on_set_state_helper) 234 215 # Creation of the fit panel 235 self.fit_panel = FitPanel(self.parent, -1) 216 self.fit_panel = FitPanel(parent=self.parent, manager=self) 217 self.on_add_new_page(event=None) 236 218 #Set the manager for the main panel 237 219 self.fit_panel.set_manager(self) … … 239 221 self.perspective = [] 240 222 self.perspective.append(self.fit_panel.window_name) 241 # take care of saving data, model and page associated with each other 242 self.page_finder = {} 223 243 224 #index number to create random model name 244 225 self.index_model = 0 245 226 self.index_theory= 0 246 227 self.parent.Bind(EVT_SLICER_PANEL, self._on_slicer_event) 247 self.parent.Bind(ERR_DATA, self._on_data_error)228 248 229 self.parent.Bind(EVT_REMOVE_DATA, self._closed_fitpage) 249 230 self.parent.Bind(EVT_SLICER_PARS_UPDATE, self._onEVT_SLICER_PANEL) … … 333 314 #set state 334 315 data = self.parent.create_gui_data(state.data) 316 335 317 data.group_id = state.data.group_id 336 318 wx.PostEvent(self.parent, NewPlotEvent(plot=data, … … 343 325 data = self.parent.create_gui_data(state.data) 344 326 data.group_id = state.data.group_id 345 page_info = self.fit_panel.get_page_info(data=data)346 panel = self.fit_panel.add_page(page_info)347 self.store_ page(page=panel, data=data)327 self.add_fit_page(data) 328 caption = panel.window_name 329 self.store_data(page=panel.id, data=data, caption=caption) 348 330 self.mypanels.append(panel) 349 331 350 351 332 # get ready for the next set_state 352 333 self.state_index += 1 … … 371 352 self.state_reader.write(filename=filepath, fitstate=fitstate) 372 353 373 def copy_data(self, item, dy=None): 374 """ 375 receive a data 1D and the list of errors on dy 376 and create a new data1D data 377 378 """ 379 id = None 380 if hasattr(item,"id"): 381 id = item.id 382 383 data= Data1D(x=item.x, y=item.y,dx=None, dy=None) 384 data.copy_from_datainfo(item) 385 item.clone_without_data(clone=data) 386 data.dy = deepcopy(dy) 387 data.name = item.name 388 ## allow to highlight data when plotted 389 data.interactive = deepcopy(item.interactive) 390 ## when 2 data have the same id override the 1 st plotted 391 data.id = id 392 data.group_id = item.group_id 393 return data 394 395 def set_fit_range(self, page, qmin, qmax): 354 def set_fit_range(self, id, qmin, qmax): 396 355 """ 397 356 Set the fitting range of a given page 398 357 """ 399 if page in self.page_finder.iterkeys(): 400 fitproblem= self.page_finder[page] 401 fitproblem.set_range(qmin= qmin, qmax= qmax) 358 self.page_finder[id].set_range(qmin=qmin, qmax=qmax) 402 359 403 def schedule_for_fit(self,value=0, page=None,fitproblem =None):360 def schedule_for_fit(self,value=0, id=None,fitproblem =None): 404 361 """ 405 362 Set the fit problem field to 0 or 1 to schedule that problem to fit. … … 414 371 fitproblem.schedule_tofit(value) 415 372 else: 416 if page in self.page_finder.iterkeys(): 417 fitproblem= self.page_finder[page] 418 fitproblem.schedule_tofit(value) 373 self.page_finder[id].schedule_tofit(value) 419 374 420 375 def get_page_finder(self): … … 435 390 436 391 """ 437 sim_page = self.sim_page438 for page, value in self.page_finder.iteritems():439 if page != sim_page:440 list =value.get_model()392 sim_page_id = self.sim_page.id 393 for id, value in self.page_finder.iteritems(): 394 if id != sim_page_id: 395 list = value.get_model() 441 396 model = list[0] 442 if model.name == modelname:443 value.set_model_param(names, values)397 if model.name == modelname: 398 value.set_model_param(names, values) 444 399 break 445 400 … … 471 426 wx.PostEvent(self.parent, StatusEvent(status="Fitting \ 472 427 is cancelled" , type="stop")) 473 474 def set_smearer _nodraw(self,smearer, qmin=None, qmax=None):428 429 def set_smearer(self, id, smearer, qmin=None, qmax=None, draw=True): 475 430 """ 476 431 Get a smear object and store it to a fit problem … … 478 433 :param smearer: smear object to allow smearing data 479 434 480 """481 self.current_pg=self.fit_panel.get_current_page()482 self.page_finder[self.current_pg].set_smearer(smearer)483 ## draw model 1D with smeared data484 data = self.page_finder[self.current_pg].get_fit_data()485 model = self.page_finder[self.current_pg].get_model()486 ## if user has already selected a model to plot487 ## redraw the model with data smeared488 smear =self.page_finder[self.current_pg].get_smearer()489 490 def set_smearer(self,smearer, qmin=None, qmax=None):491 """492 Get a smear object and store it to a fit problem493 494 :param smearer: smear object to allow smearing data495 496 435 """ 497 self.current_pg=self.fit_panel.get_current_page() 498 self.page_finder[self.current_pg].set_smearer(smearer) 499 ## draw model 1D with smeared data 500 data = self.page_finder[self.current_pg].get_fit_data() 501 model = self.page_finder[self.current_pg].get_model() 502 ## if user has already selected a model to plot 503 ## redraw the model with data smeared 504 505 smear = self.page_finder[self.current_pg].get_smearer() 506 if model != None: 507 self.draw_model(model=model, data=data, smearer=smear, 436 if id not in self.page_finder.keys(): 437 msg = "Cannot find ID: %s in page_finder" % str(id) 438 raise ValueError, msg 439 self.page_finder[id].set_smearer(smearer) 440 if draw: 441 ## draw model 1D with smeared data 442 data = self.page_finder[id].get_fit_data() 443 model = self.page_finder[id].get_model() 444 if model is None: 445 return 446 ## if user has already selected a model to plot 447 ## redraw the model with data smeared 448 smear = self.page_finder[id].get_smearer() 449 self.draw_model(model=model, data=data, id=id, smearer=smear, 508 450 qmin=qmin, qmax=qmax) 509 451 510 def draw_model(self, model, data=None, smearer=None,452 def draw_model(self, model, id, data=None, smearer=None, 511 453 enable1D=True, enable2D=False, 512 454 qmin=DEFAULT_QMIN, qmax=DEFAULT_QMAX, qstep=DEFAULT_NPTS): … … 527 469 if data.__class__.__name__ != "Data2D": 528 470 ## draw model 1D with no loaded data 471 529 472 self._draw_model1D(model=model, 530 473 data=data, 474 id=id, 531 475 enable1D=enable1D, 532 476 smearer=smearer, … … 537 481 ## draw model 2D with no initial data 538 482 self._draw_model2D(model=model, 483 id=id, 539 484 data=data, 540 485 enable2D=enable2D, … … 570 515 fproblemId = 0 571 516 self.current_pg = None 572 for page, value in self.page_finder.iteritems():517 for id, value in self.page_finder.iteritems(): 573 518 try: 574 519 if value.get_scheduled() == 1: … … 576 521 pars = [] 577 522 templist = [] 523 page = self.fit_panel.get_page_by_id(id) 578 524 templist = page.get_param_list() 579 525 for element in templist: … … 584 530 id=fproblemId, title=engineType) 585 531 fproblemId += 1 586 self.current_p g= page532 self.current_page_id = page 587 533 except: 588 msg= "%s error: %s" % (engineType, sys.exc_value) 589 wx.PostEvent(self.parent, StatusEvent(status=msg, info="error", 590 type="stop")) 591 return 534 raise 535 #msg= "%s error: %s" % (engineType, sys.exc_value) 536 #wx.PostEvent(self.parent, StatusEvent(status=msg, info="error", 537 # type="stop")) 538 #return 592 539 ## If a thread is already started, stop it 593 540 #if self.calc_fit!= None and self.calc_fit.isrunning(): … … 600 547 handler = handler, 601 548 fn=self.fitter, 602 cpage=self.current_pg,603 549 pars=pars, 604 550 updatefn=handler.update_fit, … … 625 571 time.sleep(0.4) 626 572 627 def remove_plot(self, page, theory=False):573 def remove_plot(self, id, theory=False): 628 574 """ 629 575 remove model plot when a fit page is closed 630 576 """ 631 fitproblem = self.page_finder[ page]577 fitproblem = self.page_finder[id] 632 578 data = fitproblem.get_fit_data() 633 579 model = fitproblem.get_model() 580 id = None 634 581 if model is not None: 635 name = model.name 636 new_plot = Theory1D(x=[], y=[], dy=None) 637 new_plot.name = name 638 new_plot.xaxis(data._xaxis, data._xunit) 639 new_plot.yaxis(data._yaxis, data._yunit) 640 new_plot.group_id = data.group_id 641 new_plot.id = data.id + name 642 wx.PostEvent(self.parent, NewPlotEvent(plot=new_plot, 643 title=data.name)) 582 id = data.id + name 644 583 if theory: 645 new_plot_data = Data1D(x=[], y=[], dx=None, dy=None) 646 new_plot_data.name = data.name 647 new_plot_data.xaxis(data._xaxis, data._xunit) 648 new_plot_data.yaxis(data._yaxis, data._yunit) 649 new_plot_data.group_id = data.group_id 650 new_plot_data.id = data.id 651 wx.PostEvent(self.parent, NewPlotEvent(plot=new_plot_data, 652 title=data.name)) 653 def create_fittable_data2D(self, data): 654 """ 655 check if the current data is a data 2d and add dy to that data 656 657 :return: Data2D 658 659 """ 660 if data.__class__.__name__ != "Data2D": 661 raise ValueError, " create_fittable_data2D expects a Data2D" 662 ## Data2D case 663 new_data = deepcopy(data) 664 if not hasattr(data, "is_data"): 665 new_data.group_id += "data2D" 666 new_data.id +="data2D" 667 new_data.is_data = False 668 title = new_data.name 669 title += " Fit" 670 wx.PostEvent(self.parent, NewPlotEvent(plot=new_data, 671 title=str(title))) 672 else: 673 new_data.is_data = True 674 return new_data 675 676 def create_fittable_data1D(self, data): 677 """ 678 check if the current data is a theory 1d and add dy to that data 679 680 :return: Data1D 681 682 """ 683 class_name = data.__class__.__name__ 684 if not class_name in ["Data1D", "Theory1D"]: 685 raise ValueError, "create_fittable_data1D expects Data1D" 686 687 #get the appropriate dy 688 dy = deepcopy(data.dy) 689 if len(self.err_dy) > 0: 690 if data.name in self.err_dy.iterkeys(): 691 dy = self.err_dy[data.name] 692 if data.__class__.__name__ == "Theory1D": 693 new_data = self.copy_data(data, dy) 694 new_data.group_id = str(new_data.group_id)+"data1D" 695 new_data.id = str(new_data.id)+"data1D" 696 new_data.is_data = False 697 title = new_data.name 698 title = 'Data created from Theory' 699 wx.PostEvent(self.parent, NewPlotEvent(plot=new_data, 700 title=str(title), 701 reset=True)) 702 else: 703 new_data = self.copy_data(data, dy) 704 new_data.id = data.id 705 new_data.is_data = True 706 return new_data 584 id = data.id 585 group_id = data.group_id[len(data.group_id)-1] 586 wx.PostEvent(self.parent, NewPlotEvent(id=id, 587 group_id=group_id, 588 remove=True)) 707 589 708 def store_ page(self, page, data):590 def store_data(self, id, data=None, caption=None): 709 591 """ 710 592 Helper to save page reference into the plug-in … … 713 595 714 596 """ 715 page.set_data(data)716 597 #create a fitproblem storing all link to data,model,page creation 717 if not pagein self.page_finder.keys():718 self.page_finder[ page] = FitProblem()719 self.page_finder[ page].add_fit_data(data)720 721 def add_fit_page(self, data):722 """723 given a data, ask to the fitting panel to create a new fitting page,724 get this page and store it into the page_finder of this plug-in598 if not id in self.page_finder.keys(): 599 self.page_finder[id] = FitProblem() 600 self.page_finder[id].set_fit_data(data) 601 self.page_finder[id].set_fit_tab_caption(caption) 602 603 def on_add_new_page(self, event=None): 604 """ 605 ask fit panel to create a new empty page 725 606 """ 726 607 try: 727 page = self.fit_panel.add_ fit_page(data)728 608 page = self.fit_panel.add_empty_page() 609 page_caption = page.window_name 729 610 # add data associated to the page created 730 611 if page != None: 731 self.store_page(page=page, data=data) 612 self.store_data(id=page.id, caption=page_caption, 613 data=page.get_data()) 732 614 wx.PostEvent(self.parent, StatusEvent(status="Page Created", 733 615 info="info")) … … 737 619 info="warning")) 738 620 except: 739 msg = "Creating Fit page: %s"%sys.exc_value 740 wx.PostEvent(self.parent, StatusEvent(status=msg, info="error")) 741 621 raise 622 #msg = "Creating Fit page: %s"%sys.exc_value 623 #wx.PostEvent(self.parent, StatusEvent(status=msg, info="error")) 624 625 626 def add_fit_page(self, data): 627 """ 628 given a data, ask to the fitting panel to create a new fitting page, 629 get this page and store it into the page_finder of this plug-in 630 """ 631 page = self.fit_panel.set_data(data) 632 page_caption = page.window_name 633 #append Data1D to the panel containing its theory 634 #if theory already plotted 635 if page.id in self.page_finder: 636 theory_data = self.page_finder[page.id].get_theory_data() 637 if issubclass(data.__class__, Data2D): 638 data.group_id.append(wx.NewId()) 639 else: 640 if theory_data is not None: 641 group_id = theory_data.group_id[len(theory_data.group_id)-1] 642 if group_id not in data.group_id: 643 data.group_id.append(group_id) 644 self.store_data(id=page.id, data=data, caption=page.window_name) 645 if self.sim_page is not None: 646 self.sim_page.draw_page() 647 742 648 def _onEVT_SLICER_PANEL(self, event): 743 649 """ … … 794 700 page = self.fit_panel.add_fit_page(data= data,reset=True) 795 701 if fitproblem != None: 796 self.page_finder[ page]=fitproblem702 self.page_finder[id] = fitproblem 797 703 if self.sim_page != None: 798 704 self.sim_page.draw_page() … … 808 714 unschedule or schedule all fitproblem to be fit 809 715 """ 810 for page, fitproblem in self.page_finder.iteritems():716 for fitproblem in self.page_finder.values(): 811 717 fitproblem.schedule_tofit(value) 812 718 … … 845 751 value.clear_model_param() 846 752 except: 847 msg = title + " error: %s" % sys.exc_value 848 wx.PostEvent(self.parent, StatusEvent(status=msg, type="stop")) 753 raise 754 #msg = title + " error: %s" % sys.exc_value 755 #wx.PostEvent(self.parent, StatusEvent(status=msg, type="stop")) 849 756 850 757 def _onSelect(self,event): … … 858 765 if plottable.__class__.__name__ in ["Data1D", "Theory1D"]: 859 766 if plottable.name == self.panel.graph.selected_plottable: 860 data = self.create_fittable_data1D(data=plottable)767 data = plottable 861 768 self.add_fit_page(data=data) 862 769 return 863 770 else: 864 data = self.create_fittable_data2D(data=plottable)771 data = plottable 865 772 self.add_fit_page(data=data) 866 773 867 def _single_fit_completed(self,result, pars,cpage, elapsed=None):774 def _single_fit_completed(self,result, pars, elapsed=None): 868 775 """ 869 776 Display fit result on one page of the notebook. … … 889 796 StatusEvent(status=msg, type="stop")) 890 797 return 891 for page, value in self.page_finder.iteritems(): 892 if page == cpage : 798 page_id = None 799 for id, value in self.page_finder.iteritems(): 800 if value.get_scheduled()==1: 893 801 model = value.get_model() 802 page_id = id 894 803 break 895 804 param_name = [] … … 897 806 for name in pars: 898 807 param_name.append(name) 899 808 809 cpage = self.fit_panel.get_page_by_id(page_id) 900 810 cpage.onsetValues(result.fitness, 901 811 param_name, result.pvec,result.stderr) … … 908 818 return 909 819 910 def _simul_fit_completed(self, result, pars=None, cpage=None,elapsed=None):820 def _simul_fit_completed(self, result, pars=None, elapsed=None): 911 821 """ 912 822 Parameter estimation completed, … … 925 835 return 926 836 if not numpy.isfinite(result.fitness) or numpy.any(result.pvec ==None )or not numpy.all(numpy.isfinite(result.pvec) ): 927 msg= "Si ngleFitting did not converge!!!"837 msg= "Simultaneous Fitting did not converge!!!" 928 838 wx.PostEvent(self.parent, StatusEvent(status=msg,type="stop")) 929 839 return 930 840 931 for page, value in self.page_finder.iteritems():932 if value.get_scheduled() ==1:841 for id, value in self.page_finder.iteritems(): 842 if value.get_scheduled() == 1: 933 843 model = value.get_model() 934 844 data = value.get_fit_data() … … 949 859 950 860 # Display result on each page 951 page.onsetValues(result.fitness, 861 cpage = self.fit_panel.get_page_by_id(id) 862 cpage.onsetValues(result.fitness, 952 863 small_param_name, 953 864 small_out,small_cov) 954 865 except: 955 msg= "Simultaneous Fit completed" 956 msg +=" but Following error occurred:%s"%sys.exc_value 957 wx.PostEvent(self.parent, StatusEvent(status=msg,type="stop")) 958 return 866 raise 867 #msg= "Simultaneous Fit completed" 868 #msg +=" but Following error occurred:%s"%sys.exc_value 869 #wx.PostEvent(self.parent, StatusEvent(status=msg,type="stop")) 870 #return 959 871 960 872 def _on_show_panel(self, event): 961 873 """ 962 874 """ 963 #print "_on_show_panel: fitting"964 875 pass 965 876 … … 1044 955 event = fitpage.FitterTypeEvent() 1045 956 event.type = self._fit_engine 1046 for key in self.page_finder.keys(): 1047 wx.PostEvent(key, event) 957 wx.PostEvent(self.fit_panel, event) 1048 958 1049 959 def _on_model_panel(self, evt): … … 1055 965 """ 1056 966 model = evt.model 967 id = evt.id 968 qmin = evt.qmin 969 qmax = evt.qmax 970 smearer = evt.smearer 1057 971 if model == None: 1058 972 return 1059 smearer = None 1060 qmin = None 1061 qmax = None 1062 if hasattr(evt, "qmin"): 1063 qmin = evt.qmin 1064 if hasattr(evt, "qmax"): 1065 qmax = evt.qmax 1066 if hasattr(evt, "smearer"): 1067 smearer = evt.smearer 1068 model.origin_name = model.name 1069 self.current_pg = self.fit_panel.get_current_page() 1070 ## make sure nothing is done on self.sim_page 1071 ## example trying to call set_panel on self.sim_page 1072 if self.current_pg != self.sim_page : 1073 if self.page_finder[self.current_pg].get_model() is None: 1074 model.name = "M" + str(self.index_model) 1075 self.index_model += 1 1076 else: 1077 model.name= self.page_finder[self.current_pg].get_model().name 1078 data = self.page_finder[self.current_pg].get_fit_data() 1079 # save the name containing the data name with the appropriate model 1080 self.page_finder[self.current_pg].set_model(model) 1081 qmin, qmax= self.current_pg.get_range() 1082 self.page_finder[self.current_pg].set_range(qmin=qmin, qmax=qmax) 1083 1084 if self.sim_page != None: 1085 self.sim_page.draw_page() 1086 1087 def _on_model_menu(self, evt): 1088 """ 1089 Plot a theory from a model selected from the menu 1090 1091 :param evt: wx.menu event 1092 1093 """ 1094 model = evt.model 1095 Plugin.on_perspective(self,event=evt) 1096 # Create a model page. If a new page is created, the model 1097 # will be plotted automatically. If a page already exists, 1098 # the content will be updated and the plot refreshed 1099 self.fit_panel.add_model_page(model, topmenu=True) 1100 973 974 if self.page_finder[id].get_model() is None: 975 model.name = "M" + str(self.index_model) 976 self.index_model += 1 977 else: 978 model.name = self.page_finder[id].get_model().name 979 # save the name containing the data name with the appropriate model 980 self.page_finder[id].set_model(model) 981 self.page_finder[id].set_range(qmin=qmin, qmax=qmax) 982 if self.sim_page is not None: 983 self.sim_page.draw_page() 984 1101 985 def _update1D(self,x, output): 1102 986 """ … … 1108 992 #self.calc_thread.ready(0.01) 1109 993 1110 def _fill_default_model2D(self, theory, qmax,qstep, qmin=None):994 def _fill_default_model2D(self, theory,id, qmax,qstep, qmin=None): 1111 995 """ 1112 996 fill Data2D with default value … … 1191 1075 theory.ymin = ymin 1192 1076 theory.ymax = ymax 1193 theory.group_id = "Model" 1194 theory.id = "Model" 1195 1196 def _get_plotting_info(self, data=None): 1197 """ 1198 get plotting info from data if data !=None else use some default 1199 """ 1200 my_info = PlotInfo() 1201 if data !=None: 1202 if hasattr(data,"info"): 1203 x_name, x_units = data.get_xaxis() 1204 y_name, y_units = data.get_yaxis() 1077 theory.group_id = str(id) + "Model2D" 1078 theory.id = str(id) + "Mode2D" 1079 1205 1080 1206 my_info._xunit = x_units 1207 my_info._xaxis = x_name 1208 my_info._yunit = y_units 1209 my_info._yaxis = y_name 1210 1211 my_info.title= data.name 1212 if hasattr(data, "info"): 1213 my_info.info= data.info 1214 if hasattr(data, "group_id"): 1215 my_info.group_id= data.group_id 1216 return my_info 1217 1218 def _complete1D(self, x,y, elapsed,index,model,data=None): 1081 def _complete1D(self, x,y, id, elapsed,index,model,data=None): 1219 1082 """ 1220 1083 Complete plotting 1D data 1221 1084 """ 1222 1085 try: 1223 new_plot = Theory1D(x=x, y=y) 1224 my_info = self._get_plotting_info( data) 1225 new_plot.name = model.name 1226 new_plot.id = my_info.id 1227 new_plot.group_id = my_info.group_id 1228 1229 new_plot.xaxis(my_info._xaxis, my_info._xunit) 1230 new_plot.yaxis(my_info._yaxis, my_info._yunit) 1086 new_plot = Data1D(x=x, y=y) 1087 new_plot.symbol = GUIFRAME_ID.CURVE_SYMBOL_NUM 1231 1088 if data != None: 1232 if new_plot.id == data.id: 1233 new_plot.id += "Model" 1234 new_plot.is_data =False 1089 _xaxis, _xunit = data.get_xaxis() 1090 _yaxis, _yunit = data.get_yaxis() 1091 new_plot.title = data.name 1092 #if the theory is already plotted use the same group id 1093 #to replot 1094 if id in self.page_finder: 1095 theory_data = self.page_finder[id].get_theory_data() 1096 if theory_data is not None: 1097 print "theory_data", theory_data.group_id 1098 group_id = theory_data.group_id[len(theory_data.group_id)-1] 1099 if group_id not in data.group_id: 1100 data.group_id.append(group_id) 1101 print "data", data.group_id 1102 #data is plotted before the theory, then take its group_id 1103 #assign to the new theory 1104 group_id = data.group_id[len(data.group_id)-1] 1105 if group_id not in new_plot.group_id: 1106 new_plot.group_id.append(group_id) 1107 else: 1108 _xaxis, _xunit = "\\rm{Q}", 'A^{-1}' 1109 _yaxis, _yunit = "\\rm{Intensity} ", "cm^{-1}" 1110 new_plot.title = "Analytical model 1D " 1111 #find a group id to plot theory without data 1112 group_id = str(id) + " Model1D" 1113 if group_id not in new_plot.group_id: 1114 new_plot.group_id.append(group_id) 1115 new_plot.is_data = False 1116 new_plot.id = str(id) + " Model1D" 1117 #find if this theory was already plotted and replace that plot given 1118 #the same id 1119 if id in self.page_finder: 1120 theory_data = self.page_finder[id].get_theory_data() 1121 if theory_data is not None: 1122 temp_id = theory_data.id 1123 new_plot.id = temp_id 1124 new_plot.name = model.name + " ["+ str(model.__class__.__name__)+ "]" 1125 new_plot.xaxis(_xaxis, _xunit) 1126 new_plot.yaxis(_yaxis, _yunit) 1127 self.page_finder[id].set_theory_data(new_plot) 1235 1128 1236 title = new_plot.name1237 # x, y are only in range of index1238 self.theory_data = new_plot1239 #new_plot.perspective = self.get_perspective()1240 # Pass the reset flag to let the plotting event handler1241 # know that we are replacing the whole plot1242 if title is None:1243 title = "Analytical model 1D "1244 1129 if data is None: 1245 1130 wx.PostEvent(self.parent, NewPlotEvent(plot=new_plot, 1246 title=str( title), reset=True))1131 title=str(new_plot.title))) 1247 1132 else: 1248 1133 wx.PostEvent(self.parent, NewPlotEvent(plot=new_plot, 1249 title= str(title))) 1250 # Chisqr in fitpage 1251 current_pg = self.fit_panel.get_current_page() 1134 title= str(new_plot.title))) 1135 current_pg = self.fit_panel.get_page_by_id(id) 1252 1136 wx.PostEvent(current_pg, 1253 Chi2UpdateEvent(output=self._cal_chisqr(data=data, 1254 index=index))) 1137 Chi2UpdateEvent(output=self._cal_chisqr(data=data, 1138 id=id, 1139 index=index))) 1255 1140 msg = "Plot 1D complete !" 1256 1141 wx.PostEvent( self.parent, StatusEvent(status=msg, type="stop" )) 1257 1142 except: 1258 msg = " Error occurred when drawing %s Model 1D: " % new_plot.name 1259 msg += " %s" % sys.exc_value 1260 wx.PostEvent(self.parent, StatusEvent(status=msg, type="stop")) 1143 raise 1144 #msg = " Error occurred when drawing %s Model 1D: " % new_plot.name 1145 #msg += " %s" % sys.exc_value 1146 #wx.PostEvent(self.parent, StatusEvent(status=msg, type="stop")) 1261 1147 1262 1148 def _update2D(self, output,time=None): … … 1269 1155 #self.calc_thread.ready(0.01) 1270 1156 1271 def _complete2D(self, image, data, model, elapsed, index, qmin,1157 def _complete2D(self, image, data, model, id, elapsed, index, qmin, 1272 1158 qmax, qstep=DEFAULT_NPTS): 1273 1159 """ … … 1283 1169 self._fill_default_model2D(theory=theory, 1284 1170 qmax=qmax, 1171 id=id, 1285 1172 qstep=qstep, 1286 1173 qmin= qmin) 1287 1174 1288 1175 else: 1289 theory.id = data.id + "Model" 1290 theory.group_id = data.name + "Model" 1176 theory.id = str(id) + "Model2D" 1177 theory.group_id = str(id) + "Model2D" 1178 1291 1179 theory.x_bins = data.x_bins 1292 1180 theory.y_bins = data.y_bins … … 1305 1193 theory.xmin = data.xmin 1306 1194 theory.xmax = data.xmax 1307 self.theory_data = theory 1195 theory.title = "Analytical model 2D " 1196 self.page_finder[id].set_theory_data(theory) 1197 1308 1198 ## plot 1309 1199 wx.PostEvent(self.parent, NewPlotEvent(plot=theory, 1310 title= "Analytical model 2D ", reset=True))1200 title=theory.title)) 1311 1201 # Chisqr in fitpage 1312 current_pg = self.fit_panel.get_ current_page()1202 current_pg = self.fit_panel.get_page_by_id(id) 1313 1203 wx.PostEvent(current_pg, 1314 Chi2UpdateEvent(output=self._cal_chisqr(data=data, i ndex=index)))1204 Chi2UpdateEvent(output=self._cal_chisqr(data=data, id=id, index=index))) 1315 1205 msg = "Plot 2D complete !" 1316 1206 wx.PostEvent(self.parent, StatusEvent(status=msg, type="stop")) 1317 1318 def _on_data_error(self, event): 1319 """ 1320 receives and event from plotting plu-gins to store the data name and 1321 their errors of y coordinates for 1Data hide and show error 1322 """ 1323 self.err_dy = event.err_dy 1324 1325 def _draw_model2D(self, model, data=None, smearer=None, 1207 1208 def _draw_model2D(self, model, id, data=None, smearer=None, 1326 1209 description=None, enable2D=False, 1327 1210 qmin=DEFAULT_QMIN, qmax=DEFAULT_QMAX, … … 1346 1229 num=qstep, 1347 1230 endpoint=True) 1231 if model is None: 1232 msg = "Panel with ID: %s does not contained model" % str(id) 1233 raise ValueError, msg 1348 1234 ## use data info instead 1349 1235 if data is not None: … … 1366 1252 model=model, 1367 1253 data=data, 1254 id=id, 1368 1255 smearer=smearer, 1369 1256 qmin=qmin, … … 1375 1262 1376 1263 except: 1377 msg = " Error occurred when drawing %s Model 2D: " % model.name 1378 msg += " %s" % sys.exc_value 1379 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1380 1381 def _draw_model1D(self, model, data=None, smearer=None, 1264 raise 1265 #msg = " Error occurred when drawing %s Model 2D: " % model.name 1266 #msg += " %s" % sys.exc_value 1267 #wx.PostEvent(self.parent, StatusEvent(status=msg)) 1268 1269 def _draw_model1D(self, model, id, data=None, smearer=None, 1382 1270 qmin=DEFAULT_QMIN, qmax=DEFAULT_QMAX, 1383 1271 qstep=DEFAULT_NPTS, enable1D=True): … … 1412 1300 self.calc_1D = Calc1D(x=x, 1413 1301 data=data, 1414 model=model, 1302 model=model, 1303 id=id, 1415 1304 qmin=qmin, 1416 1305 qmax=qmax, … … 1425 1314 wx.PostEvent(self.parent, StatusEvent(status=msg)) 1426 1315 1427 def _cal_chisqr(self, data=None, index=None):1316 def _cal_chisqr(self, id, data=None, index=None): 1428 1317 """ 1429 1318 Get handy Chisqr using the output from draw1D and 2D, … … 1443 1332 index = index & (data.err_data != 0) 1444 1333 fn = data.data[index] 1445 gn = self.theory_data.data[index] 1334 theory_data = self.page_finder[id].get_theory_data() 1335 gn = theory_data.data[index] 1446 1336 en = data.err_data[index] 1447 1337 else: … … 1457 1347 dy[dy==0] = 1 1458 1348 fn = data.y[index] 1459 gn = self.theory_data.y 1349 theory_data = self.page_finder[id].get_theory_data() 1350 gn = theory_data.y 1460 1351 en = dy[index] 1461 1352 # residual -
sansview/perspectives/fitting/model_thread.py
r5062bbf r6bbeacd4 15 15 """ 16 16 def __init__(self, x, y, data,model,smearer,qmin, qmax,qstep, 17 id , 17 18 completefn = None, 18 19 updatefn = None, … … 31 32 self.y = y 32 33 self.data= data 34 self.page_id = id 33 35 # the model on to calculate 34 36 self.model = model … … 115 117 116 118 elapsed = time.time()-self.starttime 117 self.complete( image = output, 118 data = self.data , 119 model = self.model, 120 elapsed = elapsed, 121 index = index_model, 122 qmin = self.qmin, 123 qmax = self.qmax, 124 qstep = self.qstep ) 119 self.complete(image=output, 120 data=self.data, 121 id=self.page_id, 122 model=self.model, 123 elapsed=elapsed, 124 index=index_model, 125 qmin=self.qmin, 126 qmax=self.qmax, 127 qstep=self.qstep) 125 128 126 129 … … 130 133 """ 131 134 def __init__(self, x, model, 135 id, 132 136 data=None, 133 137 qmin=None, … … 150 154 self.qmax= qmax 151 155 self.model = model 156 self.page_id = id 152 157 self.smearer= smearer 153 158 self.starttime = 0 … … 172 177 173 178 self.complete(x=self.x[index], y=output[index], 179 id=self.page_id, 174 180 elapsed=elapsed,index=index, model=self.model, 175 181 data=self.data) -
sansview/perspectives/fitting/models.py
r6886000 r6bbeacd4 163 163 ## Event owner (guiframe) 164 164 event_owner = None 165 165 def __init__(self): 166 """ 167 """ 168 self._getModelList() 169 166 170 def _getModelList(self): 167 171 """ … … 552 556 553 557 """ 558 self.model_combobox.set_list("Shapes", self.shape_list) 559 self.model_combobox.set_list("Shape-Independent", self.shape_indep_list) 560 self.model_combobox.set_list("Structure Factors", self.struct_list) 561 self.model_combobox.set_list("Customized Models", self.plugins) 562 self.model_combobox.set_list("P(Q)*S(Q)", self.multiplication_factor) 554 563 self.model_combobox.set_list("multiplication", self.multiplication_factor) 555 564 self.model_combobox.set_list("Multi-Functions", self.multi_func_list) -
sansview/perspectives/fitting/simfitpage.py
r4ce74917 r6bbeacd4 50 50 ##Font size 51 51 self.SetWindowVariant(variant = FONT_VARIANT) 52 52 self.id = None 53 53 self.parent = parent 54 54 ## store page_finder 55 55 self.page_finder = page_finder 56 56 ## list contaning info to set constraint 57 ## look like self.constraint_dict[page ]= page57 ## look like self.constraint_dict[page_id]= page 58 58 self.constraint_dict={} 59 59 ## item list self.constraints_list=[combobox1, combobox2,=,textcrtl, button ] … … 135 135 self._set_constraint() 136 136 ## get the fit range of very fit problem 137 for page, value in self.page_finder.iteritems():138 qmin, qmax= page.get_range()137 for id, value in self.page_finder.iteritems(): 138 qmin, qmax= self.page_finder[id].get_range() 139 139 value.set_range(qmin, qmax) 140 140 ## model was actually selected from this page to be fit … … 162 162 check all models names 163 163 """ 164 self.model_toFit =[]165 if self.cb1.GetValue()== True:164 self.model_toFit = [] 165 if self.cb1.GetValue()== True: 166 166 for item in self.model_list: 167 167 item[0].SetValue(True) … … 270 270 for item in self.model_toFit: 271 271 model = item[3] 272 page = item[2]273 self.constraint_dict[page ] = model272 page_id= item[2] 273 self.constraint_dict[page_id] = model 274 274 275 275 def _display_constraint(self, event): … … 333 333 btRemove.SetToolTipString("Remove constraint.") 334 334 335 for page,model in self.constraint_dict.iteritems():335 for id,model in self.constraint_dict.iteritems(): 336 336 ## check if all parameters have been selected for constraint 337 337 ## then do not allow add constraint on parameters … … 364 364 hide buttons related constraint 365 365 """ 366 for pagein self.page_finder.iterkeys():367 self.page_finder[ page].clear_model_param()366 for id in self.page_finder.iterkeys(): 367 self.page_finder[id].clear_model_param() 368 368 369 369 self.nb_constraint =0 … … 539 539 msg+= " to set constraint! " 540 540 wx.PostEvent(self.parent.Parent, StatusEvent(status= msg )) 541 for page, value in self.constraint_dict.iteritems():541 for id, value in self.constraint_dict.iteritems(): 542 542 if model == value: 543 543 if constraint == "": … … 546 546 wx.PostEvent(self.parent.Parent, StatusEvent(status= msg )) 547 547 constraint = None 548 self.page_finder[ page].set_model_param(param,constraint)548 self.page_finder[id].set_model_param(param,constraint) 549 549 break 550 550 … … 575 575 sizer.Add(data_used,(iy, ix),(1,1), 576 576 wx.EXPAND|wx.ADJUST_MINSIZE, 0) 577 578 for page, value in self.page_finder.iteritems(): 577 ix += 1 578 tab_used = wx.StaticText(self, -1, ' Fit Tab') 579 tab_used.SetBackgroundColour('grey') 580 sizer.Add(tab_used,(iy, ix),(1,1), 581 wx.EXPAND|wx.ADJUST_MINSIZE, 0) 582 for id, value in self.page_finder.iteritems(): 579 583 try: 580 584 ix = 0 581 585 iy += 1 582 586 model = value.get_model() 583 cb = wx.CheckBox(self, -1, str(model.name)) 587 name = '_' 588 if model is not None: 589 name = str(model.name) 590 cb = wx.CheckBox(self, -1, name) 584 591 cb.SetValue(False) 592 cb.Enable(model is not None) 585 593 sizer.Add( cb,( iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15) 586 594 wx.EVT_CHECKBOX(self, cb.GetId(), self.check_model_name) 587 588 595 ix += 2 589 596 type = model.__class__.__name__ 590 597 model_type = wx.StaticText(self, -1, str(type)) 591 598 sizer.Add(model_type,( iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0) 599 data = value.get_fit_data() 600 name = '-' 601 if data is not None: 602 name = str(data.name) 603 data_used = wx.StaticText(self, -1, name) 604 ix += 1 605 sizer.Add(data_used,( iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0) 606 607 ix += 1 608 caption = value.get_fit_tab_caption() 609 tab_caption_used= wx.StaticText(self, -1, str(caption)) 610 sizer.Add(tab_caption_used,( iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0) 592 611 593 ix += 1 594 data = value.get_fit_data() 595 data_used= wx.StaticText(self, -1, str(data.name)) 596 sizer.Add(data_used,( iy,ix),(1,1), wx.EXPAND|wx.ADJUST_MINSIZE, 0) 597 598 self.model_list.append([cb,value,page,model]) 612 self.model_list.append([cb,value,id,model]) 599 613 600 614 except: 601 pass 615 raise 616 #pass 602 617 iy += 1 603 618 sizer.Add((20,20),( iy,ix),(1,1), wx.LEFT|wx.EXPAND|wx.ADJUST_MINSIZE, 15)
Note: See TracChangeset
for help on using the changeset viewer.