class PropertyEditor(QtWidgets.QWidget): def __init__(self, viewer, history): super(PropertyEditor, self).__init__() # set class fields self.viewer = viewer self.history = history #widgets import self.ui = Ui_propertyEditor() self.ui.setupUi(self) self.tree = self.ui.propertyTree self.tree. setColumnWidth(0, 100) self.tree. setColumnWidth(1, 140) #initializes widgets on tree self.xRotate = QtWidgets.QDoubleSpinBox(self.tree) self.xRotate. setSingleStep (10.) self.xRotate. setRange (-360., 360.) xRotateAt = self.tree.topLevelItem(1).child(0) self.yRotate = QtWidgets.QDoubleSpinBox(self.tree) self.yRotate. setSingleStep (10.) self.yRotate. setRange (-360., 360.) yRotateAt = self.tree.topLevelItem(1).child(1) self.zRotate = QtWidgets.QDoubleSpinBox(self.tree) self.zRotate. setSingleStep (10.) self.zRotate. setRange (-360., 360.) zRotateAt = self.tree.topLevelItem(1).child(2) self.xMoveBy = QtWidgets.QDoubleSpinBox(self.tree) self.xMoveBy. setSingleStep (0.5) self.xMoveBy. setRange (-1000., 1000.) xMoveByAt = self.tree.topLevelItem(2).child(0) self.yMoveBy = QtWidgets.QDoubleSpinBox(self.tree) self.yMoveBy. setSingleStep (0.5) self.yMoveBy. setRange (-1000., 1000.) yMoveByAt = self.tree.topLevelItem(2).child(1) self.zMoveBy = QtWidgets.QDoubleSpinBox(self.tree) self.zMoveBy. setSingleStep (0.5) self.zMoveBy. setRange (-1000., 1000.) zMoveByAt = self.tree.topLevelItem(2).child(2) #adds widgets to tree self.tree.setItemWidget(xRotateAt, 1, self.xRotate) self.tree.setItemWidget(yRotateAt, 1, self.yRotate) self.tree.setItemWidget(zRotateAt, 1, self.zRotate) self.tree.setItemWidget(xMoveByAt, 1, self.xMoveBy) self.tree.setItemWidget(yMoveByAt, 1, self.yMoveBy) self.tree.setItemWidget(zMoveByAt, 1, self.zMoveBy) #manages widget events self.xRotate.valueChanged.connect(self.Rotate) self.yRotate.valueChanged.connect(self.Rotate) self.zRotate.valueChanged.connect(self.Rotate) self.xMoveBy.valueChanged.connect(self.MoveBy) self.yMoveBy.valueChanged.connect(self.MoveBy) self.zMoveBy.valueChanged.connect(self.MoveBy) self.tree.resizeColumnToContents(0) self.tree.resizeColumnToContents(1) #initialize tree window self.reset() def reset(self): #print "PropertyEditor reset " self.mixture = Mixture(None) self.registry = dict() #self.ident = None self.resetBoxes() self.setToolTip("Select molecules to activate.") self.setEnabled(False) self.update() def update(self): # update resistry presentMolecules = self.history.currentState().getMixture().molecules() #print "PropertyEditor update ",presentMolecules, self.registry regKeys = list(self.registry.keys()) for regKey in regKeys: if not regKey in presentMolecules: if self.mixture.hasMoleculeID(regKey): self.mixture.remove(regKey) self.registry.pop(regKey) self.resetBoxes() QtWidgets.QWidget.update(self) def resetBoxes(self): if len(self) == 0: self.tree.topLevelItem(0).setText(1, "") else: self.tree.topLevelItem(0).setText(1, str(self)) self.dx = 0. self.dy = 0. self.dz = 0. self.anglex = 0. self.angley = 0. self.anglez = 0. self.xRotate.setValue(0.) self.yRotate.setValue(0.) self.zRotate.setValue(0.) self.xMoveBy.setValue(0.) self.yMoveBy.setValue(0.) self.zMoveBy.setValue(0.) #show molecule name in the editor def setMolecule(self, molecule, ident, removeIfPresent=False): ''' Returns True if the molecule ends up selected, False otherwise.. ''' from .BuildTab import ShownSolvent #print "PropertyEditor setMolecule new", ident, self.registry if ident not in self.registry: if ShownSolvent.isSolvent(ident): mixture = self.history.currentState().getMixture() mixtureNames = mixture.molecules() #print "PropertyEditor setMolecule SOLVENT(",mixtureNames pos = ident.find(')')+1 for mol in mixtureNames: if mol[:pos] == ident[:pos]: self.registry[mol] = self.mixture.add(mixture.getMolecule(mol), False) self.registry[mol] = mixture.getMolecule(mol) else: #print "PropertyEditor setMolecule adding", ident self.registry[ident] = molecule #print "PropertyEditor setMolecule adding to mixture", ident, self.mixture.molecules() self.mixture.add(molecule, False) #self.ident = ident #self.ident = self.getId() self.setToolTip("Manage molecules' positions.") self.setEnabled(True) return False self.resetBoxes() else: #print "PropertyEditor setMolecule duplicate",ident, self.registry if removeIfPresent: if ShownSolvent.isSolvent(ident): mixture = self.history.currentState().getMixture() mixtureNames = mixture.molecules() pos = ident.find(')')+1 for mol in mixtureNames: #print "PropertyEditor removing ",ident[:pos], mol[:pos] if mol[:pos] == ident[:pos]: #print "PropertyEditor OK " self.removeSelection(mixture.getMolecule(mol), mol) else: self.removeSelection(molecule, ident) return True #print "PropertyEditor setMolecule reseting" #print "PropertyEditor setMolecule finished" def removeSelection(self, molecule, ident): if ident in self.registry: self.mixture.remove(self.mixture.getMoleculeID(molecule)) self.registry.pop(ident) #print "PropertyEditor removeSelection removed:",ident if len(self.registry) == 0: self.reset() #print "PropertyEditor setMolecule reseting" self.resetBoxes() def hasSelections(self): return len(self.registry) > 0 def selectedMolecules(self): #print "selectedMolecules ", self.registry return list(self.registry.values()) def selectedNames(self): #print "selectedMolecules ",self.registry return list(self.registry.keys()) def __str__(self): return str(list(self.registry.keys())) def __len__(self): return len(self.registry) #show rotation values in the editor def Rotate(self): if self.mixture.order() > 0: x = self.xRotate.value() y = self.yRotate.value() z = self.zRotate.value() value = str(x) + " x " + str(y) + " x " + str(z) self.tree.topLevelItem(1).setText(1, value) center = self.mixture.center() self.mixture.moveBy([-xx for xx in center]) #print "Rotate ", x-self.anglex,y-self.angley,z-self.anglez self.mixture.rotateDeg(x-self.anglex,y-self.angley,z-self.anglez) self.mixture.moveBy(center) self.anglex = x self.angley = y self.anglez = z self.history.currentState().getMixture().setChanged() self.viewer.update() else: self.tree.topLevelItem(1).setText(1, "0 x 0 x 0") def MoveBy(self): x = self.xMoveBy.value() y = self.yMoveBy.value() z = self.zMoveBy.value() value = str(x) + " x " + str(y) + " x " + str(z) self.tree.topLevelItem(2).setText(1, value) self.mixture.moveBy([x-self.dx,y-self.dy,z-self.dz]) self.dx = x self.dy = y self.dz = z self.history.currentState().getMixture().setChanged() self.viewer.update() def getId(self): return str(self.mixture.moleculeNames())
class ShownMoleculesSet(set): def __init__(self, mixture): print("ShownMoleculesSet,__init__ caller=", inspect.stack()[1]) #[3], mixture, type(mixture) if isinstance(mixture, list): self.mixture = Mixture() for m in mixture: self.mixture.add(m) self.showAll() else: self.mixture = mixture def show(self, mol): #print "ShownMolecules show",mol self.add(mol) def showAll(self, mixture=None): if mixture != None: self.addMolecules(mixture) for mol in self.mixture: self.add(mol) def add(self, mol): super(ShownMoleculesSet, self).add(self.mixture.getMolecule(mol)) def hide(self, mol): self.discard(mol) def remove(self, mol): #print "ShownMoleculesSet remove ",mol #try: if isinstance(mol, Molecule): super(ShownMoleculesSet, self).remove(mol) else: super(ShownMoleculesSet, self).remove(self.mixture.getMolecule(mol)) #except: #pass def discard(self, mol): super(ShownMoleculesSet, self).discard(self.mixture.getMolecule(mol)) ''' def discardFrom(self, molIDSet): molset = set([ self.mixture.getMolecule(m) for m in molIDSet]) super(ShownMoleculesSet, self).difference(set(molSet)) ''' def duplicate(self, mol): pass def __deepcopy__(self, memo): ''' Blocks deepcopy because it takes too long. Copy done manually in push() ''' pass def isShown(self, mol): #print "isShown ", mol, mol in self.keys(), self[mol] try: return self.mixture.getMolecule(mol) in self except: return False def shownList(self, mixture): print("WARNING: ShownMoleculesSet deprecated.") return list(self) def addMolecules(self, mixture): for mol in mixture: self.add(mol) def addDictionary(self, shDict): ''' Adds information from a ShownMolecules object. ''' for mol in shDict: if shDict[mol]: self.add(mol) def updateMixture(self, mixture): self.intersection_update( set([self.mixture.getMolecule(mol) for mol in mixture])) self.mixture = mixture def names(self): return [self.mixture.getMoleculeID(molecule) for molecule in self]