示例#1
0
    def makeGridPlane(self):
        cmd = greenmsg("Grid Plane: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select 3 or more atoms to create a Grid Plane."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure only one atom is selected.
        if len(atoms) < 3:
            msg = "To create a Grid Plane, at least 3 atoms must be selected."
            env.history.message(cmd + redmsg(msg))
            return

        from model.jigs_planes import GridPlane
        m = GridPlane(self.assy, atoms)
        m.edit()
        if m.cancelled:  # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return

        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        #After placing the jig, remove the atom list from the jig.
        m.atoms = []

        env.history.message(cmd + "Grid Plane created")
        self.assy.w.win_update()
        return
    def makeGridPlane(self):
        cmd = greenmsg("Grid Plane: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select 3 or more atoms to create a Grid Plane."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure only one atom is selected.
        if len(atoms) < 3:
            msg = "To create a Grid Plane, at least 3 atoms must be selected."
            env.history.message(cmd + redmsg(msg))
            return

        from model.jigs_planes import GridPlane
        m = GridPlane(self.assy, atoms)
        m.edit()
        if m.cancelled: # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return

        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        #After placing the jig, remove the atom list from the jig.
        m.atoms = []

        env.history.message(cmd + "Grid Plane created")
        self.assy.w.win_update()
        return
示例#3
0
    def makethermo(self):
        """
        Attaches a thermometer to the single atom selected.
        """
        cmd = greenmsg("Thermometer: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select an atom on the chunk you want to " \
                  "associate with a Thermometer."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure only one atom is selected.
        if len(atoms) != 1:
            msg = "To create a Thermometer, only one atom may be selected."
            env.history.message(cmd + redmsg(msg))
            return

        m = Thermo(self.assy, atoms)
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + "Thermometer created")
        self.assy.w.win_update()
示例#4
0
def editMakeCheckpoint(win):
    """
    This is called from MWsemantics.editMakeCheckpoint,
    which is documented as:

      "Slot for making a checkpoint (only available when
       Automatic Checkpointing is disabled)."
    """
    env.history.message(greenmsg("Make Checkpoint"))
    # do it
    try:
        #REVIEW: Should make sure this is correct with or without
        # auto-checkpointing enabled, and leaves that setting unchanged.
        # (This is not urgent, since in present UI it can't be called
        #  except when auto-checkpointing is disabled.)
        um = win.assy.undo_manager
        if um:
            um.make_manual_checkpoint()
            # no msg needed, was emitted above:
            ## env.history.message(greenmsg("Make Checkpoint"))
            pass
        else:
            # this should never happen
            msg = "Make Checkpoint: error, no undo_manager"
            env.history.message(redmsg(msg))
    except:
        print_compact_traceback("exception caught in editMakeCheckpoint: ")
        msg = "Internal error in Make Checkpoint. " \
              "Undo/Redo might be unsafe until a new file is opened."
        env.history.message(redmsg(msg))
        #e that wording assumes we can't open more than one file at a time...
    return
    def makethermo(self):
        """
        Attaches a thermometer to the single atom selected.
        """
        cmd = greenmsg("Thermometer: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select an atom on the chunk you want to " \
                  "associate with a Thermometer."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure only one atom is selected.
        if len(atoms) != 1:
            msg = "To create a Thermometer, only one atom may be selected."
            env.history.message(cmd + redmsg(msg))
            return

        m = Thermo(self.assy, atoms)
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + "Thermometer created")
        self.assy.w.win_update()
示例#6
0
 def run(self):
     """
     Execute a rosetta simulation
     """
     if not self.part.molecules: # Nothing in the part to simulate.
         msg = redmsg("Nothing to simulate.")
         env.history.message(self.cmdname + ": " + msg)
         self.win.rosettaSetupAction.setChecked(0) 
         return
     #check if at least one protein chunk is present on the NE-1 window,
     #otherwise there's no point calling the simulator
     proteinExists, chunk = checkIfProteinChunkInPart(self.part)
     if not proteinExists:
         msg = redmsg("No protein to simulate.")
         env.history.message(self.cmdname + ": " + msg)
         self.win.rosettaSetupAction.setChecked(0) 
         return
     # iff it's the current mode.
     previous_movie = self.assy.current_movie
        
     self.movie = None
     r = self.makeSimMovie( ) # will store self.movie as the one it made, or leave it as None if cancelled
     self.win.rosettaSetupAction.setChecked(0) 
     
     return
示例#7
0
    def run(self):
        """
        Execute a rosetta simulation
        """
        if not self.part.molecules:  # Nothing in the part to simulate.
            msg = redmsg("Nothing to simulate.")
            env.history.message(self.cmdname + ": " + msg)
            self.win.rosettaSetupAction.setChecked(0)
            return
        #check if at least one protein chunk is present on the NE-1 window,
        #otherwise there's no point calling the simulator
        proteinExists, chunk = checkIfProteinChunkInPart(self.part)
        if not proteinExists:
            msg = redmsg("No protein to simulate.")
            env.history.message(self.cmdname + ": " + msg)
            self.win.rosettaSetupAction.setChecked(0)
            return
        # iff it's the current mode.
        previous_movie = self.assy.current_movie

        self.movie = None
        r = self.makeSimMovie(
        )  # will store self.movie as the one it made, or leave it as None if cancelled
        self.win.rosettaSetupAction.setChecked(0)

        return
示例#8
0
    def print_energy(self):

        r, final_energy_str = get_energy_from_gms_outfile(self.outputfile)

        if r == 1:  # GAMESS terminated abnormally.
            if final_energy_str:
                env.history.message(
                    redmsg(
                        final_energy_str +
                        " Check if you have set the right Gamess executable file. Usually it's called gamess.??.x or ??gamess.exe."
                    ))
                return

            msg = "Final energy value not found. The output file is located at: " + self.outputfile
            env.history.message(redmsg(msg))

        elif r == 2:  # The output file not exist
            msg = "The output file %s doesn't exist. The reason is either that Gamess didn't run or the output file has been deleted. " % self.outputfile
            env.history.message(redmsg(msg))

        else:  # Final energy was found.
            gmstr = self.gms_parms_info()
            msg = "GAMESS finished. The output file is located at: " + self.outputfile
            env.history.message(msg)
            msg = "Parameters: " + gmstr + ".  The final energy is: " + final_energy_str + " Hartree."
            env.history.message(msg)
示例#9
0
def editMakeCheckpoint(win):
    """
    This is called from MWsemantics.editMakeCheckpoint,
    which is documented as:

      "Slot for making a checkpoint (only available when
       Automatic Checkpointing is disabled)."
    """
    env.history.message( greenmsg("Make Checkpoint")) 
    # do it
    try:
        #REVIEW: Should make sure this is correct with or without
        # auto-checkpointing enabled, and leaves that setting unchanged.
        # (This is not urgent, since in present UI it can't be called
        #  except when auto-checkpointing is disabled.)
        um = win.assy.undo_manager 
        if um:
            um.make_manual_checkpoint()
            # no msg needed, was emitted above:
            ## env.history.message(greenmsg("Make Checkpoint"))
            pass
        else:
            # this should never happen
            msg = "Make Checkpoint: error, no undo_manager"
            env.history.message(redmsg(msg))
    except:
        print_compact_traceback("exception caught in editMakeCheckpoint: ")
        msg = "Internal error in Make Checkpoint. " \
              "Undo/Redo might be unsafe until a new file is opened."
        env.history.message(redmsg(msg))
            #e that wording assumes we can't open more than one file at a time...
    return
示例#10
0
    def print_energy(self):

        r, final_energy_str = get_energy_from_gms_outfile(self.outputfile)

        if r == 1:  # GAMESS terminated abnormally.
            if final_energy_str:
                env.history.message(
                    redmsg(
                        final_energy_str
                        + " Check if you have set the right Gamess executable file. Usually it's called gamess.??.x or ??gamess.exe."
                    )
                )
                return

            msg = "Final energy value not found. The output file is located at: " + self.outputfile
            env.history.message(redmsg(msg))

        elif r == 2:  # The output file not exist
            msg = (
                "The output file %s doesn't exist. The reason is either that Gamess didn't run or the output file has been deleted. "
                % self.outputfile
            )
            env.history.message(redmsg(msg))

        else:  # Final energy was found.
            gmstr = self.gms_parms_info()
            msg = "GAMESS finished. The output file is located at: " + self.outputfile
            env.history.message(msg)
            msg = "Parameters: " + gmstr + ".  The final energy is: " + final_energy_str + " Hartree."
            env.history.message(msg)
示例#11
0
    def makegamess(self):
        """
        Makes a GAMESS jig from the selected chunks or atoms.
        """
        # [mark 2007-05-07 modified docstring]

        if sys.platform == "win32":
            gms_str = "PC GAMESS"
        else:
            gms_str = "GAMESS"

        cmd = greenmsg(gms_str + ": ")

        atoms = []

        # Get a list of atoms from the selected chunks or atoms.
        atoms = self.assy.selected_atoms_list(
            include_atoms_in_selected_chunks=True)

        if not atoms:
            msg = "At least one atom must be selected to create a " + \
                  gms_str + " jig."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure that no more than 200 atoms are selected.
        nsa = len(atoms)
        if nsa > 200:
            msg = str(nsa) + " atoms selected.  The limit is 200."
            env.history.message(cmd + redmsg(msg))
            return

        # Bug 742.    Mark 050731.
        if nsa > 50:
            ret = QMessageBox.warning(
                self.assy.w, "Too many atoms?",
                gms_str + " jigs with more than 50 atoms may take an\n"
                "excessively long time to compute (days or weeks).\n"
                "Are you sure you want to continue?", "&Continue", "Cancel",
                "", 0, 1)

            if ret == 1:  # Cancel
                return

        from analysis.GAMESS.jig_Gamess import Gamess
        m = Gamess(self.assy, atoms)
        m.edit()
        #bruce 050701 split edit method out of the constructor, so the
        # dialog doesn't show up when the jig is read from an mmp file
        if m.cancelled:  # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + gms_str + " jig created")
        self.assy.w.win_update()
    def makegamess(self):
        """
        Makes a GAMESS jig from the selected chunks or atoms.
        """
        # [mark 2007-05-07 modified docstring]

        if sys.platform == "win32":
            gms_str = "PC GAMESS"
        else:
            gms_str = "GAMESS"

        cmd = greenmsg(gms_str + ": ")

        atoms = []

        # Get a list of atoms from the selected chunks or atoms.
        atoms = self.assy.selected_atoms_list(
            include_atoms_in_selected_chunks = True)

        if not atoms:
            msg = "At least one atom must be selected to create a " + \
                  gms_str + " jig."
            env.history.message(cmd + redmsg(msg))
            return

        # Make sure that no more than 200 atoms are selected.
        nsa = len(atoms)
        if nsa > 200:
            msg = str(nsa) + " atoms selected.  The limit is 200."
            env.history.message(cmd + redmsg(msg))
            return

        # Bug 742.    Mark 050731.
        if nsa > 50:
            ret = QMessageBox.warning( self.assy.w, "Too many atoms?",
                gms_str + " jigs with more than 50 atoms may take an\n"
                "excessively long time to compute (days or weeks).\n"
                "Are you sure you want to continue?",
                "&Continue", "Cancel", "",
                0, 1 )

            if ret == 1: # Cancel
                return

        from analysis.GAMESS.jig_Gamess import Gamess
        m = Gamess(self.assy, atoms)
        m.edit()
            #bruce 050701 split edit method out of the constructor, so the
            # dialog doesn't show up when the jig is read from an mmp file
        if m.cancelled: # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + gms_str + " jig created")
        self.assy.w.win_update()
示例#13
0
    def Mirror(self):
        """
        Mirror the selected chunk(s) about a selected grid plane.
        """
        cmd = greenmsg("Mirror: ")
        #ninad060814 this is necessary to fix a bug. Otherwise program will
        #crash if you try to mirror when the top node of the part
        #(main part of clipboard) is selected

        if self.topnode.picked:
            self.topnode.unpick_top()

        self.mirrorJigs = self.getQualifiedMirrorJigs()

        jigCounter = len(self.mirrorJigs)

        if jigCounter < 1:
            msg1 = "No mirror plane selected."
            msg2 = " Please select a Reference Plane or a Grid Plane first."
            msg = redmsg(msg1 + msg2)
            instr1 = "(If it doesn't exist, create it using"
            instr2 = "<b>Insert > Reference Geometry menu </b> )"
            instruction = instr1 + instr2
            env.history.message(cmd + msg + instruction)
            return
        elif jigCounter > 1:
            msg = redmsg(
                "More than one plane selected. Please select only one plane and try again"
            )
            env.history.message(cmd + msg)
            return

        for j in self.mirrorJigs:
            j.unpick()

        copiedObject = self.o.assy.part.copy_sel_in_same_part()

        # ninad060812 Get the axis vector of the Grid Plane. Then you need to
        #rotate the inverted chunk by pi around this axis vector
        self.mirrorAxis = self.mirrorJigs[0].getaxis()

        if isinstance(copiedObject, Chunk):
            copiedObject.name = copiedObject.name + "-Mirror"
            self._mirrorChunk(copiedObject)
            return
        elif isinstance(copiedObject, Group):
            copiedObject.name = "Mirrored Items"

            def mirrorChild(obj):
                if isinstance(obj, Chunk):
                    self._mirrorChunk(obj)
                elif isinstance(obj, Jig):
                    self._mirrorJig(obj)

            copiedObject.apply2all(mirrorChild)
        return
示例#14
0
 def _update_UI_do_updates(self):
     """
     Overrides superclass method. 
     
     @see: Command_PropertyManager._update_UI_do_updates()
     """
     
     self.proteinChunk1 = None
     self.proteinChunk2 = None
     self.comparePushButton.setEnabled(False)
     self.hidePushButton.setEnabled(False)
     
     selectedProteinList = self.win.assy.getSelectedProteinChunks()
     
     if len(selectedProteinList) == 0:
         self.structure1LineEdit.setText("")
         self.structure2LineEdit.setText("")
         msg = "Select two structures of the same length in the graphics area, "\
             "then click the <b>Compare</b> button to compare them."
     
     elif len(selectedProteinList) == 1:
         self.proteinChunk1 = selectedProteinList[0]
         aa1_count = " (%d)" % self.proteinChunk1.protein.count_amino_acids()
         self.structure1LineEdit.setText(self.proteinChunk1.name + aa1_count)
         self.structure2LineEdit.setText("")
         msg = "Select one more structure in the graphics area that is the same "\
             "length as <b>" + self.proteinChunk1.name + "</b>. "\
             "Then click the <b>Compare</b> button to compare them."
     
     elif len(selectedProteinList) == 2:
         self.proteinChunk1 = selectedProteinList[0]
         aa1_count = " (%d)" % self.proteinChunk1.protein.count_amino_acids()
         self.structure1LineEdit.setText(self.proteinChunk1.name + aa1_count)
         
         self.proteinChunk2 = selectedProteinList[1]
         aa2_count = " (%d)" % self.proteinChunk2.protein.count_amino_acids()
         self.structure2LineEdit.setText(self.proteinChunk2.name + aa2_count)
         
         if aa1_count == aa2_count:
             self.comparePushButton.setEnabled(True)
             self.hidePushButton.setEnabled(True)
             msg = "Click the <b>Compare</b> button to compare the two selected structures."
         else:
             msg = "<b>%s</b> and <b>%s</b> are not the same length." % \
                 (self.proteinChunk1.name, self.proteinChunk2.name)
             msg = redmsg(msg)
             
     else:
         self.structure1LineEdit.setText("")
         self.structure2LineEdit.setText("")
         msg = redmsg("Too many proteins selected.")
     
     self.updateMessage(msg)
     env.history.redmsg(msg)
     return
示例#15
0
def simPlot(assy):  # moved here from MWsemantics method, bruce 050327
    """Opens the "Make Graphs" dialog (and waits until it's dismissed),
    for the current movie if there is one, otherwise for a previously saved
    dpb file with the same name as the current part, if one can be found.
    Returns the dialog, after it's dismissed (probably useless),
    or None if no dialog was shown.
    """
    #bruce 050326 inferred docstring from code, then revised to fit my recent changes
    # to assy.current_movie, but didn't yet try to look for alternate dpb file names
    # when the current part is not the main part. (I'm sure that we'll soon have a wholly
    # different scheme for letting the user look around for preexisting related files to use,
    # like movie files applicable to the current part.)
    #    I did reorder the code, and removed the check on the current part having atoms
    # (since plotting from an old file shouldn't require movie to be valid for current part).
    #    This method should be moved into some other file.

    if assy.current_movie and assy.current_movie.filename:
        return PlotTool(assy, assy.current_movie.filename)
    else:
        msg = redmsg("There is no current movie file loaded.")
        env.history.message(cmd + msg)
        return None

    # wware 060317, bug 1484
    if assy.filename:
        return PlotTool(assy, assy.filename)

    # no valid current movie, look for saved one with same name as assy
    msg = redmsg("No simulation has been run yet.")
    env.history.message(cmd + msg)
    if assy.filename:
        if assy.part is not assy.tree.part:
            msg = redmsg(
                "Warning: Looking for saved movie for main part, not for displayed clipboard item."
            )
            env.history.message(cmd + msg)
        mfile = assy.filename[:-4] + ".dpb"
        movie = find_saved_movie(assy, mfile)
        # just checks existence, not validity for current part or main part
        if movie:
            #e should we set this as current_movie? I don't see a good reason to do that,
            # user can open it if they want to. But I'll do it if we don't have one yet.
            if not assy.current_movie:
                assy.current_movie = movie
            #e should we switch to the part for which this movie was made?
            # No current way to tell how to do that, and this might be done even if it's not valid
            # for any loaded Part. So let's not... tho we might presume (from filename choice we used)
            # it was valid for Main Part. Maybe print warning for clip item, and for not valid? #e
            msg = "Using previously saved movie for this part."
            env.history.message(cmd + msg)
            return PlotTool(assy, movie)
        else:
            msg = redmsg("Can't find previously saved movie for this part.")
            env.history.message(cmd + msg)
    return
示例#16
0
def simPlot(assy): # moved here from MWsemantics method, bruce 050327
    """Opens the "Make Graphs" dialog (and waits until it's dismissed),
    for the current movie if there is one, otherwise for a previously saved
    dpb file with the same name as the current part, if one can be found.
    Returns the dialog, after it's dismissed (probably useless),
    or None if no dialog was shown.
    """
    #bruce 050326 inferred docstring from code, then revised to fit my recent changes
    # to assy.current_movie, but didn't yet try to look for alternate dpb file names
    # when the current part is not the main part. (I'm sure that we'll soon have a wholly
    # different scheme for letting the user look around for preexisting related files to use,
    # like movie files applicable to the current part.)
    #    I did reorder the code, and removed the check on the current part having atoms
    # (since plotting from an old file shouldn't require movie to be valid for current part).
    #    This method should be moved into some other file.

    if assy.current_movie and assy.current_movie.filename:
        return PlotTool(assy, assy.current_movie.filename)
    else:
        msg = redmsg("There is no current movie file loaded.")
        env.history.message(cmd + msg)
        return None
        
    # wware 060317, bug 1484
    if assy.filename:
        return PlotTool(assy, assy.filename)

    # no valid current movie, look for saved one with same name as assy
    msg = redmsg("No simulation has been run yet.")
    env.history.message(cmd + msg)
    if assy.filename:
        if assy.part is not assy.tree.part:
            msg = redmsg("Warning: Looking for saved movie for main part, not for displayed clipboard item.")
            env.history.message(cmd + msg)
        mfile = assy.filename[:-4] + ".dpb"
        movie = find_saved_movie( assy, mfile)
            # just checks existence, not validity for current part or main part
        if movie:
            #e should we set this as current_movie? I don't see a good reason to do that,
            # user can open it if they want to. But I'll do it if we don't have one yet.
            if not assy.current_movie:
                assy.current_movie = movie
            #e should we switch to the part for which this movie was made?
            # No current way to tell how to do that, and this might be done even if it's not valid
            # for any loaded Part. So let's not... tho we might presume (from filename choice we used)
            # it was valid for Main Part. Maybe print warning for clip item, and for not valid? #e
            msg = "Using previously saved movie for this part."
            env.history.message(cmd + msg)
            return PlotTool(assy, movie)
        else:
            msg = redmsg("Can't find previously saved movie for this part.")
            env.history.message(cmd + msg)
    return
示例#17
0
    def Mirror(self):
        """
        Mirror the selected chunk(s) about a selected grid plane.
        """
        cmd = greenmsg("Mirror: ")
        #ninad060814 this is necessary to fix a bug. Otherwise program will
        #crash if you try to mirror when the top node of the part
        #(main part of clipboard) is selected

        if self.topnode.picked:
            self.topnode.unpick_top()

        self.mirrorJigs = self.getQualifiedMirrorJigs()

        jigCounter = len(self.mirrorJigs)

        if jigCounter < 1:
            msg1 = "No mirror plane selected."
            msg2 = " Please select a Reference Plane or a Grid Plane first."
            msg = redmsg(msg1+msg2)
            instr1 = "(If it doesn't exist, create it using"
            instr2 = "<b>Insert > Reference Geometry menu </b> )"
            instruction = instr1 + instr2
            env.history.message(cmd + msg  + instruction)
            return
        elif jigCounter >1:
            msg = redmsg("More than one plane selected. Please select only one plane and try again")
            env.history.message(cmd + msg )
            return

        for j in self.mirrorJigs:
            j.unpick()

        copiedObject = self.o.assy.part.copy_sel_in_same_part()

        # ninad060812 Get the axis vector of the Grid Plane. Then you need to
        #rotate the inverted chunk by pi around this axis vector
        self.mirrorAxis = self.mirrorJigs[0].getaxis()

        if isinstance(copiedObject, Chunk):
            copiedObject.name = copiedObject.name + "-Mirror"
            self._mirrorChunk(copiedObject)
            return
        elif isinstance(copiedObject, Group):
            copiedObject.name = "Mirrored Items"
            def mirrorChild(obj):
                if isinstance(obj, Chunk):
                    self._mirrorChunk(obj)
                elif isinstance(obj, Jig):
                    self._mirrorJig(obj)

            copiedObject.apply2all(mirrorChild)
        return
示例#18
0
    def makeChunkFromSelectedAtoms(self):
        """
        Create a new chunk from the selected atoms.
        """

        # ninad 070411 moved the original method out of 'merge' method to
        # facilitate implementation of 'Create New Chunk
        # from selected atoms' feature

        cmd = greenmsg("Create New Chunk: ")
        if not self.selatoms:
            msg1 = "Create New Chunk: "
            msg2 = redmsg("Select some atoms first to create a new chunk")
            env.history.message(msg1 + msg2)
            return

        # ninad070411 : Following checks if the selected molecules
        # belong to more than one chunk. If they don't (i.e. if they are a part of
        # a sinle chunk, it returns from the method with proper histry msg

        molList = []
        for atm in self.selatoms.values():
            if not len(molList) > 1:
                mol = atm.molecule
                if mol not in molList:
                    molList.append(mol)

        if len(molList) < 2:
            msg1 = "Create New Chunk: "
            msg2 = redmsg(
                "Not created as the selected atoms are part of the \
            same chunk."
            )
            env.history.message(msg1 + msg2)
            return

        # bruce 060329 new feature: work on atoms too (put all selected atoms into a new chunk)
        self.ensure_toplevel_group()  # avoid bug for part containing just one chunk, all atoms selected
        numol = Chunk(self.assy, gensym("Chunk", self.assy))
        natoms = len(self.selatoms)
        for a in self.selatoms.values():
            # leave the moved atoms picked, so still visible
            a.hopmol(numol)
        self.addmol(numol)
        # e should we add it in the same groups (and just after the chunks) which these atoms used to belong to?
        # could use similar scheme to placing jigs...
        msg = fix_plurals(
            "made chunk from %d atom(s)" % natoms
        )  # len(numol.atoms) would count bondpoints, this doesn't
        msg = msg.replace("chunk", numol.name)
        env.history.message(cmd + msg)
        self.w.win_update()
示例#19
0
    def makeChunkFromSelectedAtoms(self):
        """
        Create a new chunk from the selected atoms.
        """

        #ninad 070411 moved the original method out of 'merge' method to
        #facilitate implementation of 'Create New Chunk
        #from selected atoms' feature

        cmd = greenmsg("Create New Chunk: ")
        if not self.selatoms:
            msg1 = "Create New Chunk: "
            msg2 = redmsg('Select some atoms first to create a new chunk')
            env.history.message(msg1 + msg2)
            return

        #ninad070411 : Following checks if the selected molecules
        #belong to more than one chunk. If they don't (i.e. if they are a part of
        # a sinle chunk, it returns from the method with proper histry msg

        molList = []
        for atm in self.selatoms.values():
            if not len(molList) > 1:
                mol = atm.molecule
                if mol not in molList:
                    molList.append(mol)

        if len(molList) < 2:
            msg1 = "Create New Chunk: "
            msg2 = redmsg('Not created as the selected atoms are part of the \
            same chunk.')
            env.history.message(msg1 + msg2)
            return

        #bruce 060329 new feature: work on atoms too (put all selected atoms into a new chunk)
        self.ensure_toplevel_group(
        )  # avoid bug for part containing just one chunk, all atoms selected
        numol = Chunk(self.assy, gensym("Chunk", self.assy))
        natoms = len(self.selatoms)
        for a in self.selatoms.values():
            # leave the moved atoms picked, so still visible
            a.hopmol(numol)
        self.addmol(numol)
        #e should we add it in the same groups (and just after the chunks) which these atoms used to belong to?
        # could use similar scheme to placing jigs...
        msg = fix_plurals(
            "made chunk from %d atom(s)" %
            natoms)  # len(numol.atoms) would count bondpoints, this doesn't
        msg = msg.replace('chunk', numol.name)
        env.history.message(cmd + msg)
        self.w.win_update()
示例#20
0
    def placePlaneOffsetToAnother(self):
        """
        Orient the plane such that it is parallel to a selected plane , with an
        offset.
        """

        cmd = self.editCommand.cmd 

        jigList = self.win.assy.getSelectedJigs()
        if jigList:
            planeList = []
            for j in jigList:
                if isinstance(j, Plane) and (j is not self):
                    planeList.append(j)  

            #First, clear all the direction arrow drawings if any in 
            #the existing Plane objectes in the part 
            if not self.assy.part.topnode.members:
                msg = redmsg("Select a different plane first to place the"
                             " current plane offset to it")
                env.history.message(cmd + msg)
                return                            

            for p in self.assy.part.topnode.members:
                if isinstance(p, Plane):
                    if p.directionArrow:
                        p.directionArrow.setDrawRequested(False)

            if len(planeList) == 1:                
                self.offsetParentGeometry = planeList[0]
                self.offsetParentGeometry.directionArrow.setDrawRequested(True)

                if self.offsetParentGeometry.directionArrow.flipDirection:
                    offset =  2 * norm(self.offsetParentGeometry.getaxis())
                else:
                    offset = -2 * norm(self.offsetParentGeometry.getaxis())

                self.center = self.offsetParentGeometry.center + offset   
                self.quat   = Q(self.offsetParentGeometry.quat)
            else:
                msg = redmsg("Select exactly one plane to\
                             create a plane offset to it.")
                env.history.message(cmd + msg)
                return            
        else:            
            msg = redmsg("Select an existing plane first to\
                         create a plane offset to it.")
            env.history.message(cmd + msg)
            return    
        self.glpane.gl_update()            
示例#21
0
    def placePlaneOffsetToAnother(self):
        """
        Orient the plane such that it is parallel to a selected plane , with an
        offset.
        """

        cmd = self.editCommand.cmd

        jigList = self.win.assy.getSelectedJigs()
        if jigList:
            planeList = []
            for j in jigList:
                if isinstance(j, Plane) and (j is not self):
                    planeList.append(j)

            #First, clear all the direction arrow drawings if any in
            #the existing Plane objectes in the part
            if not self.assy.part.topnode.members:
                msg = redmsg("Select a different plane first to place the"
                             " current plane offset to it")
                env.history.message(cmd + msg)
                return

            for p in self.assy.part.topnode.members:
                if isinstance(p, Plane):
                    if p.directionArrow:
                        p.directionArrow.setDrawRequested(False)

            if len(planeList) == 1:
                self.offsetParentGeometry = planeList[0]
                self.offsetParentGeometry.directionArrow.setDrawRequested(True)

                if self.offsetParentGeometry.directionArrow.flipDirection:
                    offset = 2 * norm(self.offsetParentGeometry.getaxis())
                else:
                    offset = -2 * norm(self.offsetParentGeometry.getaxis())

                self.center = self.offsetParentGeometry.center + offset
                self.quat = Q(self.offsetParentGeometry.quat)
            else:
                msg = redmsg("Select exactly one plane to\
                             create a plane offset to it.")
                env.history.message(cmd + msg)
                return
        else:
            msg = redmsg("Select an existing plane first to\
                         create a plane offset to it.")
            env.history.message(cmd + msg)
            return
        self.glpane.gl_update()
示例#22
0
    def run_job(self):
        """
        Slot method for the 'Save and Run' button 
        """
        self.accept()

        # Run GAMESS job.  Return value r:
        # 0 = success
        # 1 = job cancelled
        # 2 = job failed.
        r = self.job.launch()

        if r == 1:  # Job was cancelled
            env.history.message(redmsg("GAMESS job cancelled."))
            return

        if r == 2:  # Job failed.
            env.history.message(
                redmsg(
                    "GAMESS job failed. Maybe you didn't set the right Gamess executable file. Make sure you can run the same job manually."
                ))
            return

        # Job success.
        fn = self.gamessJig.outputfile

        # Print energy or move atoms
        if self.pset.ui.runtyp == 0:  #Energy
            self.gamessJig.print_energy()
        else:  # Optimize
            try:
                r = self.gamessJig.move_optimized_atoms()
                # r = insertgms(self.gamessJig.assy, fn)
            except:
                print_compact_traceback(
                    "GamessProp.run_job(): error reading GAMESS OUT file [%s]: "
                    % fn)
                env.history.message(
                    redmsg("Internal error while inserting GAMESS geometry: " +
                           fn))
            else:
                if r:
                    env.history.message(redmsg("Atoms not adjusted."))
                else:
                    self.gamessJig.assy.changed(
                    )  # The file and the part are not the same.
                    self.gamessJig.print_energy(
                    )  # Print the final energy from the optimize OUT file, too.
                    env.history.message("Atoms adjusted.")
示例#23
0
 def do_main_menu_op(self, optype):
     """
     @note: optype should be Undo or Redo
     """
     op_was_available = not not self._current_main_menu_ops.get(optype)
     global _disable_UndoRedo
     if _disable_UndoRedo: #060414
         env.history.message(redmsg("%s is not permitted now (and this action was only offered due to a bug)" % optype))
         return
     global _AutoCheckpointing_enabled
     disabled = not _AutoCheckpointing_enabled #060312
     if disabled:
         _AutoCheckpointing_enabled = True # temporarily enable it, just during the Undo or Redo command
         self.checkpoint( cptype = "preUndo" ) # do a checkpoint with it enabled, so Undo or Redo can work normally.
         # Note: in theory this might change what commands are offered and maybe even cause the error message below to come out
         # (so we might want to revise it when disabled is true ##e), but I think that can only happen if there's a change_counter
         # bug, since the only way the enabled cp will see changes not seen by disabled one is if archive.update_before_checkpoint()
         # is first to set the change_counters (probably a bug); if this happens it might make Redo suddenly unavailable.
         ####e if optype is Redo, we could pass an option to above checkpoint to not destroy redo stack or make it inaccessible!
         # (such an option is nim)
     try:
         op = self._current_main_menu_ops.get(optype)
         if op:
             undo_xxx = op.menu_desc() # note: menu_desc includes history sernos
             env.history.message(u"%s" % undo_xxx) #e say Undoing rather than Undo in case more msgs?? ######@@@@@@ TEST u"%s"
             self.archive.do_op(op)
             self.assy.w.update_select_mode() #bruce 060227 try to fix bug 1576
             self.assy.w.win_update() #bruce 060227 not positive this isn't called elsewhere, or how we got away without it if not
         else:
             if not disabled:
                 print "no op to %r; not sure how this slot was called, since it should have been disabled" % optype
                 env.history.message(redmsg("Nothing to %s (and it's a bug that its menu item or tool button was enabled)" % optype))
             else:
                 print "no op to %r; autocp disabled (so ops to offer were recomputed just now; before that, op_was_available = %r); "\
                       "see code comments for more info" % ( optype, op_was_available)
                 if op_was_available:
                     env.history.message(redmsg("Nothing to %s (possibly due to a bug)" % optype))
                 else:
                     env.history.message(redmsg("Nothing to %s (and this action was only offered due to a bug)" % optype))
         pass
     except:
         print_compact_traceback()
         env.history.message(redmsg("Bug in %s; see traceback in console" % optype))
     if disabled:
         # better get the end-cp done now (since we might be relying on it for some reason -- I'm not sure)
         self.checkpoint( cptype = "postUndo" )
         _AutoCheckpointing_enabled = False # re-disable
     return
示例#24
0
    def optimize_geometry(self):
        """
        Optimize geometry
        """

        cmd = greenmsg("Optimize Geometry: ")

        errmsgs = ["GAMESS job aborted.", "Error: GAMESS job failed."]

        pset = self.pset
        runtyp = pset.ui.runtyp  # Save runtyp (Calculate) setting to restore it later.
        pset.ui.runtyp = 1  # Optimize
        origCalType = self.gmsjob.Calculation
        self.gmsjob.Calculation = 'Optimize'

        self.update_gamess_parms()

        # Run GAMESS job.  Return value r:
        # 0 = success
        # 1 = job aborted.
        # 2 = job failed.
        r = self.gmsjob.launch()

        pset.ui.runtyp = runtyp  # Restore to original value
        self.gmsjob.Calculation = origCalType

        if r:  # Job was aborted or an error occurred.
            msg = redmsg(errmsgs[r - 1])
            env.history.message(cmd + msg)
            return

        try:
            r2 = self.move_optimized_atoms()
        except:
            print_compact_traceback( "GamessProp.run_job(): error reading GAMESS OUT file [%s]: " % \
                    self.outputfile )
            env.history.message(
                redmsg(cmd +
                       "Internal error while inserting GAMESS geometry: " +
                       self.outputfile))
        else:
            if r2:
                env.history.message(cmd + redmsg("Atoms not adjusted."))
            else:
                self.assy.changed()  # The file and the part are not the same.
                self.print_energy(
                )  # Print the final energy from the optimize OUT file, too.
                env.history.message(cmd + "Atoms adjusted.")
 def _update_UI_do_updates(self):
     """
     @see: Command_PropertyManager._update_UI_do_updates()
     @see: DnaSegment_EditCommand.model_changed()
     @see: DnaSegment_EditCommand.hasResizableStructure()
     @see: self._current_model_changed_params()
     """
     
     currentParams = self._current_model_changed_params()
     
     #Optimization. Return from the model_changed method if the 
     #params are the same. 
     if same_vals(currentParams, self._previous_model_changed_params):
         return 
     
     number_of_segments, isStructResizable, why_not = currentParams
     
     #update the self._previous_model_changed_params with this new param set.
     self._previous_model_changed_params = currentParams
     
     if not isStructResizable:
         if not number_of_segments == 0:
             #disable all widgets                
             self._pmGroupBox1.setEnabled(False)
         msg = redmsg("DnaSegment is not resizable. Reason: %s"%(why_not))
         self.updateMessage(msg)
     else:
         if not self._pmGroupBox1.isEnabled():
             self._pmGroupBox1.setEnabled(True)
         msg = "Use resize handles to resize the segments"
         self.updateMessage(msg)
                 
     self.updateListWidgets() 
示例#26
0
def open_wiki_help_URL(url, whosdoingthis="Wiki help"):  # bruce 051229 split this out of open_wiki_help_dialog
    """
    Try to open the given url in the user's browser (unless they've set preferences to prevent this (NIM)),
    first emitting a history message containing the url
    (which is described as coming from whosdoingthis, which should be a capitalized string).
    Return True if there's no evidence of an error; print error message to history and return False if it definitely failed.
    """
    url = str(url)  # precaution in case of QString
    ###e should check prefs to see if we should really open browser; if not, print different hist message
    env.history.message("%s: opening " % whosdoingthis + url)  # see module docstring re "wiki help" vs. "web help"
    # print this in case user wants to open it manually or debug the url prefix preference
    try:
        webbrowser_open(url)
        worked = True
    except:
        # bruce 051201 catch exception to mitigate bug 1167
        # (e.g. when Linux user doesn't have BROWSER env var set).
        # Probably need to make this more intelligent, perhaps by
        # catching the specific exception in the bug report, knowing
        # the OS, passing options to webbrowser.open, etc.
        print_compact_traceback("webbrowser exception: ")
        env.history.message(
            redmsg("Problem opening web browser.") + "Suggest opening above URL by hand. "
            "On some platforms, setting BROWSER environment variable might help."
        )
        worked = False
    return worked
示例#27
0
 def update_icon(self, print_missing_file=False, found=None):
     """
     Update our icon according to whether our file exists or not (or use the boolean passed as found, if one is passed).
     (Exception: icon looks normal if filename is not set yet.
      Otherwise it looks normal if file is there, not normal if file is missing.)
     If print_missing_file is true, print an error message if the filename is non-null but the file doesn't exist.
     Return "not found" in case callers want to print their own error messages (for example, if they use a different filename).
     """
     #bruce 060620 split this out of readmmp_info_povrayscene_setitem for later use in copy_fixup_at_end (not yet done ###@@@).
     # But its dual function is a mess (some callers use their own filename) so it needs more cleanup. #e
     filename = self.povrayscene_file
     if found is None:
         found = not filename or os.path.exists(filename)
     # otherwise found should have been passed as True or False
     if found:
         self.const_pixmap = imagename_to_pixmap(
             "modeltree/povrayscene.png")
     else:
         self.const_pixmap = imagename_to_pixmap(
             "modeltree/povrayscene-notfound.png")
         if print_missing_file:
             msg = redmsg(
                 "POV-Ray Scene file [" + filename + "] does not exist."
             )  #e some callers would prefer orangemsg, cmd, etc.
             env.history.message(msg)
     return not found
示例#28
0
    def makeAnchor(self):
        """
        Anchors the selected atoms so that they will not move
        during a minimization or simulation run.
        """
        cmd = greenmsg("Anchor: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select at least one atom to create an Anchor."
            env.history.message(cmd + redmsg(msg))
            return

        # Print warning if over 200 atoms are selected.
        if atom_limit_exceeded_and_confirmed(self.assy.w,
                                             len(atoms),
                                             limit=200):
            return

        m = Anchor(self.assy, atoms)
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + "Anchor created")
        self.assy.w.win_update()
示例#29
0
 def selectDoubly(self):
     """
     Select any atom that can be reached from any currently
     selected atom through two or more non-overlapping sequences of
     bonds. Also select atoms that are connected to this group by
     one bond and have no other bonds.
     """
     ###@@@ same comment about interspace bonds as in selectConnected
     
     cmd = greenmsg("Select Doubly: ")
     
     if not self.selatoms:
         msg = redmsg("No atoms selected")
         env.history.message(cmd + msg)
         return
     
     alreadySelected = len(self.selatoms.values())
     from operations.op_select_doubly import select_doubly # new code, bruce 050520
     #e could also reload it now to speed devel!
     select_doubly(self.selatoms.values()) #e optim
     totalSelected = len(self.selatoms.values())
     
     from platform_dependent.PlatformDependent import fix_plurals
     info = fix_plurals("%d new atom(s) selected (besides the %d initially selected)." % \
                            (totalSelected - alreadySelected, alreadySelected) )
     env.history.message( cmd + info)
             
     if totalSelected > alreadySelected:
         ## otherwise, means nothing new selected. Am I right? ---Huaicai, not analyze the markdouble() algorithm yet 
         #self.w.win_update()
         self.o.gl_update()
     return
示例#30
0
 def _makeDuplexChunk(self, dnaGroup):
     """
     Returns a single DNA chunk given a dnaGroup containing multiple strand
     chunks.
     
     @param dnaGroup: The group object containing the DNA strand chunks.
     @type  dnaGroup: L{Group}
     
     @return: The DNA chunk.
     @rtype:  L{Chunk}
     """
     
     if not isinstance(dnaGroup.members[0], Chunk):
         env.history.message(redmsg(
             "Internal error in creating a single chunk DNA"))
         return
     
     for m in dnaGroup.members[1:]:
         if isinstance(m, Chunk):
             dnaGroup.members[0].merge(m)
             
     # Rename the merged chunk 
     dnaGroup.members[0].name = dnaGroup.name
     
     dnaChunk = dnaGroup.members[0]
     dnaChunk.setcolor(None)
     dnaGroup.ungroup()
     
     return dnaChunk
示例#31
0
 def __init__(self, mapping, chunk):
     # immediately memoize some settings which need to be constant
     # during use, as a bug precaution. Also do whatever precomputes
     # are convenient.
     writemmp_mapping_memo.__init__(self, mapping)
     self.chunk = chunk
     self.ladder = chunk.ladder
     if not dna_updater_is_enabled():
         msg = "Warning: can't convert PAM model when dna updater is disabled; affects [N] chunk(s)"
         env.history.deferred_summary_message(orangemsg(msg))
     elif not self.ladder:
         # (might happen if dna updater is turned off at runtime -- not sure;
         #  note, doing that might have worse effects, like self.ladder existing
         #  but being out of date, causing traceback errors. #### FIX those sometime (elsewhere).)
         print "error: ladder not set during writemmp, can't convert pam model, in %r" % chunk
         msg = "Error: [N] chunk(s) don't have ladders set"
         env.history.deferred_summary_message(redmsg(msg))
     else:
         self.convert_pam_enabled = True
     if self.convert_pam_enabled:
         # Note: this only means conversion is possible -- we don't yet know
         # if it's requested by options on this mapping and chunk.
         # The ladder memo will decide that.
         self._ladder_memo = mapping.get_memo_for(self.ladder)
         self._save_as_pam = self._ladder_memo._f_save_as_what_PAM_model()
     return
示例#32
0
    def merge(self):
        """
        Merges selected atoms into a single chunk, or merges the selected
        chunks into a single chunk.
        
        @note: If the selected atoms belong to the same chunk, nothing happens.
        """
        #mark 050411 changed name from weld to merge (Bug 515)
        #bruce 050131 comment: might now be safe for clipboard items
        # since all selection is now forced to be in the same one;
        # this is mostly academic since there's no pleasing way to use it on them,
        # though it's theoretically possible (since Groups can be cut and maybe copied).

        cmd = greenmsg("Combine Chunks: ")

        if self.selatoms:
            self.makeChunkFromSelectedAtoms()
            return

        if len(self.selmols) < 2:
            msg = redmsg("Need two or more selected chunks to merge")
            env.history.message(cmd + msg)
            return
        self.changed()  #bruce 050131 bugfix or precaution
        mol = self.selmols[0]
        for m in self.selmols[1:]:
            mol.merge(m)
示例#33
0
    def _update_UI_do_updates(self):
        """
        @see: Command_PropertyManager._update_UI_do_updates()
        @see: DnaSegment_EditCommand.model_changed()
        @see: DnaSegment_EditCommand.hasResizableStructure()
        @see: self._current_model_changed_params()
        """

        currentParams = self._current_model_changed_params()

        #Optimization. Return from the model_changed method if the
        #params are the same.
        if same_vals(currentParams, self._previous_model_changed_params):
            return

        number_of_segments, isStructResizable, why_not = currentParams

        #update the self._previous_model_changed_params with this new param set.
        self._previous_model_changed_params = currentParams

        if not isStructResizable:
            if not number_of_segments == 0:
                #disable all widgets
                self._pmGroupBox1.setEnabled(False)
            msg = redmsg("DnaSegment is not resizable. Reason: %s" % (why_not))
            self.updateMessage(msg)
        else:
            if not self._pmGroupBox1.isEnabled():
                self._pmGroupBox1.setEnabled(True)
            msg = "Use resize handles to resize the segments"
            self.updateMessage(msg)

        self.updateListWidgets()
    def conformationComboBoxChanged( self, inIndex ):
        """
        Slot for the Conformation combobox. It is called whenever the
        Conformation choice is changed.

        @param inIndex: The new index.
        @type  inIndex: int
        """
        self.basesPerTurnComboBox.clear()
        conformation  =  self.conformationComboBox.currentText()

        if conformation == "B-DNA":
            self.basesPerTurnComboBox.insertItem(0, "10.0")
            self.basesPerTurnComboBox.insertItem(1, "10.5")
            self.basesPerTurnComboBox.insertItem(2, "10.67")

            #10.5 is the default value for Bases per turn.
            #So set the current index to 1
            self.basesPerTurnComboBox.setCurrentIndex(1)

        elif conformation == "Z-DNA":
            self.basesPerTurnComboBox.insertItem(0, "12.0")

        elif inIndex == -1:
            # Caused by clear(). This is tolerable for now. Mark 2007-05-24.
            conformation = "B-DNA" # Workaround for "Restore Defaults".
            pass

        else:
            msg = redmsg("conformationComboBoxChanged(): \
            Error - unknown DNA conformation. Index = "+ inIndex)
            env.history.message(msg)

        self.duplexLengthSpinBox.setSingleStep(
                self.getDuplexRise(conformation) )
示例#35
0
    def moveAbsolute(self):
        """
        Move selected chunk(s), jig(s) to absolute X, Y, and Z by computing
        the bbox center of everything as if they were one big chunk, then move
        everything as a unit.
        """
        movables = self.graphicsMode.getMovablesForLeftDragging()
        if not movables:
            env.history.message(redmsg("No chunks or movable jigs selected."))
            return

        ## Compute bbox for selected chunk(s).

        bbox = BBox()
        for m in movables:
            if hasattr(m, "bbox"): # Fixes bug 1990. Mark 060702.
                bbox.merge(m.bbox)
        pt1 = bbox.center() # pt1 = center point for bbox of selected chunk(s).

        pt2 = self.propMgr.get_move_xyz() # pt2 = X, Y, Z values from PM
        offset = pt2 - pt1 # Compute offset for translating the selection

        self.assy.translateSpecifiedMovables(offset,
                                             movables = movables)

        # Print history message about what happened.
        if len(movables) == 1:
            msg = "[%s] moved to [X: %.2f] [Y: %.2f] [Z: %.2f]" % (movables[0].name, pt2[0], pt2[1], pt2[2])
        else:
            msg = "Selected chunks/jigs moved by offset [X: %.2f] [Y: %.2f] [Z: %.2f]" % (offset[0], offset[1], offset[2])
        env.history.message(msg)
        self.o.gl_update()
        return
示例#36
0
    def loadImage(self, file_name):
        """
        Loads an image to be displayed on the plane as a texture. Displays 
        a warning message if the image format is not supported or the file 
        cannot be open.

        This method should be extened to support basic image operations
        (resizing, flipping, cropping).

        @param file_name: The name of the image file.
        """

        # piotr 080528

        self.deleteImage()

        try:
            mipmaps, image = load_image_into_new_texture_name(file_name)
            self.imagePath = file_name  # piotr 080624
            self.tex_image = image
            # this gl_update may not be enough to show the image immediately
            self.glpane.gl_update()
        except:
            msg = redmsg("Cannot load plane image " + file_name)
            env.history.message(msg)
            self.tex_image = None
示例#37
0
    def viewParallelTo(self):
        """
        Set view parallel to the vector defined by 2 selected atoms.
        """
        cmd = greenmsg("Set View Parallel To: ")

        atoms = self.assy.selatoms_list()

        if len(atoms) != 2:
            msg = redmsg("You must select 2 atoms.")
            env.history.message(cmd + msg)
            return

        v = norm(atoms[0].posn()-atoms[1].posn())

        if vlen(v) < 0.0001: # Atoms are on top of each other.
            info = 'The selected atoms are on top of each other.  No change in view.'
            env.history.message(cmd + info)
            return

        # If vec is pointing into the screen, negate (reverse) vec.
        if dot(v, self.glpane.lineOfSight) > 0:
            v = -v

        # Compute the destination quat (q2).
        q2 = Q(V(0,0,1), v)
        q2 = q2.conj()

        self.glpane.rotateView(q2)

        info = 'View set parallel to the vector defined by the 2 selected atoms.'
        env.history.message(cmd + info)
示例#38
0
 def __init__(self, mapping, chunk):
     # immediately memoize some settings which need to be constant
     # during use, as a bug precaution. Also do whatever precomputes
     # are convenient.
     writemmp_mapping_memo.__init__(self, mapping)
     self.chunk = chunk
     self.ladder = chunk.ladder
     if not dna_updater_is_enabled():
         msg = "Warning: can't convert PAM model when dna updater is disabled; affects [N] chunk(s)"
         env.history.deferred_summary_message( orangemsg( msg))
     elif not self.ladder:
         # (might happen if dna updater is turned off at runtime -- not sure;
         #  note, doing that might have worse effects, like self.ladder existing
         #  but being out of date, causing traceback errors. #### FIX those sometime (elsewhere).)
         print "error: ladder not set during writemmp, can't convert pam model, in %r" % chunk
         msg = "Error: [N] chunk(s) don't have ladders set"
         env.history.deferred_summary_message( redmsg( msg))
     else:
         self.convert_pam_enabled = True
     if self.convert_pam_enabled:
         # Note: this only means conversion is possible -- we don't yet know
         # if it's requested by options on this mapping and chunk.
         # The ladder memo will decide that.
         self._ladder_memo = mapping.get_memo_for(self.ladder)
         self._save_as_pam = self._ladder_memo._f_save_as_what_PAM_model()
     return
示例#39
0
    def selectDoubly(self):
        """
        Select any atom that can be reached from any currently
        selected atom through two or more non-overlapping sequences of
        bonds. Also select atoms that are connected to this group by
        one bond and have no other bonds.
        """
        ###@@@ same comment about interspace bonds as in selectConnected

        cmd = greenmsg("Select Doubly: ")

        if not self.selatoms:
            msg = redmsg("No atoms selected")
            env.history.message(cmd + msg)
            return

        alreadySelected = len(self.selatoms.values())
        from operations.op_select_doubly import select_doubly # new code, bruce 050520
        #e could also reload it now to speed devel!
        select_doubly(self.selatoms.values()) #e optim
        totalSelected = len(self.selatoms.values())

        from platform_dependent.PlatformDependent import fix_plurals
        info = fix_plurals("%d new atom(s) selected (besides the %d initially selected)." % \
                               (totalSelected - alreadySelected, alreadySelected) )
        env.history.message( cmd + info)

        if totalSelected > alreadySelected:
            ## otherwise, means nothing new selected. Am I right? ---Huaicai, not analyze the markdouble() algorithm yet
            #self.w.win_update()
            self.o.gl_update()
        return
示例#40
0
 def calculate_energy(self):
     """
     Calculate energy.
     """
     
     cmd = greenmsg("Calculate Energy: ")
     
     errmsgs = ["GAMESS job aborted.",
                         "Error: GAMESS job failed."]
                         
     pset = self.pset
     runtyp = pset.ui.runtyp # Save runtyp (Calculate) setting to restore it later.
     pset.ui.runtyp = 0 # Energy calculation
     origCalType = self.gmsjob.Calculation
     self.gmsjob.Calculation = 'Energy'
     
     self.update_gamess_parms()
     
     # Run GAMESS job.  Return value r:
     # 0 = success
     # 1 = job aborted
     # 2 = job failed.
     r = self.gmsjob.launch()
     
     pset.ui.runtyp = runtyp # Restore to original value
     self.gmsjob.Calculation = origCalType
     
     if r: # Job was aborted or an error occurred.
         msg = redmsg(errmsgs[r-1])
         env.history.message( cmd + msg )
         return
         
     self.print_energy()
示例#41
0
    def loadImage(self, file_name):
        """
        Loads an image to be displayed on the plane as a texture. Displays 
        a warning message if the image format is not supported or the file 
        cannot be open.

        This method should be extened to support basic image operations
        (resizing, flipping, cropping).

        @param file_name: The name of the image file.
        """

        # piotr 080528
        
        self.deleteImage()
        
        try:
            mipmaps, image = load_image_into_new_texture_name(file_name)
            self.imagePath = file_name # piotr 080624
            self.tex_image = image
            # this gl_update may not be enough to show the image immediately
            self.glpane.gl_update()
        except:
            msg = redmsg("Cannot load plane image " + file_name)
            env.history.message(msg)
            self.tex_image = None
示例#42
0
    def conformationComboBoxChanged(self, inIndex):
        """
        Slot for the Conformation combobox. It is called whenever the
        Conformation choice is changed.
        
        @param inIndex: The new index.
        @type  inIndex: int
        """
        self.basesPerTurnComboBox.clear()
        conformation = self.conformationComboBox.currentText()

        if conformation == "B-DNA":
            self.basesPerTurnComboBox.insertItem(0, "10.0")
            self.basesPerTurnComboBox.insertItem(1, "10.5")
            self.basesPerTurnComboBox.insertItem(2, "10.67")

            #10.5 is the default value for Bases per turn.
            #So set the current index to 1
            self.basesPerTurnComboBox.setCurrentIndex(1)

        elif conformation == "Z-DNA":
            self.basesPerTurnComboBox.insertItem(0, "12.0")

        elif inIndex == -1:
            # Caused by clear(). This is tolerable for now. Mark 2007-05-24.
            conformation = "B-DNA"  # Workaround for "Restore Defaults".
            pass

        else:
            msg = redmsg("conformationComboBoxChanged(): \
            Error - unknown DNA conformation. Index = " + inIndex)
            env.history.message(msg)

        self.duplexLengthSpinBox.setSingleStep(
            self.getDuplexRise(conformation))
示例#43
0
    def calculate_energy(self):
        """
        Calculate energy.
        """

        cmd = greenmsg("Calculate Energy: ")

        errmsgs = ["GAMESS job aborted.", "Error: GAMESS job failed."]

        pset = self.pset
        runtyp = pset.ui.runtyp  # Save runtyp (Calculate) setting to restore it later.
        pset.ui.runtyp = 0  # Energy calculation
        origCalType = self.gmsjob.Calculation
        self.gmsjob.Calculation = 'Energy'

        self.update_gamess_parms()

        # Run GAMESS job.  Return value r:
        # 0 = success
        # 1 = job aborted
        # 2 = job failed.
        r = self.gmsjob.launch()

        pset.ui.runtyp = runtyp  # Restore to original value
        self.gmsjob.Calculation = origCalType

        if r:  # Job was aborted or an error occurred.
            msg = redmsg(errmsgs[r - 1])
            env.history.message(cmd + msg)
            return

        self.print_energy()
示例#44
0
    def makeESPImage(self):
        cmd = greenmsg("ESP Image: ")

        atoms = self.assy.selatoms_list()

        if len(atoms) < 3:
            msg = "You must select at least 3 atoms to create an ESP Image."
            env.history.message(cmd + redmsg(msg))
            return

        from analysis.ESP.ESPImage import ESPImage
        m = ESPImage(self.assy, atoms)
        m.edit()
        if m.cancelled:  # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return

        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        # After placing the jig, remove the atom list from the jig.
        m.atoms = []

        env.history.message(cmd + "ESP Image created.")
        self.assy.w.win_update()
        return
示例#45
0
 def update_node(self, ok_pressed=False):
     'Update the POV-Ray Scene node.'
     self.set_params( self.node, self.gather_parameters())
     
     ini, pov, out = self.node.get_povfile_trio()
     
     # If the node was renamed, rename the POV-Ray Scene file name, too.
     # Don't do this if the "Preview" button was pressed since the user could later
     # hit "Cancel". In that case we'd loose the original .pov file, which would not be good. 
     # Mark 060702.
     if ok_pressed and self.originalName != self.node.name:
         if os.path.isfile(self.originalPov):
             if os.path.isfile(pov):
                 # Normally, I'd never allow the user to delete an existing POV-Ray Scene file without asking. 
                 # For A8 I'll allow it since I've run out of time.
                 # This will be fixed when Bruce implements the new File class in A9 (or later). Mark 060702.
                 os.remove(pov)
             os.rename(self.originalPov, pov)
             
     # Write the POV-Ray Scene (.pov) file if this is a new node or if the node's ".pov" file doesn't exist. 
     # Possible ways the ".pov" file could be missing from an existing node:
     #   1. the user renamed the node in the Model Tree, or 
     #   2. the POV-Ray Scene node was deleted, which deletes the file in self.kill(), and then Undo was pressed, or
     #   3. the ".pov" file was deleted by the user another way (via OS).
     # In the future, the POV-Ray Scene should save the view quat in the MMP (info) record. Then it
     # would always be possible to regenerate the POV-Ray Scene file from the MMP record, even if  
     # the node's .pov file didn't exist on disk anymore. Mark 060701.
     
     if self.node_is_new or not os.path.exists(pov):
         errorcode, filename_or_errortext = self.node.write_povrayscene_file()
         if errorcode:
             # The Pov-Ray Scene file could not be written, so remove the node.
             self.remove_node()
             env.history.message( self.cmdname + redmsg(filename_or_errortext) )
     return
示例#46
0
 def unselectConnected(self, atomlist=None):
     """
     Unselect any atom that can be reached from any currently
     selected atom through a sequence of bonds.
     If <atomlist> is supplied, use it instead of the currently selected atoms.
     """
     cmd = greenmsg("Unselect Connected: ")
     
     if atomlist is None and not self.selatoms:
         msg = redmsg("No atoms selected")
         env.history.message(cmd + msg)
         return
     
     if atomlist is None: # test for None since atomlist can be an empty list.
         atomlist = self.selatoms.values()
         
     catoms = self.getConnectedAtoms(atomlist)
     if not len(catoms): return
     
     natoms = 0
     for atom in catoms[:]:
         if atom.picked:
             atom.unpick()
             if not atom.picked:
                 # Just in case a selection filter was applied to this atom.
                 natoms += 1 
     
     from platform_dependent.PlatformDependent import fix_plurals
     info = fix_plurals( "%d atom(s) unselected." % natoms)
     env.history.message( cmd + info)
     self.o.gl_update()
示例#47
0
    def merge(self):
        """
        Merges selected atoms into a single chunk, or merges the selected
        chunks into a single chunk.

        @note: If the selected atoms belong to the same chunk, nothing happens.
        """
        #mark 050411 changed name from weld to merge (Bug 515)
        #bruce 050131 comment: might now be safe for clipboard items
        # since all selection is now forced to be in the same one;
        # this is mostly academic since there's no pleasing way to use it on them,
        # though it's theoretically possible (since Groups can be cut and maybe copied).

        cmd = greenmsg("Combine Chunks: ")

        if self.selatoms:
            self.makeChunkFromSelectedAtoms()
            return

        if len(self.selmols) < 2:
            msg = redmsg("Need two or more selected chunks to merge")
            env.history.message(cmd + msg)
            return
        self.changed() #bruce 050131 bugfix or precaution
        mol = self.selmols[0]
        for m in self.selmols[1:]:
            mol.merge(m)
    def model_changed(self): 
        """
        @see: DnaSegment_EditCommand.model_changed()
        @see: DnaSegment_EditCommand.hasResizableStructure()
        @see: self._current_model_changed_params()
        """
        currentParams = self._current_model_changed_params()
        #Optimization. Return from the model_changed method if the 
        #params are the same. 
        if same_vals(currentParams, self._previous_model_changed_params):
            return 

        isStructResizable, why_not = currentParams
        #update the self._previous_model_changed_params with this new param set.
        self._previous_model_changed_params = currentParams

        if not isStructResizable:
            #disable all widgets
            if self._pmGroupBox1.isEnabled():
                self._pmGroupBox1.setEnabled(False)
                msg = redmsg("DnaSegment is not resizable. Reason: %s"%(why_not))
                self.updateMessage(msg)
        else:
            if not self._pmGroupBox1.isEnabled():
                self._pmGroupBox1.setEnabled(True)
                msg = "Use resize handles to resize the segment. Drag any axis or sugar"\
                    " atom for translation or rotation about axis respectively. Dragging"\
                    " any bond will freely move the whole segment."
                self.updateMessage(msg)
    def makeAnchor(self):
        """
        Anchors the selected atoms so that they will not move
        during a minimization or simulation run.
        """
        cmd = greenmsg("Anchor: ")

        atoms = self.assy.selatoms_list()

        if not atoms:
            msg = "You must select at least one atom to create an Anchor."
            env.history.message(cmd + redmsg(msg))
            return

        # Print warning if over 200 atoms are selected.
        if atom_limit_exceeded_and_confirmed(self.assy.w,
                                             len(atoms),
                                             limit=200):
            return

        m = Anchor(self.assy, atoms)
        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        env.history.message(cmd + "Anchor created")
        self.assy.w.win_update()
示例#50
0
    def setup(self, pov=None):
        """
        Show the Properties Manager dialog. If <pov> is supplied,
        get the parameters from it and load the dialog widgets.
        """
        if not self.win.assy.filename:
            env.history.message(self.cmdname + redmsg(
                "Can't insert POV-Ray Scene until the current part has been saved."
            ))
            return

        if not pov:
            self.node_is_new = True
            from model.PovrayScene import PovrayScene
            self.node = PovrayScene(self.win.assy, None)
        else:
            self.node_is_new = False
            self.node = pov

        self.name = self.originalName = self.node.name
        ini, self.originalPov, out = self.node.get_povfile_trio()
        self.width, self.height, self.output_type = self.node.get_parameters()

        self.update_widgets()
        self.previousParams = params = self.gather_parameters()
        self.show()
示例#51
0
    def command_for_insert_menu(self):
        """
        Run an Insert Whatever menu command to let the user generate things using this plugin.
        """
        if self.errorcode:
            env.history.message(redmsg("Plugin %r is permanently disabled due to this error, reported previously: %s" % \
                               (self.plugin_name, self.errortext)))
            return
        self.create_working_directory_if_needed()
        assert not self.errorcode
        if debug_run():
            print 'ought to insert a', self.what_we_generate
        self.make_dialog_if_needed()
        dialog = self.dialog
        ###e Not yet properly handled: retaining default values from last time it was used. (Should pass dict of them to the maker.)
        dialog.set_defaults({}) ### IMPLEM
        controller = GeneratorController(self.win, dialog, self)
            # Note: this needs both self and the dialog, to be inited.
            # So it takes care of telling the dialog to control it (and not some prior controller).
        dialog.show()
        # now it's able to take commands and run its callbacks; that does not happen inside this method, though, does it?
        # hmm, good question... if it's modal, this makes things easier (re preview and bug protection)...
        # and it means the undo wrapping was ok... but what do we do here to make it modal?
        # 1. find out by test if other generators are modal.
        # 2. find out from code, how.

        pass###e
示例#52
0
    def moveAbsolute(self):
        """
        Move selected chunk(s), jig(s) to absolute X, Y, and Z by computing
        the bbox center of everything as if they were one big chunk, then move
        everything as a unit.
        """
        movables = self.graphicsMode.getMovablesForLeftDragging()
        if not movables:
            env.history.message(redmsg("No chunks or movable jigs selected."))
            return

        ## Compute bbox for selected chunk(s).

        bbox = BBox()
        for m in movables:
            if hasattr(m, "bbox"):  # Fixes bug 1990. Mark 060702.
                bbox.merge(m.bbox)
        pt1 = bbox.center(
        )  # pt1 = center point for bbox of selected chunk(s).

        pt2 = self.propMgr.get_move_xyz()  # pt2 = X, Y, Z values from PM
        offset = pt2 - pt1  # Compute offset for translating the selection

        self.assy.translateSpecifiedMovables(offset, movables=movables)

        # Print history message about what happened.
        if len(movables) == 1:
            msg = "[%s] moved to [X: %.2f] [Y: %.2f] [Z: %.2f]" % (
                movables[0].name, pt2[0], pt2[1], pt2[2])
        else:
            msg = "Selected chunks/jigs moved by offset [X: %.2f] [Y: %.2f] [Z: %.2f]" % (
                offset[0], offset[1], offset[2])
        env.history.message(msg)
        self.o.gl_update()
        return
示例#53
0
def debug_make_BorrowerChunk_raw(do_addmol=True):
    win = env.mainwindow()
    atomset = win.assy.selatoms
    if not atomset:
        env.history.message(
            redmsg(
                "Need selected atoms to make a BorrowerChunk (for debugging only)"
            ))
    else:
        atomset = dict(
            atomset
        )  # copy it, since we shouldn't really add singlets to assy.selatoms...
        for atom in atomset.values(
        ):  # not itervalues, we're changing it in the loop!
            # BTW Python is nicer about this than I expected:
            # exceptions.RuntimeError: dictionary changed size during iteration
            for bp in atom.singNeighbors(
            ):  # likely bugs if these are not added into the set!
                atomset[bp.key] = bp
            assy = atom.molecule.assy  # these are all the same, and we do this at least once
        chunk = BorrowerChunk(assy, atomset)
        if do_addmol:
            win.assy.addmol(chunk)
        import __main__
        __main__._bc = chunk
        env.history.message(
            orangemsg("__main__._bc = %s (for debugging only)" %
                      quote_html(safe_repr(chunk))))
    win.win_update()  #k is this done by caller?
    return
示例#54
0
    def makeSimMovie(self): ####@@@@ some of this should be a Movie method since it uses attrs of Movie...
        #bruce 050324 made this from the Part method makeSimMovie.
        # It's called only from self.run() above; not clear it should be a separate method,
        # or if it is, that it's split from the caller at the right boundary.
        suffix = self.part.movie_suffix()
        if suffix is None: #bruce 050316 temporary kluge
            msg = redmsg( "Simulator is not yet implemented for clipboard items.")
            env.history.message(self.cmdname + ": " + msg)
            return -1
        ###@@@ else use suffix below!

        self.simcntl = SimSetup(self.win, self.part, suffix = suffix)
            # this now has its own sticky params, doesn't need previous_movie [bruce 060601, fixing bug 1840]
            # Open SimSetup dialog [and run it until user dismisses it]
        movie = self.simcntl.movie # always a Movie object, even if user cancelled the dialog

        if movie.cancelled:
            # user hit Cancel button in SimSetup Dialog. No history msg went out; caller will do that.
            movie.destroy()
            return -1
        r = writemovie(self.part, movie, print_sim_warnings = True, cmdname = self.cmdname)
            # not passing mtype means "run dynamic sim (not minimize), make movie"
            ###@@@ bruce 050324 comment: maybe should do following in that function too
        if not r:
            # Movie file created. Initialize. ###@@@ bruce 050325 comment: following mods private attrs, needs cleanup.
            movie.IsValid = True # Movie is valid.###@@@ bruce 050325 Q: what exactly does this (or should this) mean?
                ###@@@ bruce 050404: need to make sure this is a new obj-- if not always and this is not init False, will cause bugs
            self.movie = movie # bruce 050324 added this
            # it's up to caller to store self.movie in self.assy.current_movie if it wants to.
        return r
    def makeESPImage(self):
        cmd = greenmsg("ESP Image: ")

        atoms = self.assy.selatoms_list()

        if len(atoms) < 3:
            msg = "You must select at least 3 atoms to create an ESP Image."
            env.history.message(cmd + redmsg(msg))
            return

        from analysis.ESP.ESPImage import ESPImage
        m = ESPImage(self.assy, atoms)
        m.edit()
        if m.cancelled: # User hit 'Cancel' button in the jig dialog.
            env.history.message(cmd + "Cancelled")
            return

        self.unpickall_in_GLPane()
        self.place_new_jig(m)

        # After placing the jig, remove the atom list from the jig.
        m.atoms = []

        env.history.message(cmd + "ESP Image created.")
        self.assy.w.win_update()
        return
示例#56
0
    def unselectConnected(self, atomlist=None):
        """
        Unselect any atom that can be reached from any currently
        selected atom through a sequence of bonds.
        If <atomlist> is supplied, use it instead of the currently selected atoms.
        """
        cmd = greenmsg("Unselect Connected: ")

        if atomlist is None and not self.selatoms:
            msg = redmsg("No atoms selected")
            env.history.message(cmd + msg)
            return

        if atomlist is None: # test for None since atomlist can be an empty list.
            atomlist = self.selatoms.values()

        catoms = self.getConnectedAtoms(atomlist)
        if not len(catoms): return

        natoms = 0
        for atom in catoms[:]:
            if atom.picked:
                atom.unpick()
                if not atom.picked:
                    # Just in case a selection filter was applied to this atom.
                    natoms += 1

        from platform_dependent.PlatformDependent import fix_plurals
        info = fix_plurals( "%d atom(s) unselected." % natoms)
        env.history.message( cmd + info)
        self.o.gl_update()
示例#57
0
    def _update_UI_do_updates(self):
        """
        @see: Command_PropertyManager._update_UI_do_updates()
        @see: DnaSegment_EditCommand.command_update_UI()
        @see: DnaSegment_EditCommand.hasResizableStructure()
        @see: self._current_model_changed_params()
        """
        currentParams = self._current_model_changed_params()
        #Optimization. Return from the model_changed method if the
        #params are the same.
        if same_vals(currentParams, self._previous_model_changed_params):
            return

        isStructResizable, why_not = currentParams
        #update the self._previous_model_changed_params with this new param set.
        self._previous_model_changed_params = currentParams

        if not isStructResizable:
            #disable all widgets
            if self._pmGroupBox1.isEnabled():
                self._pmGroupBox1.setEnabled(False)
                msg = redmsg("DnaSegment is not resizable. Reason: %s" %
                             (why_not))
                self.updateMessage(msg)
        else:
            if not self._pmGroupBox1.isEnabled():
                self._pmGroupBox1.setEnabled(True)
                msg = "Use resize handles to resize the segment. Drag any axis or sugar"\
                    " atom for translation or rotation about axis respectively. Dragging"\
                    " any bond will freely move the whole segment."
                self.updateMessage(msg)