/[ascend]/trunk/pygtk/gtkbrowser.py
ViewVC logotype

Contents of /trunk/pygtk/gtkbrowser.py

Parent Directory Parent Directory | Revision Log Revision Log


Revision 669 - (show annotations) (download) (as text)
Wed Jun 21 07:00:45 2006 UTC (14 years, 3 months ago) by johnpye
File MIME type: text/x-python
File size: 27465 byte(s)
Merged changes from DAE branch (revisions 702 to 819) back into trunk.
This adds the Integration API to the ASCEND solver (in base/generic).
Also provides pre-alpha support for 'IDA' from the SUNDIALS suite, a DAE solver.
Many other minor code clean-ups, including adoption of new 'ASC_NEW' and friends (to replace 'ascmalloc')
Added some very sketchy stuff providing 'DIFF(...)' syntax, although it is anticipated that this will be removed.
1 #!/usr/bin/env python
2
3 import sys
4 def print_loading_status(status,msg=None):
5 sys.stderr.write("\r \r")
6 if msg!=None:
7 sys.stderr.write(msg+"\n")
8 sys.stderr.write(status+"...")
9 sys.stderr.flush()
10
11 try:
12 print_loading_status("Loading PSYCO")
13
14 #try:
15 # import psyco
16 # psyco.full()
17 # print "Running with PSYCO optimisation..."
18 #except ImportError:
19 # pass
20
21
22 print_loading_status("Loading python standard libraries")
23
24 import re
25 import urlparse
26 import optparse
27 import platform
28 import sys
29 import os.path
30
31 if platform.system() != "Windows":
32 import dl
33 # This sets the flags for dlopen used by python so that the symbols in the
34 # ascend library are made available to libraries dlopened within ASCEND:
35 sys.setdlopenflags(dl.RTLD_GLOBAL|dl.RTLD_NOW)
36
37 print_loading_status("Loading LIBASCEND/ascpy")
38 import ascpy
39
40 print_loading_status("Loading PyGTK, glade, pango")
41
42 import pygtk
43 pygtk.require('2.0')
44 import gtk
45 import gtk.glade
46 import pango
47
48 print_loading_status("Loading python matplotlib")
49 try:
50 import matplotlib
51 matplotlib.use('GTKAgg')
52
53 try:
54 print_loading_status("Trying python numpy")
55 import numpy
56 matplotlib.rcParams['numerix'] = 'numpy'
57 print_loading_status("","Using python module numpy")
58 except ImportError:
59 try:
60 print_loading_status("Trying python numarray")
61 import numarray
62 matplotlib.rcParams['numerix'] = 'numarray'
63 print_loading_status("","Using python module numarray")
64 except ImportError:
65 try:
66 print_loading_status("Trying python Numeric")
67 import Numeric
68 matplotlib.rcParams['numerix'] = 'Numeric'
69 print_loading_status("","Using python module Numeric")
70 except ImportError:
71 print_loading_status("","FAILED TO LOAD A NUMERIC MODULE FOR PYTHON")
72
73 except ImportError,e:
74 print_loading_status("","FAILED TO LOAD MATPLOTLIB")
75 raise RuntimeError("Failed to load MATPLOTLIB (is it installed?). Details:"+str(e))
76
77 print_loading_status("Loading IPython")
78 import console;
79 if not console.have_ipython:
80 print_loading_status("","IPython couldn't be loaded")
81
82 print_loading_status("Loading ASCEND python modules")
83 from preferences import * # loading/saving of .ini options
84 from solverparameters import * # 'solver parameters' window
85 from help import * # viewing help files
86 from incidencematrix import * # incidence/sparsity matrix matplotlib window
87 from observer import * # observer tab support
88 from properties import * # solver_var properties dialog
89 from varentry import * # for inputting of variables with units
90 from diagnose import * # for diagnosing block non-convergence
91 from solverreporter import * # solver status reporting
92 from modelview import * # model browser
93 from integrator import * # integrator dialog
94 import config
95
96 except RuntimeError, e:
97 print "ASCEND had problems starting up. Please report the following"
98 print "error message at http://mantis.cruncher2.dyndns.org/."
99 print "\n\nFull error message:",str(e)
100 print "\n\nPress ENTER to close this window."
101 sys.stdout.flush()
102 sys.stdin.readline();
103 sys.exit();
104
105 except ImportError, e:
106 print "\n\n------------------ ERROR ---------------------"
107 print "ASCEND had problems importing required models."
108 print "\nPlease ensure you have all the runtime prerequisites installed."
109 print "Please then report a bug if you continue to have problems."
110 print "\nFull error message:",str(e)
111 if platform.system()=="Windows":
112 print "\nYou will also need to report the contents of any popup error"
113 print "messages from Windows if any were shown."
114 print "\n\nPress ENTER to close this window."
115 sys.stdout.flush()
116 sys.stdin.readline();
117 sys.exit();
118
119 print_loading_status("Starting GUI")
120
121 # This is my first ever GUI code so please be nice :)
122 # But I *have* at least read
123 # http://www.joelonsoftware.com/uibook/chapters/fog0000000057.html
124 # and leafed through
125 # http://developer.gnome.org/projects/gup/hig/
126
127 # The fancy tree-view gizmo is the GtkTreeView object. See the article
128 # http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/300304
129 # for the original source code on which my implementation was based.
130
131 ESCAPE_KEY = 65307
132
133 HELP_ROOT = None
134
135 #======================================
136 # Browser is the main ASCEND library/model browser window
137
138 class Browser:
139
140 # ---------------------------------
141 # SETUP
142
143 def __init__(self):
144 #--------
145 # load the file referenced in the command line, if any
146
147 print_loading_status("Parsing options")
148
149 parser = optparse.OptionParser(usage="%prog [[-m typename] file]", version="gtkbrowser $rev$" )
150 # add options here if we want
151
152 parser.add_option("-m", "--model"
153 ,action="store", type="string", dest="model"
154 ,help="specify the model to instantiate upon loading modules")
155
156 parser.add_option("--pygtk-assets"
157 ,action="store", type="string", dest="assets_dir"
158 ,help="override the configuration value for the location of assets"\
159 +" required by PyGTK for the ASCEND GUI, optional"
160 ,default=config.PYGTK_ASSETS
161 )
162
163 parser.add_option("--library"
164 ,action="store", type="string", dest="library_path"
165 ,help="overried the configuration value for the library path"
166 ,default=None
167 )
168
169 (self.options, args) = parser.parse_args()
170
171 #print "OPTIONS_______________:",self.options
172
173 self.assets_dir = self.options.assets_dir
174
175 self.observers = []
176 self.clip = None
177
178 #--------
179 # load up the preferences ini file
180
181 print_loading_status("Loading preferences")
182
183 self.prefs = Preferences()
184
185 _prefpath = self.prefs.getStringPref("Directories","librarypath",None)
186 _preffileopenpath = self.prefs.getStringPref("Directories","fileopenpath",None)
187
188 #--------
189 # set up library path and the path to use for File->Open dialogs
190
191 if self.options.library_path != None:
192 _path = os.path.abspath(self.options.library_path)
193 _pathsrc = "commandline"
194 # when a special path is specified, use that as the file-open location
195 self.fileopenpath = _path
196 else:
197 if _prefpath:
198 _path = _prefpath
199 _pathsrc = "user preferences"
200 else:
201 _path = config.LIBRARY_PATH
202 _pathsrc = "default (config.py)"
203
204 if _preffileopenpath:
205 self.fileopenpath = _preffileopenpath
206 else:
207 self.fileopenpath = _path
208
209 #--------
210 # Create the ASCXX 'Library' object
211
212 print_loading_status("Creating ASCEND 'Library' object","PATH = "+_path+" FROM "+_pathsrc)
213 self.library = ascpy.Library(_path)
214
215 self.sim = None
216
217 #--------
218 # Prepare the ASCEND icon
219
220 print_loading_status("Setting up windows")
221
222 if config.ICON_EXTENSION:
223 _icon = gtk.Image()
224 _iconpath = self.assets_dir+'ascend'+config.ICON_EXTENSION
225 _icon.set_from_file(_iconpath)
226 try:
227 self.icon = _icon.get_pixbuf()
228 except RuntimeError, e:
229 print "FAILED to set icon:",str(e)
230
231 #-------------------
232 # Set up the window and main widget actions
233
234 self.glade_file = self.assets_dir+config.GLADE_FILE
235 glade = gtk.glade.XML(self.glade_file,"browserwin")
236
237 self.window = glade.get_widget("browserwin")
238 if self.icon:
239 self.window.set_icon(self.icon)
240
241 if not self.window:
242 raise RuntimeError("Couldn't load window from glade file")
243
244 _display = self.window.get_screen().get_display().get_name()
245 _geom=self.prefs.getGeometrySizePosition(_display,"browserwin")
246 if _geom:
247 self.window.resize(_geom[0],_geom[1])
248 self.window.move(_geom[2],_geom[3])
249
250 self.window.connect("delete_event", self.delete_event)
251
252 self.browserpaned=glade.get_widget("browserpaned")
253 _geom2=self.prefs.getGeometryValue(_display,"browserpaned")
254 if _geom2:
255 self.browserpaned.set_position(_geom2)
256
257 self.openbutton=glade.get_widget("openbutton")
258 self.openbutton.connect("clicked",self.open_click)
259
260 self.reloadbutton=glade.get_widget("reloadbutton")
261 self.reloadbutton.connect("clicked",self.reload_click)
262
263 self.solvebutton=glade.get_widget("solvebutton")
264 self.solvebutton.connect("clicked",self.solve_click)
265
266 self.integratebutton=glade.get_widget("integratebutton")
267 self.integratebutton.connect("clicked",self.integrate_click)
268
269 self.checkbutton=glade.get_widget("checkbutton")
270 self.checkbutton.connect("clicked",self.check_click)
271
272 self.autotoggle=glade.get_widget("autotoggle")
273 self.autotoggle.connect("toggled",self.auto_toggle)
274
275 self.is_auto = self.autotoggle.get_active()
276
277 self.methodrunbutton=glade.get_widget("methodrunbutton")
278 self.methodrunbutton.connect("clicked",self.methodrun_click)
279
280 self.methodsel=glade.get_widget("methodsel")
281
282 self.maintabs = glade.get_widget("maintabs")
283
284 self.statusbar = glade.get_widget("statusbar")
285
286 self.menu = glade.get_widget("browsermenu")
287 glade.signal_autoconnect(self)
288
289 self.automenu = glade.get_widget("automenu")
290 self.automenu.set_active(self.is_auto)
291 if self.automenu == None:
292 print "NO AUTOMENU FOUND"
293
294 self.show_solving_popup=glade.get_widget("show_solving_popup")
295 self.show_solving_popup.set_active(self.prefs.getBoolPref("SolverReporter","show_popup",True))
296 self.close_on_converged=glade.get_widget("close_on_converged")
297 self.close_on_converged.set_active(self.prefs.getBoolPref("SolverReporter","close_on_converged",True))
298 self.close_on_nonconverged=glade.get_widget("close_on_nonconverged")
299 self.close_on_nonconverged.set_active(self.prefs.getBoolPref("SolverReporter","close_on_nonconverged",True))
300
301 #-------
302 # Status icons
303
304 self.fixedimg = gtk.Image()
305 self.fixedimg.set_from_file(self.options.assets_dir+'locked.png')
306
307 self.iconstatusunknown = None
308 self.iconfixed = self.fixedimg.get_pixbuf()
309 self.iconsolved = self.window.render_icon(gtk.STOCK_YES,gtk.ICON_SIZE_MENU)
310 self.iconactive = self.window.render_icon(gtk.STOCK_NO,gtk.ICON_SIZE_MENU)
311 self.iconunsolved = None
312
313 self.statusicons={
314 ascpy.ASCXX_VAR_STATUS_UNKNOWN: self.iconstatusunknown
315 ,ascpy.ASCXX_VAR_FIXED: self.iconfixed
316 ,ascpy.ASCXX_VAR_SOLVED: self.iconsolved
317 ,ascpy.ASCXX_VAR_ACTIVE: self.iconactive
318 ,ascpy.ASCXX_VAR_UNSOLVED: self.iconunsolved
319 }
320
321
322 self.statusmessages={
323 ascpy.ASCXX_VAR_STATUS_UNKNOWN: "Status unknown"
324 ,ascpy.ASCXX_VAR_FIXED: "Fixed"
325 ,ascpy.ASCXX_VAR_SOLVED: "Converged"
326 ,ascpy.ASCXX_VAR_ACTIVE: "Active (unconverged)"
327 ,ascpy.ASCXX_VAR_UNSOLVED: "Not yet visited"
328 }
329
330 #-------------------
331 # waitwin
332
333 self.waitwin = gtk.gdk.Window(self.window.window,
334 gtk.gdk.screen_width(),
335 gtk.gdk.screen_height(),
336 gtk.gdk.WINDOW_CHILD,
337 0,
338 gtk.gdk.INPUT_ONLY)
339
340 _cursor = gtk.gdk.Cursor(gtk.gdk.WATCH)
341 self.waitwin.set_cursor(_cursor)
342
343 #-------------------
344 # pixbufs to be used in the error listing
345
346 self.iconok = self.window.render_icon(gtk.STOCK_YES,gtk.ICON_SIZE_MENU)
347 self.iconinfo = self.window.render_icon(gtk.STOCK_DIALOG_INFO,gtk.ICON_SIZE_MENU)
348 self.iconwarning = self.window.render_icon(gtk.STOCK_DIALOG_WARNING,gtk.ICON_SIZE_MENU)
349 self.iconerror = self.window.render_icon(gtk.STOCK_DIALOG_ERROR,gtk.ICON_SIZE_MENU)
350
351 #--------------------
352 # pixbufs for solver_var status
353
354 #--------------------
355 # set up the error view
356
357 self.errorview = glade.get_widget("errorview")
358 errstorecolstypes = [gtk.gdk.Pixbuf,str,str,str,int]
359 self.errorstore = gtk.TreeStore(*errstorecolstypes)
360 errtitles = ["","Location","Message"];
361 self.errorview.set_model(self.errorstore)
362 self.errcols = [ gtk.TreeViewColumn() for _type in errstorecolstypes]
363
364 i = 0
365 for tvcolumn in self.errcols[:len(errtitles)]:
366 tvcolumn.set_title(errtitles[i])
367 self.errorview.append_column(tvcolumn)
368
369 if i>0:
370 _renderer = gtk.CellRendererText()
371 tvcolumn.pack_start(_renderer, True)
372 tvcolumn.add_attribute(_renderer, 'text', i)
373 if(i==2):
374 tvcolumn.add_attribute(_renderer, 'foreground', 3)
375 tvcolumn.add_attribute(_renderer, 'weight', 4)
376 else:
377 _renderer1 = gtk.CellRendererPixbuf()
378 tvcolumn.pack_start(_renderer1, False)
379 tvcolumn.add_attribute(_renderer1, 'pixbuf', int(0))
380
381 i = i + 1
382
383
384 #--------------------
385 # set up the error reporter callback
386 self.reporter = ascpy.getReporter()
387 self.reporter.setPythonErrorCallback(self.error_callback)
388
389 #-------------------
390 # set up the module view
391
392 self.modtank = {}
393 self.moduleview = glade.get_widget("moduleview")
394 modulestorecoltypes = [str, str, int] # bool=can-be-instantiated
395 self.modulestore = gtk.TreeStore(*modulestorecoltypes)
396 moduleviewtitles = ["Module name", "Filename"]
397 self.moduleview.set_model(self.modulestore)
398 self.modcols = [ gtk.TreeViewColumn() for _type in modulestorecoltypes]
399 i = 0
400 for modcol in self.modcols[:len(moduleviewtitles)]:
401 modcol.set_title(moduleviewtitles[i])
402 self.moduleview.append_column(modcol)
403 _renderer = gtk.CellRendererText()
404 modcol.pack_start(_renderer, True)
405 modcol.add_attribute(_renderer, 'text', i)
406 modcol.add_attribute(_renderer,'weight',2)
407 i = i + 1
408 self.moduleview.connect("row-activated", self.module_activated )
409
410 #--------------------
411 # set up the methods combobox
412
413 self.methodstore = gtk.ListStore(str)
414 self.methodsel.set_model(self.methodstore)
415 _methodrenderer = gtk.CellRendererText()
416 self.methodsel.pack_start(_methodrenderer, True)
417 self.methodsel.add_attribute(_methodrenderer, 'text',0)
418
419 #--------
420 # set up the instance browser view
421
422 self.modelview = ModelView(self, glade)
423
424 #--------
425 # options
426
427 if(len(args)==1):
428 self.do_open(args[0])
429
430 print "Options: ",self.options
431
432 if self.options.model:
433 try:
434 _t =self.library.findType(self.options.model);
435 self.do_sim(_t);
436 except RuntimeError, e:
437 self.reporter.reportError("Failed to create instance of '%s': %s" %(self.options.model, str(e)));
438
439
440 def run(self):
441 self.window.show()
442 print_loading_status("ASCEND is now running")
443 gtk.main()
444
445 # --------------------------------------------
446 # MAJOR GUI COMMANDS
447
448 def on_fix_variable_activate(self,*args):
449 self.modelview.on_fix_variable_activate(*args)
450
451 def on_free_variable_activate(self,*args):
452 self.modelview.on_free_variable_activate(*args)
453
454 def do_open(self,filename):
455 # TODO does the user want to lose their work?
456 # TODO do we need to chdir?
457
458 _context = self.statusbar.get_context_id("do_open")
459
460 self.errorstore.clear()
461
462 self.modelview.clear()
463
464 # self.library.clear()
465
466 self.statusbar.push(_context,"Loading '"+filename+"'")
467 self.library.load(filename)
468 self.statusbar.pop(_context)
469
470 self.filename = filename
471
472 # Load the current list of modules into self.modules
473 self.modtank = {}
474 self.modulestore.clear()
475 modules = self.library.getModules()
476 self.library.listModules()
477 try:
478 _lll=len(modules)
479 except:
480 _msg = "UNABLE TO ACCESS MODULES LIST. This is bad.\n"+\
481 "Check your SWIG configuration (check for warnings during build)."
482
483 self.reporter.reportError(_msg)
484 raise RuntimeError(_msg)
485
486 for m in reversed(modules):
487 _n = str( m.getName() )
488 _f = str( m.getFilename() )
489 #print "ADDING ROW name %s, file = %s" % (_n, _f)
490 _r = self.modulestore.append(None, [ _n, _f, pango.WEIGHT_NORMAL ])
491 for t in self.library.getModuleTypes(m):
492 _n = t.getName()
493 _hasparams = t.hasParameters()
494 if _hasparams:
495 _w = pango.WEIGHT_NORMAL
496 else:
497 _w = pango.WEIGHT_BOLD
498
499 #print "ADDING TYPE %s" % _n
500 _piter = self.modulestore.append(_r , [ _n, "", _w ])
501 _path = self.modulestore.get_path(_piter)
502 self.modtank[_path]=t
503
504 #print "DONE ADDING MODULES"
505
506 self.sim = None;
507 self.maintabs.set_current_page(0);
508
509 # See http://www.daa.com.au/pipermail/pygtk/2005-October/011303.html
510 # for details on how the 'wait cursor' is done.
511 def start_waiting(self, message):
512 self.waitcontext = self.statusbar.get_context_id("waiting")
513 self.statusbar.push(self.waitcontext,message)
514
515 if self.waitwin:
516 self.waitwin.show()
517
518 while gtk.events_pending():
519 gtk.main_iteration()
520
521 def stop_waiting(self):
522 if self.waitwin:
523 self.statusbar.pop(self.waitcontext)
524 self.waitwin.hide()
525
526 def do_sim(self, type_object):
527 self.sim = None;
528 # TODO: clear out old simulation first!
529
530 print "DO_SIM(%s)" % str(type_object.getName())
531 self.start_waiting("Compiling...")
532
533 try:
534 self.sim = type_object.getSimulation(str(type_object.getName())+"_sim")
535 except RuntimeError, e:
536 self.stop_waiting()
537 self.reporter.reportError(str(e))
538 return
539
540 print "...DONE 'getSimulation'"
541 self.stop_waiting()
542
543 self.start_waiting("Building simulation...")
544 print "BUILDING SIMULATION"
545
546 try:
547 self.sim.build()
548 except RuntimeError, e:
549 self.stop_waiting()
550 self.reporter.reportError(str(e))
551 return;
552
553 print "DONE BUILDING"
554 self.stop_waiting()
555
556 self.sim.setSolver(ascpy.Solver("QRSlv"))
557
558 # methods
559 self.methodstore.clear()
560 _methods = self.sim.getType().getMethods()
561 _activemethod = None;
562 for _m in _methods:
563 _i = self.methodstore.append([_m.getName()])
564 if _m.getName()=="on_load":
565 self.methodsel.set_active_iter(_i)
566
567 self.modelview.setSimulation(self.sim)
568
569 def do_solve_if_auto(self):
570 if self.is_auto:
571 self.sim.check()
572 self.do_solve()
573 else:
574 self.sim.processVarStatus()
575 self.modelview.refreshtree()
576
577 self.sync_observers()
578
579 def do_solve(self):
580 if not self.sim:
581 self.reporter.reportError("No model selected yet")
582 return
583
584 self.start_waiting("Solving...")
585
586 if self.prefs.getBoolPref("SolverReporter","show_popup",True):
587 reporter = PopupSolverReporter(self,self.sim.getNumVars())
588 else:
589 reporter = SimpleSolverReporter(self)
590
591 self.sim.solve(ascpy.Solver("QRSlv"),reporter)
592
593 self.stop_waiting()
594
595 self.sim.processVarStatus()
596 self.modelview.refreshtree()
597
598 def do_integrate(self):
599 if not self.sim:
600 self.reporter.reportError("No model selected yet")
601 return
602 integwin = IntegratorWindow(self,self.sim)
603 _integratorreporter = integwin.run()
604 if _integratorreporter!=None:
605 _integratorreporter.run()
606 self.sim.processVarStatus()
607 self.modelview.refreshtree()
608
609
610 def do_check(self):
611 if not self.sim:
612 self.reporter.reportError("No model selected yet")
613 return
614
615 self.start_waiting("Checking system...")
616
617 try:
618 if self.sim.check():
619 self.reporter.reportNote("System check OK")
620 self.sim.checkDoF()
621 except RuntimeError, e:
622 self.stop_waiting()
623 self.reporter.reportError(str(e))
624 return
625
626 self.stop_waiting()
627
628 self.modelview.refreshtree()
629
630 def do_method(self,method):
631 if not self.sim:
632 self.reporter.reportError("No model selected yet")
633
634 self.sim.run(method)
635 self.modelview.refreshtree()
636
637 def do_quit(self):
638 print_loading_status("Saving window location")
639 self.reporter.clearPythonErrorCallback()
640
641 _w,_h = self.window.get_size()
642 _t,_l = self.window.get_position()
643 _display = self.window.get_screen().get_display().get_name()
644 self.prefs.setGeometrySizePosition(_display,"browserwin",_w,_h,_t,_l );
645
646 _p = self.browserpaned.get_position()
647 self.prefs.setGeometryValue(_display,"browserpaned",_p);
648
649 print_loading_status("Saving current directory")
650 self.prefs.setStringPref("Directories","fileopenpath",self.fileopenpath)
651
652 print_loading_status("Saving preferences")
653 # causes prefs to be saved unless they are still being used elsewher
654 del(self.prefs)
655
656 print_loading_status("Closing down GTK")
657 gtk.main_quit()
658
659 print_loading_status("Clearing error callback")
660 self.reporter.clearPythonErrorCallback()
661
662 print_loading_status("Quitting")
663 return False
664
665 def on_tools_sparsity_click(self,*args):
666
667 self.reporter.reportNote("Preparing incidence matrix...")
668 _im = self.sim.getIncidenceMatrix();
669
670 self.reporter.reportNote("Plotting incidence matrix...")
671
672 _sp = IncidenceMatrixWindow(_im);
673 _sp.run();
674
675 def on_diagnose_blocks_click(self,*args):
676 try:
677 _bl = self.sim.getActiveBlock()
678 except RuntimeError, e:
679 self.reporter.reportError(str(e))
680 return
681 _db = DiagnoseWindow(self,_bl)
682 _db.run();
683
684 def on_add_observer_click(self,*args):
685 if len(self.observers) > 0:
686 self.reporter.reportError("Not supported: multiple observers")
687 return
688 self.create_observer()
689
690 def on_keep_observed_click(self,*args):
691 if len(self.observers) > 1:
692 self.reporter.reportError("Not supported: multiple observers")
693 return
694 if len(self.observers) <= 0:
695 self.reporter.reportError("No observer defined!")
696 return
697 self.observers[0].do_add_row()
698
699 def on_copy_observer_matrix_click(self,*args):
700 if self.clip == None:
701 self.clip = gtk.Clipboard()
702
703 if len(self.observers) > 1:
704 self.reporter.reportError("Not supported: multiple observers")
705 return
706 if len(self.observers) <= 0:
707 self.reporter.reportError("No observer defined!")
708 return
709 self.observers[0].copy_to_clipboard(self.clip)
710
711 def on_show_solving_popup_toggle(self,checkmenuitem,*args):
712 _v = checkmenuitem.get_active()
713 self.prefs.setBoolPref("SolverReporter","show_popup",_v)
714 print "SET TO",_v
715
716 def on_close_on_converged_toggle(self,checkmenuitem,*args):
717 _v = checkmenuitem.get_active()
718 self.prefs.setBoolPref("SolverReporter","close_on_converged",_v)
719
720 def on_close_on_nonconverged_toggle(self,checkmenuitem,*args):
721 _v = checkmenuitem.get_active()
722 self.prefs.setBoolPref("SolverReporter","close_on_nonconverged",_v)
723
724 def on_show_variables_near_bounds_activate(self,*args):
725 _epsilon = 1e-4;
726 _vars = self.sim.getVariablesNearBounds(_epsilon)
727 print "VARIABLES NEAR BOUNDS"
728 for _v in _vars:
729 print _v.getName();
730
731 # --------------------------------------------
732 # MODULE LIST
733
734 def module_activated(self, treeview, path, column, *args):
735 modules = self.library.getModules()
736 print "PATH",path
737 if len(path)==1:
738 self.reporter.reportNote("Launching of external editor not yet implemented")
739 elif len(path)==2:
740 if(self.modtank.has_key(path)):
741 _type = self.modtank[path];
742 self.reporter.reportNote("Creating simulation for type %s" % str(_type.getName()) )
743 self.do_sim(_type)
744 else:
745 self.reporter.reportError("Didn't find type corresponding to row")
746
747 # ----------------------------------
748 # ERROR PANEL
749
750 def get_error_row_data(self,sev,filename,line,msg):
751 _sevicon = {
752 0: self.iconok
753 ,1: self.iconinfo
754 ,2: self.iconwarning
755 ,3: self.iconerror
756 ,4: self.iconinfo
757 ,5: self.iconwarning
758 ,6: self.iconerror
759 }[sev]
760
761 _fontweight = pango.WEIGHT_NORMAL
762 if sev==6:
763 _fontweight = pango.WEIGHT_BOLD
764
765 _fgcolor = "black"
766 if sev==4:
767 _fgcolor = "#888800"
768 elif sev==5:
769 _fgcolor = "#884400"
770 elif sev==6:
771 _fgcolor = "#880000"
772 elif sev==0:
773 _fgcolor = BROWSER_FIXED_COLOR
774
775 if not filename and not line:
776 _fileline = ""
777 else:
778 if(len(filename) > 25):
779 filename = "..."+filename[-22:]
780 _fileline = filename + ":" + str(line)
781
782 _res = [_sevicon,_fileline,msg.rstrip(),_fgcolor,_fontweight]
783 #print _res
784 return _res
785
786 def error_callback(self,sev,filename,line,msg):
787 pos = self.errorstore.append(None, self.get_error_row_data(sev, filename,line,msg))
788 path = self.errorstore.get_path(pos)
789 col = self.errorview.get_column(3)
790 self.errorview.scroll_to_cell(path,col)
791
792 return 0;
793
794 # --------------------------------
795 # BUTTON METHODS
796
797 def open_click(self,*args):
798 #print_loading_status("CURRENT FILEOPENPATH is",self.fileopenpath)
799 dialog = gtk.FileChooserDialog("Open ASCEND model...",
800 self.window,
801 gtk.FILE_CHOOSER_ACTION_OPEN,
802 (gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL, gtk.STOCK_OPEN, gtk.RESPONSE_OK)
803 )
804 dialog.set_current_folder(self.fileopenpath)
805 dialog.set_default_response(gtk.RESPONSE_OK)
806 dialog.set_transient_for(self.window)
807 dialog.set_modal(True)
808
809 filter = gtk.FileFilter()
810 filter.set_name("*.a4c, *.a4l")
811 filter.add_pattern("*.[Aa]4[Cc]")
812 filter.add_pattern("*.[Aa]4[Ll]")
813 dialog.add_filter(filter)
814
815 filter = gtk.FileFilter()
816 filter.set_name("All files")
817 filter.add_pattern("*")
818 dialog.add_filter(filter)
819
820 response = dialog.run()
821 _filename = dialog.get_filename()
822 print "\nFILENAME SELECTED:",_filename
823
824 _path = dialog.get_current_folder()
825 if _path:
826 self.fileopenpath = _path
827
828 dialog.hide()
829
830 if response == gtk.RESPONSE_OK:
831 self.reporter.reportNote("File %s selected." % dialog.get_filename() )
832 self.library.clear()
833 self.do_open( _filename)
834
835 def reload_click(self,*args):
836 _type = None
837 if(self.sim):
838 _type = self.sim.getType().getName().toString();
839
840 self.library.clear()
841 self.do_open(self.filename)
842
843 if _type:
844 _t = self.library.findType(_type)
845 self.do_sim(_t)
846
847 def props_activate(self,widget,*args):
848 return self.modelview.props_activate(self,widget,*args)
849
850 def observe_activate(self,widget,*args):
851 return self.modelview.observe_activate(self,widget,*args)
852
853 def solve_click(self,*args):
854 #self.reporter.reportError("Solving simulation '" + self.sim.getName().toString() +"'...")
855 self.do_solve()
856
857 def console_click(self,*args):
858 try:
859 console.start(self)
860 except RuntimeError,e:
861 self.reporter.reportError("Unable to start console: "+str(e));
862
863 def integrate_click(self,*args):
864 self.do_integrate()
865
866 def check_click(self,*args):
867 self.do_check()
868 #self.reporter.reportError("CHECK clicked")
869
870 def preferences_click(self,*args):
871 if not self.sim:
872 self.reporter.reportError("No simulation created yet!");
873
874 _paramswin = SolverParametersWindow(self)
875 _paramswin.show()
876
877 def methodrun_click(self,*args):
878 _sel = self.methodsel.get_active_text()
879 if _sel:
880 _method = None
881 _methods = self.sim.getType().getMethods()
882 for _m in _methods:
883 if _m.getName()==_sel:
884 _method = _m
885 if not _method:
886 self.reporter.reportError("Method is not valid")
887 return
888 self.do_method(_method)
889 else:
890 self.reporter.reportError("No method selected")
891
892 def auto_toggle(self,button,*args):
893 self.is_auto = button.get_active()
894 self.automenu.set_active(self.is_auto)
895
896 if self.is_auto:
897 self.reporter.reportSuccess("Auto mode is now ON")
898 else:
899 self.reporter.reportSuccess("Auto mode is now OFF")
900
901 def on_file_quit_click(self,*args):
902 self.do_quit()
903
904 def on_tools_auto_toggle(self,checkmenuitem,*args):
905 self.is_auto = checkmenuitem.get_active()
906 self.autotoggle.set_active(self.is_auto)
907
908 def on_help_about_click(self,*args):
909 _xml = gtk.glade.XML(self.glade_file,"aboutdialog")
910 _about = _xml.get_widget("aboutdialog")
911 _about.set_position(gtk.WIN_POS_CENTER_ON_PARENT)
912 _about.set_transient_for(self.window);
913 _about.set_version(config.VERSION)
914 _about.run()
915 _about.destroy()
916
917 def on_help_contents_click(self,*args):
918 _help = Help(HELP_ROOT)
919 _help.run()
920
921 def on_find_fixable_variables_activate(self,*args):
922 v = self.sim.getFixableVariables()
923 for var in v:
924 print "FIXABLE:",var
925
926 def create_observer(self,name=None):
927 if name==None:
928 name="New Observer"
929
930 _xml = gtk.glade.XML(self.glade_file,"observervbox");
931 _label = gtk.Label();
932 _label.set_text(name)
933 _tab = self.maintabs.append_page(_xml.get_widget("observervbox"),_label);
934 self.observers.append(ObserverTab(_xml, name, self, _tab))
935
936 def sync_observers(self):
937 for _o in self.observers:
938 _o.sync()
939
940 def delete_event(self, widget, event):
941 self.do_quit()
942 return False
943
944 def observe(self,instance):
945 if len(self.observers) > 1:
946 self.reporter.reportError("Not implemented: multiple observers (currently %d observers)" %
947 len(self.observers) )
948 return
949 if len(self.observers) ==0:
950 self.create_observer()
951 _observer = self.observers[0]
952 _observer.add_instance(instance)
953
954 if __name__ == "__main__":
955 b = Browser();
956 b.run()

john.pye@anu.edu.au
ViewVC Help
Powered by ViewVC 1.1.22