def loadLog(menuitem, filename, checkpoints): if gtklogger.replaying(): raise ooferror.ErrUserError( "Multiple GUI logs cannot be replayed simultaneously!") debug.fmsg("Loading gui script", filename) menuitem.root().setOption('post_hook', menucheckpoint) dblevel = 0 if debug.debug(): dblevel = 3 #dblevel = 4 global _replaying _replaying = True # When replaying, we have to make sure that progress bars *always* # appear, so we set the delay time to 0. If the delay time is # non-zero, then a script recorded on a slow machine would insert # a checkpoint for opening the activity viewer window, but a # faster machine might never open the window, and would wait # forever for the checkpoint when replaying the script. progressbar_delay.set_delay(None, 0) gtklogger.replay(filename, beginCB=activityViewer.openActivityViewer, finishCB=logFinished, debugLevel=dblevel, threaded=thread_enable.query(), exceptHook=loggererror, checkpoints=checkpoints)
def loadLog(menuitem, filename, checkpoints): if gtklogger.replaying(): raise ooferror.ErrUserError( "Multiple GUI logs cannot be replayed simultaneously!") debug.fmsg("Loading gui script", filename) menuitem.root().setOption('post_hook', menucheckpoint) dblevel = 0 if debug.debug(): dblevel = 3 #dblevel = 4 global _replaying _replaying = True # When replaying, we have to make sure that progress bars *always* # appear, so we set the delay time to 0. If the delay time is # non-zero, then a script recorded on a slow machine would insert # a checkpoint for opening the activity viewer window, but a # faster machine might never open the window, and would wait # forever for the checkpoint when replaying the script. progressbar_delay.set_delay(None, 0) gtklogger.replay( filename, beginCB=activityViewer.openActivityViewer, finishCB=logFinished, debugLevel=dblevel, threaded=thread_enable.query(), exceptHook=loggererror, checkpoints=checkpoints)
def startLog(menuitem, filename, use_gui):#Passing the use_gui parameter to show the loggergui gtklogger.reset_checkpoints() menuitem.root().setOption('post_hook', menucheckpoint) if debug.debug(): dblevel = 3 else: dblevel = 0 global _recording _recording = True gtklogger.start(filename, debugLevel=dblevel, logger_comments=use_gui)
def startLog(menuitem, filename, use_gui): #Passing the use_gui parameter to show the loggergui gtklogger.reset_checkpoints() menuitem.root().setOption('post_hook', menucheckpoint) if debug.debug(): dblevel = 3 else: dblevel = 0 global _recording _recording = True gtklogger.start(filename, debugLevel=dblevel, logger_comments=use_gui)
def _append(self, type, *args): message = string.join([str(x) for x in args], ' ') MessageManager.lock.acquire() try: if debug.debug() and type!="Log" and guitop.top(): print message self.message_list.append( (message, type) ) if self.flag_dict[type]: self._write(message) finally: MessageManager.lock.release() switchboard.notify( "write message", (message, type) ) return message
def sensitize(self): debug.mainthreadTest() # Back, Jump, Done self.backbutton.set_sensitive(self.index != 0) self.jumpbutton.set_sensitive(self.index != self.progress) # Next self.nextbutton.set_sensitive(1) # Default if self.index == self.progress: if self.lesson.signal and not self.signalReceived \ and not debug.debug(): self.nextbutton.set_sensitive(0) if self.lesson == self.tutor.lessons[-1]: # the last one? self.nextbutton.set_sensitive(0)
def _append(self, type, *args): message = ' '.join([str(x) for x in args]) self.lock.acquire() try: if debug.debug() and type!="Log" and guitop.top(): print message self.message_list.append( (message, type) ) if self.flag_dict[type]: self._write(message) finally: self.lock.release() switchboard.notify( "write message", (message, type) ) return message
def gui_printTraceBack(e_type, e_value, tbacklist): # If the mainloop isn't running yet, just display to the terminal. # In debugging mode, always display to the terminal. if debug.debug() or not guitop.getMainLoop(): excepthook.printTraceBack(e_type, e_value, tbacklist) if guitop.getMainLoop(): # Transfer control to the main thread to report errors in the GUI. res = mainthread.runBlock(errorpopup_, (e_type, e_value, tbacklist)) if res == ErrorPopUp.ABORT: from ooflib.common.IO.GUI import quit if not mainthread.runBlock(quit.queryQuit, kwargs=dict(exitstatus=1)): sys.exc_clear() # quitting was cancelled else: # Not aborting. Clear the exception because it can # contain references to objects and prevent garbage # collection. sys.exc_clear()
def log(self, strng): self.loglock.acquire() try: if debug.debug() and not self.quiet: global debugcounter if len(strng) < 1000: dstr = strng else: dstr = strng[:80] + '...' + strng[-20:] debug.msg("====%04d===="%debugcounter, dstr) debugcounter += 1 if self._loghalted == 0: self._logchanged = 1 self.logbook.append(strng+'\n') for logger in self.loggers: logger(strng) finally: self.loglock.release()
def startLog(menuitem, filename, use_gui): #Passing the use_gui parameter to show the loggergui gtklogger.reset_checkpoints() menuitem.root().setOption('post_hook', menucheckpoint) if debug.debug(): dblevel = 3 else: dblevel = 0 global _recording _recording = True #if use_gui: # loggui = os.popen("python -m loggergui " + filename, "w") # gtklogger.start(loggui, debugLevel=dblevel) #else: # gtklogger.start(filename, debugLevel=dblevel) #debug.fmsg() #debug.dumpTrace() gtklogger.start( filename, debugLevel=dblevel, logger_comments=use_gui ) # Passing the logger_comments parameter to show the loggergui
def rerecordLog(menuitem, filename, checkpoints, use_gui): if gtklogger.replaying(): raise ooferror.ErrUserError( "Multiple GUI logs cannot be replayed simultaneously!") menuitem.root().setOption('post_hook', menucheckpoint) dblevel = 0 if debug.debug(): dblevel = 3 #dblevel = 4 global _replaying, _recording _replaying = True _recording = True progressbar_delay.set_delay(None, 0) # Find a suitable new name for the backup copy of the old log # file. Just append ".bak", but if that file already exists, # append ".bakX", where X is an integer. if not os.path.exists(filename + '.bak'): backupname = filename + '.bak' else: backupname = None count = 2 while not backupname: trialname = "%s.bak%d" % (filename, count) if not os.path.exists(trialname): backupname = trialname count += 1 os.system('cp ' + filename + ' ' + backupname) debug.fmsg("Loading gui script", backupname) gtklogger.replay( backupname, beginCB=activityViewer.openActivityViewer, finishCB=logFinished, debugLevel=dblevel, threaded=thread_enable.query(), exceptHook=loggererror, rerecord=filename, checkpoints=checkpoints, logger_comments=use_gui ) #Passing the logger_comments parameter to show the loggergui
def rerecordLog(menuitem, filename, checkpoints, use_gui): if gtklogger.replaying(): raise ooferror.ErrUserError( "Multiple GUI logs cannot be replayed simultaneously!") menuitem.root().setOption('post_hook', menucheckpoint) dblevel = 0 if debug.debug(): dblevel = 3 #dblevel = 4 global _replaying, _recording _replaying = True _recording = True progressbar_delay.set_delay(None, 0) # Find a suitable new name for the backup copy of the old log # file. Just append ".bak", but if that file already exists, # append ".bakX", where X is an integer. if not os.path.exists(filename + '.bak'): backupname = filename + '.bak' else: backupname = None count = 2 while not backupname: trialname = "%s.bak%d" % (filename, count) if not os.path.exists(trialname): backupname = trialname count += 1 os.system('cp '+filename+' '+backupname) debug.fmsg("Loading gui script", backupname) gtklogger.replay( backupname, beginCB=activityViewer.openActivityViewer, finishCB=logFinished, debugLevel=dblevel, threaded=thread_enable.query(), exceptHook=loggererror, rerecord=filename, checkpoints=checkpoints, logger_comments=use_gui) #Passing the logger_comments parameter to show the loggergui
discussion= """ <para>Tools for figuring out what's going on when it's not going well. Mostly of interest to the developers.</para> """ )) def set_debug(menuitem, state): if state: debug.set_debug_mode() else: debug.clear_debug_mode() debugmenu.addItem(CheckOOFMenuItem( 'Debug', debug.debug(), callback=set_debug, help='Turn debugging mode on and off.', discussion=xmlmenudump.loadFile('DISCUSSIONS/common/menu/debug.xml') )) debugmenu.addItem(CheckOOFMenuItem( 'Verbose_Switchboard', switchboard.switchboard.verbose, callback=switchboard.verbose, help='Print all switchboard calls as they occur.', discussion=xmlmenudump.loadFile('DISCUSSIONS/common/menu/verbosesb.xml') )) def setWarnPopups(menuitem, value): reporter.messagemanager.set_warning_pop_up(value)
def front_end(no_interp=None): global startupfiles global gtk_options global randomseed ## From here on is the serial version. # When loading modules, use utils.OOFexec so that names are # imported into the oof environment, not the oof.run environment. if not (runtimeflags.text_mode or config.no_gui()): # The gtk import dance described below doesn't work when the program # has been packaged by cx_freeze. # TODO LATER: is checking frozen required for gtk2? frozen = hasattr(sys, 'frozen') if not frozen: import pygtk pygtk.require("2.0") import gtk msg = gtk.check_version(2, 6, 0) if msg: print msg sys.exit(3) import ooflib.common.IO.GUI.initialize # temporarily disable the engine, tutorials, orientationmap # for 3D development import ooflib.engine.IO.GUI.initialize import ooflib.image.IO.GUI.initialize if config.dimension() == 2: import ooflib.orientationmap.GUI.initialize import ooflib.tutorials.initialize if replaydelay is not None: from ooflib.common.IO.GUI import gtklogger gtklogger.set_delay(int(replaydelay)) else: # text mode import ooflib.common.initialize import ooflib.engine.initialize import ooflib.image.initialize if config.dimension() == 2: import ooflib.orientationmap.initialize import ooflib.EXTENSIONS.initialize # The random number generator must be seeded *after* the gui has # been started, because libfontconfig is using random numbers. We # want the numbers to be the same in text and gui modes, so that # the test suite gets predictable answers. if debug.debug() or randomseed is not None: if randomseed is None: randomseed = 17 random.seed(randomseed) crandom.rndmseed(randomseed) for module in startupimports: exec('import ' + module) if not (runtimeflags.text_mode or config.no_gui()): reporter.report("Welcome to OOF2 version %s!" % oofversion.version) ## The files to be loaded must be loaded *after* the GUI ## starts, but this routine doesn't regain control once it ## starts the GUI. So we have to install the file loader ## (loadStartUpFiles) as an idle callback, which will run on ## the main thread. loadStartUpFiles just issues menu ## commands that load the files, and if it runs on the main ## thread those menu commands will run by Workers on ## subthreads, and won't be run sequentially. So, instead of ## installing loadStartUpFiles as an idle callback, we install ## subthread.execute and have it call loadStartUpFiles, since ## workers on subthreads don't create additional subthreads to ## run their menu items. if startupfiles: # startupfiles won't be run until after the GUI starts. mainthread.run(subthread.execute_immortal, (loadStartUpFiles, (startupfiles, ))) if not no_interp: # Default case, run on local thread. from ooflib.common.IO.GUI import oofGUI oofGUI.start() # This call never returns. print "This line should never be printed. rank =", _rank else: # TODO LATER: The gui and no_interp combination is # thinkable, but has problems. You have to run the GUI on # a separate thread, but then exceptions show up as modal # dialog boxes in the GUI, and block the menu items which # raised them, causing a loss of control. Also, the # current threading scheme requires that all gtk activity # happen on the main thread. print "GUI no_interp mode not implemented. Sorry." raise NotImplementedError("GUI no_interp mode") else: # text mode from ooflib.common import quit # Allow exceptions to propagate to the user if in batch mode # or not running an interpreter. Otherwise, exceptions are # caught and reported to the user, but the program keeps # running. if runtimeflags.batch_mode or no_interp: from ooflib.common import worker worker.propagate_exceptions = True if startupfiles: loadStartUpFiles(startupfiles) if runtimeflags.batch_mode: # Batch mode runs startupfiles and quits immediately. quit.set_quiet() quit.quit() if sys.exc_info()[0] is not None: sys.exit(1) sys.exit(0) # Format the banner for the current line width. if not quit.quiet(): width = utils.screenwidth() wiggles = "//=*=\\\\=*=" nwiggles = (width - 2) / len(wiggles) welcome = "Welcome to OOF2 version %s!" % oofversion.version nblanks = (width - len(welcome)) / 2 banner = wiggles*nwiggles + "//\n\n" \ + " "*nblanks + welcome + "\n" + \ string.join(utils.format(banner1, width),"\n") + \ "\n\n" + wiggles*nwiggles + "//\n" + \ string.join(utils.format(banner2, width), "\n") else: banner = "" if not no_interp: import code # Try to import readline, which allows command line # editing in text mode. If it's not there, don't worry -- # it's possible to live without it. Some systems don't # seem to have it, although it's supposedly available on # all Unix systems. try: import readline except ImportError: pass # Start up the interpreter in the __main__ namespace. # This is the namespace that utils.OOFeval and OOFdefine # use. It's not necessarily *this* namespace. interp = code.InteractiveConsole(sys.modules['__main__'].__dict__) interp.interact(banner)
1000, tip="Maximum number of iterations to perform.") ], tip="Conjugate Gradient method for iteratively solving symmetric matrices.", discussion=xmlmenudump.loadFile('DISCUSSIONS/engine/reg/cg.xml')) def check_symmetry(menuitem, state): global _check_symmetry _check_symmetry = state mainmenu.debugmenu.addItem( oofmenu.CheckOOFMenuItem( 'Check_CG_symmetry', debug.debug(), callback=check_symmetry, help='Verify matrix symmetry before using Conjugate Gradient.', discussion="<para>For debugging. Slow.</para>")) #=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=# class BiConjugateGradient(PreconditionedMatrixMethod): def __init__(self, preconditioner, tolerance, max_iterations): self.preconditioner = preconditioner self.tolerance = tolerance self.max_iterations = max_iterations def solveMatrix(self, matrix, rhs, solution): pc = self.preconditioner.create_preconditioner(matrix)
tip="Largest acceptable relative error in the matrix solution."), parameter.IntParameter( "max_iterations", 1000, tip="Maximum number of iterations to perform.")], tip="Conjugate Gradient method for iteratively solving symmetric matrices.", discussion=xmlmenudump.loadFile('DISCUSSIONS/engine/reg/cg.xml') ) def check_symmetry(menuitem, state): global _check_symmetry _check_symmetry = state mainmenu.debugmenu.addItem( oofmenu.CheckOOFMenuItem( 'Check_CG_symmetry', debug.debug(), callback=check_symmetry, help='Verify matrix symmetry before using Conjugate Gradient.', discussion="<para>For debugging. Slow.</para>")) #=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=##=--=# class BiConjugateGradient(PreconditionedMatrixMethod): def __init__(self, preconditioner, tolerance, max_iterations): self.preconditioner = preconditioner self.tolerance = tolerance self.max_iterations = max_iterations def solveMatrix(self, matrix, rhs, solution): pc = self.preconditioner.create_preconditioner(matrix) return cmatrixmethods.solveBiCG( matrix, rhs, pc,
<para>Tools for figuring out what's going on when it's not going well. Mostly of interest to the developers.</para> """)) def set_debug(menuitem, state): if state: debug.set_debug_mode() else: debug.clear_debug_mode() debugmenu.addItem( CheckOOFMenuItem( 'Debug', debug.debug(), callback=set_debug, help='Turn debugging mode on and off.', discussion=xmlmenudump.loadFile('DISCUSSIONS/common/menu/debug.xml'))) debugmenu.addItem( CheckOOFMenuItem('Verbose_Switchboard', switchboard.switchboard.verbose, callback=switchboard.verbose, help='Print all switchboard calls as they occur.', discussion=xmlmenudump.loadFile( 'DISCUSSIONS/common/menu/verbosesb.xml'))) debugmenu.addItem( OOFMenuItem("Dump_Switchboard", callback=switchboard.dump,
def subScriptErrorHandler(e_type, e_value, tbacklist): _savedExceptions.append((e_type, e_value, tbacklist)) if debug.debug() or not guitop.getMainLoop(): excepthook.printTraceBack(e_type, e_value, tbacklist)
def front_end(no_interp=None): global startupfiles global gtk_options global randomseed ## From here on is the serial version. # VTK is started even in text mode to allow off-screen rendering, # interpretation of scripted mouse clicks, etc. from ooflib.SWIG.common.IO import vtkutils vtkutils.initialize_vtk() # When loading modules, use utils.OOFexec so that names are # imported into the oof environment, not the oof.run environment. if not (runtimeflags.text_mode or config.no_gui()): # The gtk import dance described below doesn't work when the program # has been packaged by cx_freeze. # TODO 3.1: is checking frozen required for gtk2? frozen = hasattr(sys, 'frozen') if not frozen: import pygtk pygtk.require("2.0") import gtk msg = gtk.check_version(2, 6, 0) if msg: print msg sys.exit(3) # The GUI initialization modules must be called before any # calls to mainthread.run(), because mainthread.run() is # redefined when mainthreadGUI.py is loaded (by # common/IO/GUI/initialize.py) import ooflib.common.IO.GUI.initialize import ooflib.engine.IO.GUI.initialize import ooflib.image.IO.GUI.initialize import ooflib.orientationmap.GUI.initialize import ooflib.tutorials.initialize if replaydelay is not None: from ooflib.common.IO.GUI import gtklogger gtklogger.set_delay(int(replaydelay)) else: # text mode # Load non-gui initialization modules. import ooflib.common.initialize import ooflib.engine.initialize import ooflib.image.initialize import ooflib.orientationmap.initialize import ooflib.EXTENSIONS.initialize # The random number generator must be seeded *after* the gui has # been started, because libfontconfig is using random numbers. We # want the numbers to be the same in text and gui modes, so that # the test suite gets predictable answers. if debug.debug() or randomseed is not None: if randomseed is None: randomseed = 17 random.seed(randomseed) crandom.rndmseed(randomseed) for module in startupimports: exec('import ' + module) if not (runtimeflags.text_mode or config.no_gui()): reporter.report("Welcome to %s version %s!" % (program_name.upper(), oofversion.version)) if not no_interp: # Default case, run on local thread. from ooflib.common.IO.GUI import oofGUI oofGUI.start(files=startupfiles) # This call never returns. print "This line should never be printed. rank =", _rank else: # TODO 3.1: The gui and no_interp combination is # thinkable, but has problems. You have to run the GUI on # a separate thread, but then exceptions show up as modal # dialog boxes in the GUI, and block the menu items which # raised them, causing a loss of control. Also, the # current threading scheme requires that all gtk activity # happen on the main thread. print "GUI no_interp mode not implemented. Sorry." raise NotImplementedError("GUI no_interp mode") else: # text mode from ooflib.common import quit # Allow exceptions to propagate to the user if in batch mode # or not running an interpreter. Otherwise, exceptions are # caught and reported to the user, but the program keeps # running. if runtimeflags.batch_mode or no_interp: from ooflib.common import worker worker.propagate_exceptions = True threadstate.textMode() lock.disableLocks() # disables Locks, but not SLocks if startupfiles: loadStartUpFiles(startupfiles) if runtimeflags.batch_mode: # Batch mode runs startupfiles and quits immediately. quit.set_quiet() quit.quit() if sys.exc_info()[0] is not None: sys.exit(1) sys.exit(0) # Format the banner for the current line width. if not quit.quiet(): width = utils.screenwidth() wiggles = "//=*=\\\\=*=" nwiggles = (width - 2) / len(wiggles) welcome = "Welcome to %s version %s!" % (program_name.upper(), oofversion.version) nblanks = (width - len(welcome)) / 2 banner = ( wiggles * nwiggles + "//\n\n" + " " * nblanks + welcome + "\n" + string.join( utils.format(banner1 % {'name': program_name.upper()}, width), "\n") + "\n\n" + wiggles * nwiggles + "//\n" + string.join( utils.format(banner2 % {'name': program_name.upper()}, width), "\n")) else: banner = "" if not no_interp: import code # Try to import readline, which allows command line # editing in text mode. If it's not there, don't worry -- # it's possible to live without it. Some systems don't # seem to have it, although it's supposedly available on # all Unix systems. try: import readline except ImportError: pass # Start up the interpreter in the __main__ namespace. # This is the namespace that utils.OOFeval and OOFdefine # use. It's not necessarily *this* namespace. interp = code.InteractiveConsole(sys.modules['__main__'].__dict__) interp.interact(banner)
def refinement(self, skeleton, newSkeleton, context, prog): maxdelta = max(newSkeleton.MS.sizeOfPixels()) maxdelta2 = (self.min_distance * maxdelta)**2 markedEdges = SnapEdgeMarkings(newSkeleton, skeleton, maxdelta2) self.newEdgeNodes = {} # allows sharing of new edge nodes # Primary marking (bisections only!) self.targets(skeleton, context, 1, markedEdges, self.criterion) # Additional marking #self.degree.markExtras(skeleton, markedEdges) # Refine elements and segments segmentdict = {} # which segments have been handled n = len(skeleton.elements) elements = skeleton.elements for ii in range(n): #print ii, n oldElement = elements[ii] oldnnodes = oldElement.nnodes() # For 2D: # Get list of number of subdivisions on each edge ("marks") (numinitmarks,marks,cats,edgenodes) = \ markedEdges.getSnapMarks(oldElement) # Find the canonical order for the marks. (The order is # ambiguous due to the arbitrary choice of the starting # edge. Finding the canonical order allows the refinement # rule to be found in the rule table.) rotation is the # offset into the elements node list required to match the # refinement rule to the element's marked edges. # signature is the canonical ordering of the marks. #rotation, signature = findSignature(marks) signature_info = findSignature(marks) if config.dimension() == 2: signature = signature_info[1] elif config.dimension() == 3: signature = signature_info #print numinitmarks, signature # Create new elements # TODO: It's annoying that we have a separate # "unrefinedelement" method. It would be cleaner if this # were called automatically using the signature. We # should do this when we move things to C. if numinitmarks > 0: newElements = self.rules[signature].apply( oldElement, signature_info, cats, edgenodes, newSkeleton, maxdelta2) if debug.debug(): for el in newElements: if el.illegal(): debug.fmsg("oldElement=", oldElement) debug.fmsg( [n.position() for n in oldElement.nodes]) debug.fmsg("newElement=", el) debug.fmsg([n.position() for n in el.nodes]) debug.fmsg("signature=", signature) debug.fmsg("rule=", self.rules[signature]) raise ooferror2.ErrPyProgrammingError( "Illegal element created by SnapRefine") else: newElements = snaprefinemethod.unrefinedelement( oldElement, signature_info, newSkeleton) # If the old element's homogeneity is 1, it's safe to say that # new elements' homogeneities are 1. if oldElement.homogeneity(skeleton.MS, False) == 1.0: for el in newElements: el.copyHomogeneity(oldElement) # The calls to Skeleton.newElement() made by the # refinement rules have created new SkeletonSegments in # newSkeleton, but have not set the parentage of those # segments. We have to fix that here. for newElement in newElements: for segment in newElement.getSegments(newSkeleton): # Only look at each segment once. if segment not in segmentdict: segmentdict[segment] = 1 pseg = findParentSegment(skeleton, newElement, segment, edgenodes) if pseg: pseg.add_child(segment) segment.add_parent(pseg) if prog.stopped(): return None prog.setFraction(1.0 * (ii + 1) / n) prog.setMessage("%d/%d elements" % (ii + 1, n)) newSkeleton.cleanUp() #print "end of refinement" return newSkeleton
def front_end(no_interp=None): global startupfiles global gtk_options global randomseed ## From here on is the serial version. # When loading modules, use utils.OOFexec so that names are # imported into the oof environment, not the oof.run environment. if not (runtimeflags.text_mode or config.no_gui()): # The gtk import dance described below doesn't work when the program # has been packaged by cx_freeze. # TODO LATER: is checking frozen required for gtk2? frozen = hasattr(sys, 'frozen') if not frozen: import pygtk pygtk.require("2.0") import gtk msg = gtk.check_version(2, 6, 0) if msg: print msg sys.exit(3) import ooflib.common.IO.GUI.initialize # temporarily disable the engine, tutorials, orientationmap # for 3D development import ooflib.engine.IO.GUI.initialize import ooflib.image.IO.GUI.initialize if config.dimension() == 2: import ooflib.orientationmap.GUI.initialize import ooflib.tutorials.initialize if replaydelay is not None: from ooflib.common.IO.GUI import gtklogger gtklogger.set_delay(int(replaydelay)) else: # text mode import ooflib.common.initialize import ooflib.engine.initialize import ooflib.image.initialize if config.dimension() == 2: import ooflib.orientationmap.initialize import ooflib.EXTENSIONS.initialize # The random number generator must be seeded *after* the gui has # been started, because libfontconfig is using random numbers. We # want the numbers to be the same in text and gui modes, so that # the test suite gets predictable answers. if debug.debug() or randomseed is not None: if randomseed is None: randomseed = 17 random.seed(randomseed) crandom.rndmseed(randomseed) for module in startupimports: exec('import ' + module) if not (runtimeflags.text_mode or config.no_gui()): reporter.report("Welcome to OOF2 version %s!" % oofversion.version) ## The files to be loaded must be loaded *after* the GUI ## starts, but this routine doesn't regain control once it ## starts the GUI. So we have to install the file loader ## (loadStartUpFiles) as an idle callback, which will run on ## the main thread. loadStartUpFiles just issues menu ## commands that load the files, and if it runs on the main ## thread those menu commands will run by Workers on ## subthreads, and won't be run sequentially. So, instead of ## installing loadStartUpFiles as an idle callback, we install ## subthread.execute and have it call loadStartUpFiles, since ## workers on subthreads don't create additional subthreads to ## run their menu items. if startupfiles: # startupfiles won't be run until after the GUI starts. mainthread.run(subthread.execute_immortal, (loadStartUpFiles, (startupfiles,))) if not no_interp: # Default case, run on local thread. from ooflib.common.IO.GUI import oofGUI oofGUI.start() # This call never returns. print "This line should never be printed. rank =", _rank else: # TODO LATER: The gui and no_interp combination is # thinkable, but has problems. You have to run the GUI on # a separate thread, but then exceptions show up as modal # dialog boxes in the GUI, and block the menu items which # raised them, causing a loss of control. Also, the # current threading scheme requires that all gtk activity # happen on the main thread. print "GUI no_interp mode not implemented. Sorry." raise NotImplementedError("GUI no_interp mode") else: # text mode from ooflib.common import quit # Allow exceptions to propagate to the user if in batch mode # or not running an interpreter. Otherwise, exceptions are # caught and reported to the user, but the program keeps # running. if runtimeflags.batch_mode or no_interp: from ooflib.common import worker worker.propagate_exceptions = True if startupfiles: loadStartUpFiles(startupfiles) if runtimeflags.batch_mode: # Batch mode runs startupfiles and quits immediately. quit.set_quiet() quit.quit() if sys.exc_info()[0] is not None: sys.exit(1) sys.exit(0) # Format the banner for the current line width. if not quit.quiet(): width = utils.screenwidth() wiggles = "//=*=\\\\=*=" nwiggles = (width-2)/len(wiggles) welcome = "Welcome to OOF2 version %s!" % oofversion.version nblanks = (width - len(welcome))/2 banner = wiggles*nwiggles + "//\n\n" \ + " "*nblanks + welcome + "\n" + \ string.join(utils.format(banner1, width),"\n") + \ "\n\n" + wiggles*nwiggles + "//\n" + \ string.join(utils.format(banner2, width), "\n") else: banner = "" if not no_interp: import code # Try to import readline, which allows command line # editing in text mode. If it's not there, don't worry -- # it's possible to live without it. Some systems don't # seem to have it, although it's supposedly available on # all Unix systems. try: import readline except ImportError: pass # Start up the interpreter in the __main__ namespace. # This is the namespace that utils.OOFeval and OOFdefine # use. It's not necessarily *this* namespace. interp = code.InteractiveConsole(sys.modules['__main__'].__dict__) interp.interact(banner)