コード例 #1
0
    def init_gui(self):
        """
        Do changes to the GUI while entering this mode. This includes opening 
        the property manager, updating the command toolbar, connecting widget 
        slots etc. 

        Called once each time the mode is entered; should be called only by code 
        in modes.py

        @see: L{self.restore_gui}
        """
        self.enable_gui_actions(False)
        self.dont_update_gui = True
        self.pastable = None

        if not self.propMgr:
            self.propMgr = PastePropertyManager(self)
            changes.keep_forever(self.propMgr)

        self.propMgr.show()

        self.connect_or_disconnect_signals(True)
        self.updateCommandToolbar(bool_entering=True)

        #Following is required to make sure that the
        #clipboard groupbox in paste mode is updated
        #(This is done by calling depositeMode.update_gui method
        #Not only that, but the above mentioned method also defines
        #self.pastable_list which is needed to paste items! This needs a
        #separate code clean up in depositmode.py -- Ninad 20070827
        self.dont_update_gui = False
コード例 #2
0
 def init_gui(self):
     """
     Initialize GUI for this mode 
     """
     previousCommand = self.commandSequencer.prevMode 
     if previousCommand.commandName == 'BUILD_DNA':
         try:
             self.flyoutToolbar = previousCommand.flyoutToolbar
             #Need a better way to deal with changing state of the 
             #corresponding action in the flyout toolbar. To be revised 
             #during command toolbar cleanup 
             self.flyoutToolbar.makeCrossoversAction.setChecked(True)
         except AttributeError:
             self.flyoutToolbar = None
     
     if self.propMgr is None:
         self.propMgr = MakeCrossovers_PropertyManager(self)
         #@bug BUG: following is a workaround for bug 2494.
         #This bug is mitigated as propMgr object no longer gets recreated
         #for modes -- niand 2007-08-29
         changes.keep_forever(self.propMgr)  
         
     #Now set the initial segment list. The segments within this segment list
     #will be searched for the crossovers. 
     selectedSegments = self.win.assy.getSelectedDnaSegments()        
     self.ensureSegmentListItemsWithinLimit(selectedSegments)
             
     self.propMgr.show()    
コード例 #3
0
ファイル: PasteMode.py プロジェクト: ematvey/NanoEngineer-1
    def init_gui(self):
        """
        Do changes to the GUI while entering this mode. This includes opening 
        the property manager, updating the command toolbar, connecting widget 
        slots etc. 

        Called once each time the mode is entered; should be called only by code 
        in modes.py

        @see: L{self.restore_gui}
        """
        self.enable_gui_actions(False)
        self.dont_update_gui = True
        self.pastable = None 

        if not self.propMgr:
            self.propMgr = PastePropertyManager(self)
            changes.keep_forever(self.propMgr)

        self.propMgr.show()     

        self.connect_or_disconnect_signals(True)
        self.updateCommandToolbar(bool_entering = True)

        #Following is required to make sure that the 
        #clipboard groupbox in paste mode is updated 
        #(This is done by calling depositeMode.update_gui method 
        #Not only that, but the above mentioned method also defines 
        #self.pastable_list which is needed to paste items! This needs a 
        #separate code clean up in depositmode.py -- Ninad 20070827
        self.dont_update_gui = False
コード例 #4
0
    def init_gui(self):
        """
        Initialize GUI for this mode 
        """
        if self.propMgr is None:
            self.propMgr = StereoProperties_PropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494.
            #This bug is mitigated as propMgr object no longer gets recreated
            #for modes -- niand 2007-08-29
            changes.keep_forever(self.propMgr)  

        self.propMgr.show()
コード例 #5
0
    def init_gui(self):
        """
        Initialize GUI for this mode 
        """
        if self.propMgr is None:
            self.propMgr = StereoProperties_PropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494.
            #This bug is mitigated as propMgr object no longer gets recreated
            #for modes -- niand 2007-08-29
            changes.keep_forever(self.propMgr)

        self.propMgr.show()
コード例 #6
0
    def init_gui(self):
        if not self.propMgr:
            self.propMgr = MovePropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494
            changes.keep_forever(self.propMgr)

        self.propMgr.show()
        self.updateCommandToolbar(bool_entering = True)

        # connect signals (these all need to be disconnected in restore_gui)
        self.connect_or_disconnect_signals(True)

        self.propMgr.set_move_xyz(0, 0, 0) # Init X, Y, and Z to zero
        self.propMgr.set_move_delta_xyz(0,0,0) # Init DelX,DelY, DelZ to zero
コード例 #7
0
ファイル: Command.py プロジェクト: elfion/nanoengineer
 def command_enter_PM(self):
     """
     Overrides superclass method. 
     
     @see: baseCommand.command_enter_PM()  for documentation
     """
     #important to check for old propMgr object. Reusing propMgr object 
     #significantly improves the performance.
     if not self.propMgr:
         self.propMgr = self._createPropMgrObject()
         #@bug BUG: following is a workaround for bug 2494.
         #This bug is mitigated as propMgr object no longer gets recreated
         #for modes -- ninad 2007-08-29
         if self.propMgr:
             changes.keep_forever(self.propMgr)  
コード例 #8
0
    def init_gui(self):
        if not self.propMgr:
            self.propMgr = MovePropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494
            changes.keep_forever(self.propMgr)

        self.propMgr.show()
        self.updateCommandToolbar(bool_entering=True)

        # connect signals (these all need to be disconnected in restore_gui)
        self.connect_or_disconnect_signals(True)

        self.propMgr.set_move_xyz(0, 0, 0)  # Init X, Y, and Z to zero
        self.propMgr.set_move_delta_xyz(0, 0,
                                        0)  # Init DelX,DelY, DelZ to zero
コード例 #9
0
ファイル: Command.py プロジェクト: elfion/nanoengineer
 def command_enter_PM(self):
     """
     Overrides superclass method. 
     
     @see: baseCommand.command_enter_PM()  for documentation
     """
     #important to check for old propMgr object. Reusing propMgr object
     #significantly improves the performance.
     if not self.propMgr:
         self.propMgr = self._createPropMgrObject()
         #@bug BUG: following is a workaround for bug 2494.
         #This bug is mitigated as propMgr object no longer gets recreated
         #for modes -- ninad 2007-08-29
         if self.propMgr:
             changes.keep_forever(self.propMgr)
コード例 #10
0
    def create_and_or_show_PM_if_wanted(self, showPropMgr=True):
        """
        Create the property manager object if one doesn't already exist 
        and then show the propMgr if wanted by the user
        @param showPropMgr: If True, show the property manager 
        @type showPropMgr: boolean
        """
        if not self.propMgr:
            self.propMgr = self._createPropMgrObject()
            #IMPORTANT keep this propMgr permanently -- needed to fix bug 2563
            changes.keep_forever(self.propMgr)

        if not showPropMgr:
            return

        self.propMgr.show()
コード例 #11
0
    def create_and_or_show_PM_if_wanted(self, showPropMgr=True):
        """
        Create the property manager object if one doesn't already exist 
        and then show the propMgr if wanted by the user
        @param showPropMgr: If True, show the property manager 
        @type showPropMgr: boolean
        """
        if not self.propMgr:
            self.propMgr = self._createPropMgrObject()
            # IMPORTANT keep this propMgr permanently -- needed to fix bug 2563
            changes.keep_forever(self.propMgr)

        if not showPropMgr:
            return

        self.propMgr.show()
コード例 #12
0
def construct_cmdrun( cmd_class, glpane):
    """
    Construct and return a new "command run" object, for use in the given glpane.
    Don't start it -- there is no obligation for the caller to ever start it;
    and if it does, it's allowed to do that after other user events and model changes
    happened in the meantime [REVIEW THAT, it's not good for "potential commands"] --
    but it should not be after this glpane or its underlying model (assembly object)
    get replaced (e.g. by Open File).
    """
    # (we use same interface as <mode>.__init__ for now,
    #  though passing assy might be more logical)
    cmdrun = cmd_class(glpane)
    if not hasattr(cmdrun, 'glpane'):
        print "bug: no glpane in cmdrun %r: did it forget to call ExampleCommand.__init__?" % (cmdrun,)
    ###e should also put it somewhere, as needed for a mode ####DOIT
    if 'kluge, might prevent malloc errors after removing pm from ui (guess)':
        import foundation.changes as changes
        changes.keep_forever(cmdrun)
    return cmdrun
コード例 #13
0
    def init_gui(self):
        if self.propMgr is None:
            self.propMgr = FusePropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494
            changes.keep_forever(self.propMgr)

        self.propMgr.show()

        self.change_fuse_mode(str(self.propMgr.fuseComboBox.currentText()))
            # This maintains state of fuse mode when leaving/reentering mode,
            # and syncs the PM and glpane (and does a gl_update).

        self.w.toolsFuseChunksAction.setChecked(1)

        self.updateCommandToolbar(bool_entering = True)

        # connect signals
        #(these all need to be disconnected in restore_gui) [mark 050901]
        self.connect_or_disconnect_signals(True)

        if self.o.assy.selmols:
            self.graphicsMode.something_was_picked = True
コード例 #14
0
 def init_gui(self):
     """
     Initialize GUI for this mode 
     """
     previousCommand = self.commandSequencer.prevMode 
     if previousCommand.commandName == 'BUILD_DNA':
         try:
             self.flyoutToolbar = previousCommand.flyoutToolbar
             #Need a better way to deal with changing state of the 
             #corresponding action in the flyout toolbar. To be revised 
             #during command toolbar cleanup 
             self.flyoutToolbar.joinStrandsAction.setChecked(True)
         except AttributeError:
             self.flyoutToolbar = None
     if self.propMgr is None:
         self.propMgr = JoinStrands_PropertyManager(self)
         #@bug BUG: following is a workaround for bug 2494.
         #This bug is mitigated as propMgr object no longer gets recreated
         #for modes -- niand 2007-08-29
         changes.keep_forever(self.propMgr)  
         
     self.propMgr.show()    
コード例 #15
0
    def init_gui(self):
        """
        Do changes to the GUI while entering this mode. This includes opening 
        the property manager, updating the command toolbar, connecting widget 
        slots, etc. 

        Called once each time the mode is entered; should be called only by code 
        in modes.py.

        @see: L{self.restore_gui}
        """
        self.enable_gui_actions(False)
        self.dont_update_gui = True
        if not self.propMgr:
            self.propMgr = PartLibPropertyManager(self)
            changes.keep_forever(self.propMgr)

        self.propMgr.show()     

        self.connect_or_disconnect_signals(True)
        self.updateCommandToolbar(bool_entering = True)

        self.dont_update_gui = False
コード例 #16
0
    def init_gui(self):
        """
        Initialize GUI for this mode 
        """
        previousCommand = self.commandSequencer.prevMode
        if previousCommand.commandName == 'BUILD_PROTEIN':
            try:
                self.flyoutToolbar = previousCommand.flyoutToolbar
                self.flyoutToolbar.editResiduesAction.setChecked(True)
            except AttributeError:
                self.flyoutToolbar = None
            if self.flyoutToolbar:
                if not self.flyoutToolbar.editResiduesAction.isChecked():
                    self.flyoutToolbar.editResiduesAction.setChecked(True)

        if self.propMgr is None:
            self.propMgr = EditResidues_PropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494.
            #This bug is mitigated as propMgr object no longer gets recreated
            #for modes -- niand 2007-08-29
            changes.keep_forever(self.propMgr)

        self.propMgr.show()
コード例 #17
0
 def init_gui(self):
     """
     Initialize GUI for this mode 
     """
     previousCommand = self.commandSequencer.prevMode 
     if previousCommand.commandName == 'BUILD_PROTEIN':
         try:
             self.flyoutToolbar = previousCommand.flyoutToolbar
             self.flyoutToolbar.editResiduesAction.setChecked(True)
         except AttributeError:
             self.flyoutToolbar = None
         if self.flyoutToolbar:
             if not self.flyoutToolbar.editResiduesAction.isChecked():
                 self.flyoutToolbar.editResiduesAction.setChecked(True)         
         
             
     if self.propMgr is None:
         self.propMgr = EditResidues_PropertyManager(self)
         #@bug BUG: following is a workaround for bug 2494.
         #This bug is mitigated as propMgr object no longer gets recreated
         #for modes -- niand 2007-08-29
         changes.keep_forever(self.propMgr)  
         
     self.propMgr.show()
コード例 #18
0
def makemenu_helper(widget, menu_spec, menu = None):
    """
    Make and return a reusable or one-time-use (at caller's option)
    popup menu whose structure is specified by menu_spec,
    which is a list of menu item specifiers, each of which is either None
    (for a separator) or a tuple of the form (menu text, callable or submenu,
    option1, option2, ...) with 0 or more options (described below).
       A submenu can be either another menu_spec list, or a QMenu object
    (but in the latter case the menu text is ignored -- maybe it comes
    from that QMenu object somehow -- not sure if this was different in Qt3).
    In either case it is the 2nd menu-item-tuple element, in place of the callable.
       Otherwise the callable must satisfy the python 'callable' predicate,
    and is executed if the menu item is chosen, wrapped inside another function
    which handles Undo checkpointing and Undo-command-name setting.
       The options in a menu item tuple can be zero or more (in any order,
    duplicates allowed) of the following:
    'disabled' -- the menu item should be disabled;
    'checked' -- the menu item will be checked;
    None -- this option is legal but ignored (but the callable must still satisfy
    the python predicate "callable"; constants.noop might be useful for that case).
       The Qt3 version also supported tuple-options consisting of one of the words
    'iconset' and 'whatsThis' followed by an appropriate argument, but those have
    not yet been ported to Qt4 (except possibly for disabled menu items -- UNTESTED).
       Unrecognized options may or may not generate warnings, and are otherwise ignored.
    [###FIX that -- they always ought to print a warning to developers. Note that right
    now they do iff 'disabled' is one of the options and ATOM_DEBUG is set.]
       The 'widget' argument should be the Qt widget
    which is using this function to put up a menu.
       If the menu argument is provided, it should be a QMenu
    to which we'll add items; otherwise we create our own QMenu
    and add items to it.
    """
    from utilities.debug import print_compact_traceback
    import types
    if menu is None:
        menu = QMenu(widget)
        ## menu.show()
        #bruce 070514 removed menu.show() to fix a cosmetic and performance bug
        # (on Mac, possibly on other platforms too; probably unreported)
        # in which the debug menu first appears in screen center, slowly grows
        # to full size while remaining blank, then moves to its final position
        # and looks normal (causing a visual glitch, and a 2-3 second delay
        # in being able to use it). May fix similar issues with other menus.
        # If this causes harm for some menus or platforms, we can adapt it.
    # bruce 040909-16 moved this method from basicMode to GLPane,
    # leaving a delegator for it in basicMode.
    # (bruce was not the original author, but modified it)
    #menu = QMenu( widget)
    for m in menu_spec:
        try: #bruce 050416 added try/except as debug code and for safety
            menutext = m and widget.trUtf8(m[0])
            if m and isinstance(m[1], QMenu): #bruce 041010 added this case
                submenu = m[1]
                #menu.insertItem( menutext, submenu )
                menu.addMenu(submenu)   # how do I get menutext in there?
                    # (similar code might work for QAction case too, not sure)
            elif m and isinstance(m[1], types.ListType): #bruce 041103 added this case
                submenu = QMenu(menutext, menu)
                submenu = makemenu_helper(widget, m[1], submenu) # [this used to call widget.makemenu]
                menu.addMenu(submenu)
            elif m:
                assert callable(m[1]), \
                    "%r[1] needs to be a callable" % (m,) #bruce 041103
                # transform m[1] into a new callable that makes undo checkpoints and provides an undo command-name
                # [bruce 060324 for possible bugs in undo noticing cmenu items, and for the cmdnames]
                func = wrap_callable_for_undo(m[1], cmdname = m[0])
                    # guess about cmdname, but it might be reasonable for A7 as long as we ensure weird characters won't confuse it
                import foundation.changes as changes
                changes.keep_forever(func) # THIS IS BAD (memory leak), but it's not a severe one, so ok for A7 [bruce 060324]
                    # (note: the hard part about removing these when we no longer need them is knowing when to do that
                    #  if the user ends up not selecting anything from the menu. Also, some callers make these
                    #  menus for reuse multiple times, and for them we never want to deallocate func even when some
                    #  menu command gets used. We could solve both of these by making the caller pass a place to keep these
                    #  which it would deallocate someday or which would ensure only one per distinct kind of menu is kept. #e)
                if 'disabled' not in m[2:]:
                    act = QAction(widget)
                    act.setText( menutext)
                    if 'checked' in m[2:]:
                        act.setCheckable(True)
                        act.setChecked(True)
                    menu.addAction(act)
                    widget.connect(act, SIGNAL("activated()"), func)
                else:
                    # disabled case
                    # [why is this case done differently, in this Qt4 port?? -- bruce 070522 question]
                    insert_command_into_menu(menu, menutext, func, options = m[2:], raw_command = True)
            else:
                menu.addSeparator() #bruce 070522 bugfix -- before this, separators were placed lower down or dropped
                    # so as not to come before disabled items, for unknown reasons.
                    # (Speculation: maybe because insertSeparator was used, since addSeparator didn't work or wasn't noticed,
                    #  and since disabled item were added by an older function (also for unknown reasons)?)
                pass
        except Exception, e:
            if isinstance(e, SystemExit):
                raise
            print_compact_traceback("exception in makemenu_helper ignored, for %r:\n" % (m,) )
                #bruce 070522 restored this (was skipped in Qt4 port)
            pass #e could add a fake menu item here as an error message
コード例 #19
0
    def init_gui(self):

        if not self.propMgr:
            self.propMgr = MoviePropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494
            changes.keep_forever(self.propMgr)

        #@NOTE: self.propMgr.show() is called later in this (init_gui) method.

        self.updateCommandToolbar(bool_entering=True)

        self.w.simMoviePlayerAction.setChecked(
            1)  # toggle on the Movie Player icon+

        # Disable some action items in the main window.
        # [bruce 050426 comment: I'm skeptical of disabling the ones marked #k
        #  and suggest for some others (especially "simulator") that they
        #  auto-exit the mode rather than be disabled,
        #  but I won't revise these for now.]
        self.w.disable_QActions_for_movieMode(True)
        #  Actions marked #k are now in disable_QActions_for_movieMode(). mark 060314)

        # MP dashboard initialization.
        self.enableMovieControls(False)
        #bruce 050428 precaution (has no noticable effect but seems safer in theory)
        #bruce 050428, working on bug 395: I think some undesirable state is left in the dashboard, so let's reinit it
        # (and down below we might like to init it from the movie if possible, but it's not always possible).
        self.propMgr._moviePropMgr_reinit(
        )  ###e could pass frameno? is max frames avail yet in all playable movies? not sure.
        # [bruce 050426 comment: probably this should just be a call of an update method, also used during the mode ###e]
        movie = self.o.assy.current_movie  # might be None, but might_be_playable() true implies it's not
        if self.might_be_playable():  #bruce 050426 added condition
            frameno = movie.currentFrame
        else:
            frameno = 0  #bruce 050426 guessed value

        self.propMgr.frameNumberSpinBox.setValue(
            frameno
        )  # bruce 050428 question: does this call our slot method?? ###k
        self.propMgr.moviePlayActiveAction.setVisible(0)
        self.propMgr.moviePlayRevActiveAction.setVisible(0)

        if self.might_be_playable(
        ):  # We have a movie file ready.  It's showtime! [bruce 050426 changed .filename -> .might_be_playable()]
            movie.cueMovie(propMgr=self.propMgr)  # Cue movie.
            self.enableMovieControls(True)
            self.propMgr.updateFrameInformation()
            if movie.filename:  #k not sure this cond is needed or what to do if not true [bruce 050510]
                env.history.message(
                    "Movie file ready to play: %s" %
                    movie.filename)  #bruce 050510 added this message
        else:
            self.enableMovieControls(False)

        #Need to do this after calling movie._setUp (propMgr displays movie
        #information in its msg groupbox.  All this will be cleaned up when we
        #do moviemode code cleanup.

        self.propMgr.show()

        # Disable Undo/Redo actions, and undo checkpoints, during this mode (they *must* be reenabled in restore_gui).
        # We do this last, so as not to do it if there are exceptions in the rest of the method,
        # since if it's done and never undone, Undo/Redo won't work for the rest of the session.
        # [bruce 060414; same thing done in some other modes]
        import foundation.undo_manager as undo_manager
        undo_manager.disable_undo_checkpoints('Movie Player')
        undo_manager.disable_UndoRedo(
            'Movie Player',
            "in Movie Player")  # optimizing this for shortness in menu text
        # this makes Undo menu commands and tooltips look like "Undo (not permitted in Movie Player)" (and similarly for Redo)
        self.connect_or_disconnect_signals(True)
コード例 #20
0
ファイル: movieMode.py プロジェクト: ematvey/NanoEngineer-1
    def init_gui(self):

        if not self.propMgr:
            self.propMgr = MoviePropertyManager(self)
            #@bug BUG: following is a workaround for bug 2494
            changes.keep_forever(self.propMgr)

        #@NOTE: self.propMgr.show() is called later in this (init_gui) method.

        self.updateCommandToolbar(bool_entering = True)

        self.w.simMoviePlayerAction.setChecked(1) # toggle on the Movie Player icon+

        # Disable some action items in the main window.
        # [bruce 050426 comment: I'm skeptical of disabling the ones marked #k
        #  and suggest for some others (especially "simulator") that they
        #  auto-exit the mode rather than be disabled,
        #  but I won't revise these for now.]
        self.w.disable_QActions_for_movieMode(True)
            #  Actions marked #k are now in disable_QActions_for_movieMode(). mark 060314)

        # MP dashboard initialization.
        self.enableMovieControls(False)
            #bruce 050428 precaution (has no noticable effect but seems safer in theory)
        #bruce 050428, working on bug 395: I think some undesirable state is left in the dashboard, so let's reinit it
        # (and down below we might like to init it from the movie if possible, but it's not always possible).
        self.propMgr._moviePropMgr_reinit() ###e could pass frameno? is max frames avail yet in all playable movies? not sure.
        # [bruce 050426 comment: probably this should just be a call of an update method, also used during the mode ###e]
        movie = self.o.assy.current_movie # might be None, but might_be_playable() true implies it's not
        if self.might_be_playable(): #bruce 050426 added condition
            frameno = movie.currentFrame
        else:
            frameno = 0 #bruce 050426 guessed value

        self.propMgr.frameNumberSpinBox.setValue(frameno) # bruce 050428 question: does this call our slot method?? ###k
        self.propMgr.moviePlayActiveAction.setVisible(0)
        self.propMgr.moviePlayRevActiveAction.setVisible(0)

        if self.might_be_playable(): # We have a movie file ready.  It's showtime! [bruce 050426 changed .filename -> .might_be_playable()]
            movie.cueMovie(propMgr = self.propMgr) # Cue movie.
            self.enableMovieControls(True)
            self.propMgr.updateFrameInformation()
            if movie.filename: #k not sure this cond is needed or what to do if not true [bruce 050510]
                env.history.message( "Movie file ready to play: %s" % movie.filename) #bruce 050510 added this message
        else:
            self.enableMovieControls(False)

        #Need to do this after calling movie._setUp (propMgr displays movie
        #information in its msg groupbox.  All this will be cleaned up when we
        #do moviemode code cleanup.

        self.propMgr.show()

        # Disable Undo/Redo actions, and undo checkpoints, during this mode (they *must* be reenabled in restore_gui).
        # We do this last, so as not to do it if there are exceptions in the rest of the method,
        # since if it's done and never undone, Undo/Redo won't work for the rest of the session.
        # [bruce 060414; same thing done in some other modes]
        import foundation.undo_manager as undo_manager
        undo_manager.disable_undo_checkpoints('Movie Player')
        undo_manager.disable_UndoRedo('Movie Player', "in Movie Player") # optimizing this for shortness in menu text
            # this makes Undo menu commands and tooltips look like "Undo (not permitted in Movie Player)" (and similarly for Redo)
        self.connect_or_disconnect_signals(True)
コード例 #21
0
def makemenu_helper(widget, menu_spec, menu=None):
    """
    Make and return a reusable or one-time-use (at caller's option)
    popup menu whose structure is specified by menu_spec,
    which is a list of menu item specifiers, each of which is either None
    (for a separator) or a tuple of the form (menu text, callable or submenu,
    option1, option2, ...) with 0 or more options (described below).
       A submenu can be either another menu_spec list, or a QMenu object
    (but in the latter case the menu text is ignored -- maybe it comes
    from that QMenu object somehow -- not sure if this was different in Qt3).
    In either case it is the 2nd menu-item-tuple element, in place of the callable.
       Otherwise the callable must satisfy the python 'callable' predicate,
    and is executed if the menu item is chosen, wrapped inside another function
    which handles Undo checkpointing and Undo-command-name setting.
       The options in a menu item tuple can be zero or more (in any order,
    duplicates allowed) of the following:
    'disabled' -- the menu item should be disabled;
    'checked' -- the menu item will be checked;
    None -- this option is legal but ignored (but the callable must still satisfy
    the python predicate "callable"; constants.noop might be useful for that case).
       The Qt3 version also supported tuple-options consisting of one of the words
    'iconset' and 'whatsThis' followed by an appropriate argument, but those have
    not yet been ported to Qt4 (except possibly for disabled menu items -- UNTESTED).
       Unrecognized options may or may not generate warnings, and are otherwise ignored.
    [###FIX that -- they always ought to print a warning to developers. Note that right
    now they do iff 'disabled' is one of the options and ATOM_DEBUG is set.]
       The 'widget' argument should be the Qt widget
    which is using this function to put up a menu.
       If the menu argument is provided, it should be a QMenu
    to which we'll add items; otherwise we create our own QMenu
    and add items to it.
    """
    from utilities.debug import print_compact_traceback
    import types
    if menu is None:
        menu = QMenu(widget)
        ## menu.show()
        #bruce 070514 removed menu.show() to fix a cosmetic and performance bug
        # (on Mac, possibly on other platforms too; probably unreported)
        # in which the debug menu first appears in screen center, slowly grows
        # to full size while remaining blank, then moves to its final position
        # and looks normal (causing a visual glitch, and a 2-3 second delay
        # in being able to use it). May fix similar issues with other menus.
        # If this causes harm for some menus or platforms, we can adapt it.
    # bruce 040909-16 moved this method from basicMode to GLPane,
    # leaving a delegator for it in basicMode.
    # (bruce was not the original author, but modified it)
    #menu = QMenu( widget)
    for m in menu_spec:
        try:  #bruce 050416 added try/except as debug code and for safety
            menutext = m and widget.trUtf8(m[0])
            if m and isinstance(m[1], QMenu):  #bruce 041010 added this case
                submenu = m[1]
                #menu.insertItem( menutext, submenu )
                menu.addMenu(submenu)  # how do I get menutext in there?
                # (similar code might work for QAction case too, not sure)
            elif m and isinstance(
                    m[1], types.ListType):  #bruce 041103 added this case
                submenu = QMenu(menutext, menu)
                submenu = makemenu_helper(
                    widget, m[1],
                    submenu)  # [this used to call widget.makemenu]
                menu.addMenu(submenu)
            elif m:
                assert callable(m[1]), \
                    "%r[1] needs to be a callable" % (m,) #bruce 041103
                # transform m[1] into a new callable that makes undo checkpoints and provides an undo command-name
                # [bruce 060324 for possible bugs in undo noticing cmenu items, and for the cmdnames]
                func = wrap_callable_for_undo(m[1], cmdname=m[0])
                # guess about cmdname, but it might be reasonable for A7 as long as we ensure weird characters won't confuse it
                import foundation.changes as changes
                changes.keep_forever(
                    func
                )  # THIS IS BAD (memory leak), but it's not a severe one, so ok for A7 [bruce 060324]
                # (note: the hard part about removing these when we no longer need them is knowing when to do that
                #  if the user ends up not selecting anything from the menu. Also, some callers make these
                #  menus for reuse multiple times, and for them we never want to deallocate func even when some
                #  menu command gets used. We could solve both of these by making the caller pass a place to keep these
                #  which it would deallocate someday or which would ensure only one per distinct kind of menu is kept. #e)
                if 'disabled' not in m[2:]:
                    act = QAction(widget)
                    act.setText(menutext)
                    if 'checked' in m[2:]:
                        act.setCheckable(True)
                        act.setChecked(True)
                    menu.addAction(act)
                    widget.connect(act, SIGNAL("activated()"), func)
                else:
                    # disabled case
                    # [why is this case done differently, in this Qt4 port?? -- bruce 070522 question]
                    insert_command_into_menu(menu,
                                             menutext,
                                             func,
                                             options=m[2:],
                                             raw_command=True)
            else:
                menu.addSeparator(
                )  #bruce 070522 bugfix -- before this, separators were placed lower down or dropped
                # so as not to come before disabled items, for unknown reasons.
                # (Speculation: maybe because insertSeparator was used, since addSeparator didn't work or wasn't noticed,
                #  and since disabled item were added by an older function (also for unknown reasons)?)
                pass
        except Exception, e:
            if isinstance(e, SystemExit):
                raise
            print_compact_traceback(
                "exception in makemenu_helper ignored, for %r:\n" % (m, ))
            #bruce 070522 restored this (was skipped in Qt4 port)
            pass  #e could add a fake menu item here as an error message
コード例 #22
0
def insert_command_into_menu(menu,
                             menutext,
                             command,
                             options=(),
                             position=-1,
                             raw_command=False,
                             undo_cmdname=None):
    """
    [This was part of makemenu_helper in the Qt3 version; in Qt4 it's only
     used for the disabled case, presumably for some good reason but not one
     which has been documented. It's also used independently of makemenu_helper.]
    
    Insert a new item into menu (a QMenu), whose menutext, command, and options are as given,
    with undo_cmdname defaulting to menutext (used only if raw_command is false), 
    where options is a list or tuple in the same form as used in "menu_spec" lists
    such as are passed to makemenu_helper (which this function helps implement).
       The caller should have already translated/localized menutext if desired.
       If position is given, insert the new item at that position, otherwise at the end.
    Return the Qt menu item id of the new menu item.
    (I am not sure whether this remains valid if other items are inserted before it. ###k)
       If raw_command is False (default), this function will wrap command with standard logic for nE-1 menu commands
    (presently, wrap_callable_for_undo), and ensure that a python reference to the resulting callable is kept forever.
       If raw_command is True, this function will pass command unchanged into the menu,
    and the caller is responsible for retaining a Python reference to command.
       ###e This might need an argument for the path or function to be used to resolve icon filenames.
    """
    #bruce 060613 split this out of makemenu_helper.
    # Only called for len(options) > 0, though it presumably works
    # just as well for len 0 (try it sometime).
    import types
    from foundation.whatsthis_utilities import turn_featurenames_into_links, ENABLE_WHATSTHIS_LINKS
    if not raw_command:
        command = wrap_callable_for_undo(command,
                                         cmdname=undo_cmdname or menutext)
        import foundation.changes as changes
        changes.keep_forever(command)
        # see comments on similar code above about why this is bad in theory, but necessary and ok for now
    iconset = None
    for option in options:
        # some options have to be processed first
        # since they are only usable when the menu item is inserted. [bruce 050614]
        if type(option) is types.TupleType:
            if option[0] == 'iconset':
                # support iconset, pixmap, or pixmap filename [bruce 050614 new feature]
                iconset = option[1]
                if type(iconset) is types.StringType:
                    filename = iconset
                    from utilities.icon_utilities import imagename_to_pixmap
                    iconset = imagename_to_pixmap(filename)
                if isinstance(iconset, QPixmap):
                    # (this is true for imagename_to_pixmap retval)
                    iconset = QIcon(iconset)
    if iconset is not None:
        import foundation.changes as changes
        changes.keep_forever(
            iconset
        )  #e memory leak; ought to make caller pass a place to keep it, or a unique id of what to keep
        #mitem_id = menu.insertItem( iconset, menutext, -1, position ) #bruce 050614, revised 060613 (added -1, position)
        mitem = menu.addAction(
            iconset,
            menutext)  #bruce 050614, revised 060613 (added -1, position)
        # Will this work with checkmark items? Yes, but it replaces the checkmark --
        # instead, the icon looks different for the checked item.
        # For the test case of gamess.png on Mac, the 'checked' item's icon
        # looked like a 3d-depressed button.
        # In the future we can tell the iconset what to display in each case
        # (see QIcon and/or QMenu docs, and helper funcs presently in debug_prefs.py.)
    else:
        # mitem_id = len(menu) -- mitem_id was previously an integer, indexing into the menu
        mitem = menu.addAction(menutext)
    for option in options:
        if option == 'checked':
            mitem.setChecked(True)
        elif option == 'unchecked':  #bruce 050614 -- see what this does visually, if anything
            mitem.setChecked(False)
        elif option == 'disabled':
            mitem.setEnabled(False)
        elif type(option) is types.TupleType:
            if option[0] == 'whatsThis':
                text = option[1]
                if ENABLE_WHATSTHIS_LINKS:
                    text = turn_featurenames_into_links(text)
                mitem.setWhatsThis(text)
            elif option[0] == 'iconset':
                pass  # this was processed above
            else:
                if debug_flags.atom_debug:
                    print "atom_debug: fyi: don't understand menu_spec option %r", (
                        option, )
            pass
        elif option is None:
            pass  # this is explicitly permitted and has no effect
        else:
            if debug_flags.atom_debug:
                print "atom_debug: fyi: don't understand menu_spec option %r", (
                    option, )
        pass
        #e and something to use QMenuData.setShortcut
        #e and something to run whatever func you want on menu and mitem_id
    return mitem  # from insert_command_into_menu
コード例 #23
0
def insert_command_into_menu(menu, menutext, command, options = (), position = -1, raw_command = False, undo_cmdname = None): 
    """
    [This was part of makemenu_helper in the Qt3 version; in Qt4 it's only
     used for the disabled case, presumably for some good reason but not one
     which has been documented. It's also used independently of makemenu_helper.]
    
    Insert a new item into menu (a QMenu), whose menutext, command, and options are as given,
    with undo_cmdname defaulting to menutext (used only if raw_command is false), 
    where options is a list or tuple in the same form as used in "menu_spec" lists
    such as are passed to makemenu_helper (which this function helps implement).
       The caller should have already translated/localized menutext if desired.
       If position is given, insert the new item at that position, otherwise at the end.
    Return the Qt menu item id of the new menu item.
    (I am not sure whether this remains valid if other items are inserted before it. ###k)
       If raw_command is False (default), this function will wrap command with standard logic for nE-1 menu commands
    (presently, wrap_callable_for_undo), and ensure that a python reference to the resulting callable is kept forever.
       If raw_command is True, this function will pass command unchanged into the menu,
    and the caller is responsible for retaining a Python reference to command.
       ###e This might need an argument for the path or function to be used to resolve icon filenames.
    """
    #bruce 060613 split this out of makemenu_helper.
    # Only called for len(options) > 0, though it presumably works
    # just as well for len 0 (try it sometime).
    import types
    from foundation.whatsthis_utilities import turn_featurenames_into_links, ENABLE_WHATSTHIS_LINKS
    if not raw_command:
        command = wrap_callable_for_undo(command, cmdname = undo_cmdname or menutext)
        import foundation.changes as changes
        changes.keep_forever(command)
            # see comments on similar code above about why this is bad in theory, but necessary and ok for now
    iconset = None
    for option in options:
        # some options have to be processed first
        # since they are only usable when the menu item is inserted. [bruce 050614]
        if type(option) is types.TupleType:
            if option[0] == 'iconset':
                # support iconset, pixmap, or pixmap filename [bruce 050614 new feature]
                iconset = option[1]
                if type(iconset) is types.StringType:
                    filename = iconset
                    from utilities.icon_utilities import imagename_to_pixmap
                    iconset = imagename_to_pixmap(filename)
                if isinstance(iconset, QPixmap):
                    # (this is true for imagename_to_pixmap retval)
                    iconset = QIcon(iconset)
    if iconset is not None:
        import foundation.changes as changes
        changes.keep_forever(iconset) #e memory leak; ought to make caller pass a place to keep it, or a unique id of what to keep
        #mitem_id = menu.insertItem( iconset, menutext, -1, position ) #bruce 050614, revised 060613 (added -1, position)
        mitem = menu.addAction( iconset, menutext ) #bruce 050614, revised 060613 (added -1, position)
            # Will this work with checkmark items? Yes, but it replaces the checkmark --
            # instead, the icon looks different for the checked item.
            # For the test case of gamess.png on Mac, the 'checked' item's icon
            # looked like a 3d-depressed button.
            # In the future we can tell the iconset what to display in each case
            # (see QIcon and/or QMenu docs, and helper funcs presently in debug_prefs.py.)
    else:
        # mitem_id = len(menu) -- mitem_id was previously an integer, indexing into the menu
        mitem = menu.addAction(menutext)
    for option in options:
        if option == 'checked':
            mitem.setChecked(True)
        elif option == 'unchecked': #bruce 050614 -- see what this does visually, if anything
            mitem.setChecked(False)
        elif option == 'disabled':
            mitem.setEnabled(False)
        elif type(option) is types.TupleType:
            if option[0] == 'whatsThis':
                text = option[1]
                if ENABLE_WHATSTHIS_LINKS:
                    text = turn_featurenames_into_links(text)
                mitem.setWhatsThis(text)
            elif option[0] == 'iconset':
                pass # this was processed above
            else:
                if debug_flags.atom_debug:
                    print "atom_debug: fyi: don't understand menu_spec option %r", (option,)
            pass
        elif option is None:
            pass # this is explicitly permitted and has no effect
        else:
            if debug_flags.atom_debug:
                print "atom_debug: fyi: don't understand menu_spec option %r", (option,)
        pass
        #e and something to use QMenuData.setShortcut
        #e and something to run whatever func you want on menu and mitem_id
    return mitem # from insert_command_into_menu