class NamingSystemPopup(TemporaryBasePopup): help_url = joinPath(getHelpUrlDir(), 'NamingSystem.html') def __init__(self, parent, namingSysList=None, namingSysDict=None): # Constructor doesn't do much except call body # The parent is self.parent (parent of the popup) self.namingSys = None self.namingSysList = namingSysList self.namingSysDict = namingSysDict # modal = true means that it won't continue unless this one returns value TemporaryBasePopup.__init__(self, parent=parent, title='Choose namingSys', modal=False, transient=True) def body(self, master): # # Popup gui # # First row row = 0 label = Label(master, text="Choose a naming system:") label.grid(row=row, column=0, sticky=Tkinter.W) row = row + 1 label = Label(master, text="(% matches in brackets)") label.grid(row=row, column=0, sticky=Tkinter.W) row = row + 1 self.menu = PulldownMenu(master, entries=self.namingSysList) self.menu.grid(row=row, column=0, sticky=Tkinter.EW) row = row + 1 texts = ['OK'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Exit', help_url=self.help_url) buttons.grid(row=row, column=0) def apply(self): self.namingSysName = self.namingSysDict[self.menu.getSelected()] return True
class ItemSelectPopup(BasePopup): def __init__(self, parent, entries, label='', message='', select_text='Select', *args, **kw): self.entries = entries self.label = label self.message = message self.select_text = select_text self.item = None kw['title'] = 'Select item' kw['transient'] = True kw['modal'] = True BasePopup.__init__(self, parent=parent, *args, **kw) def body(self, master): master.grid_rowconfigure(0, weight=1) master.grid_columnconfigure(1, weight=1) row = 0 if (self.message): label = Label(master, text=self.message) label.grid(row=row, column=0, columnspan=2, sticky=Tkinter.W) row = row + 1 if (self.label): label = Label(master, text=self.label) label.grid(row=row, column=0, sticky=Tkinter.W) self.itemMenu = PulldownMenu(master, entries=self.entries) self.itemMenu.grid(row=row, column=1, sticky=Tkinter.EW) row = row + 1 texts = [self.select_text] commands = [self.ok] buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Cancel') buttons.grid(row=row, column=0, columnspan=2, sticky=Tkinter.EW) def apply(self): self.item = self.itemMenu.getSelected() return True
class BacusPopup(BasePopup): def __init__(self, parent, *args, **kw): self.project = parent.project self.hNoesy = None self.nNoesy = None self.cNoesy = None self.shiftList = None BasePopup.__init__(self, parent, title="BACUS control module", **kw) def body(self, guiParent): guiParent.grid_columnconfigure(0, weight=1) row = 0 guiParent.grid_rowconfigure(row, weight=1) inputFrame = LabelFrame(guiParent, text='Inputs:') inputFrame.grid(row=row, column=0, sticky=Tkinter.NSEW) label = Label(inputFrame, text='NOESY:') label.grid(row=0, column=0, sticky=Tkinter.NW) self.hNoesyPulldown = PulldownMenu(inputFrame,callback=self.setHNoesy) self.hNoesyPulldown.grid(row=0, column=1, sticky=Tkinter.NW) label = Label(inputFrame, text='15N NOESY:') label.grid(row=1, column=0, sticky=Tkinter.NW) self.nNoesyPulldown = PulldownMenu(inputFrame,callback=self.setNNoesy) self.nNoesyPulldown.grid(row=1, column=1, sticky=Tkinter.NW) label = Label(inputFrame, text='13C NOESY:') label.grid(row=2, column=0, sticky=Tkinter.NW) self.cNoesyPulldown = PulldownMenu(inputFrame,callback=self.setCNoesy) self.cNoesyPulldown.grid(row=2, column=1, sticky=Tkinter.NW) label = Label(inputFrame, text='Shift List:') label.grid(row=3, column=0, sticky=Tkinter.NW) self.shiftListPulldown = PulldownMenu(inputFrame,callback=self.setShiftList) self.shiftListPulldown.grid(row=3, column=1, sticky=Tkinter.NW) label = Label(inputFrame, text='2d BACUS executable:') label.grid(row=4, column=0, sticky=Tkinter.NW) self.executableEntry = Entry(inputFrame, text='/home/tjs23/clouds/justin/SpiBacusMidge/bacus/bacus_tjs.exe') self.executableEntry.grid(row=4, column=1, sticky=Tkinter.NW) self.executableButton = Button(inputFrame, text='Choose file', command=self.chooseExecutable) self.executableButton.grid(row=5, column=1, sticky=Tkinter.EW) row += 1 outputFrame = LabelFrame(guiParent, text='Output:') outputFrame.grid(row=row, column=0, sticky=Tkinter.NSEW) row += 1 texts = ['Run BACUS 2d','Run BACUS 3d'] commands = [self.runBacus,self.runBacus3d] self.bottomButtons = createDismissHelpButtonList(guiParent,texts=texts,commands=commands,expands=0,help_url=None) self.bottomButtons.grid(row=row, column=0, sticky=Tkinter.EW) self.update() def chooseExecutable(self): fileTypes = [FileType('Table', ['*.exe']), FileType('All', ['*'])] fileSelectPopup = FileSelectPopup(self, file_types = fileTypes, title = 'Choose 2d BACUS executable', dismiss_text = 'Cancel', selected_file_must_exist = False) fileName = fileSelectPopup.getFile() if fileName: self.executableEntry.set(fileName) def update(self): # set defaults via pulldown callbacks names = [self.getPeakListlabel(x) for x in self.gethNoesys()] if names: self.hNoesyPulldown.setup(names,0) else: self.hNoesyPulldown.setup([],-1) names = [self.getPeakListlabel(x) for x in self.getNNoesys()] if names: self.nNoesyPulldown.setup(names,0) else: self.nNoesyPulldown.setup([],-1) names = [self.getPeakListlabel(x) for x in self.getCNoesys()] if names: self.cNoesyPulldown.setup(names,0) else: self.cNoesyPulldown.setup([],-1) names = ['Shift List %d' % x.serial for x in self.getShiftLists()] if names: self.shiftListPulldown.setup(names,0) else: self.shiftListPulldown.setup([],-1) self.updateButtons() def updateButtons(self): if ( self.cNoesy or self.nNoesy ) and self.shiftList: self.bottomButtons.buttons[1].enable() else: self.bottomButtons.buttons[1].disable() if self.hNoesy and self.executableEntry.get() and self.shiftList: self.bottomButtons.buttons[0].enable() else: self.bottomButtons.buttons[0].disable() def runBacus3d(self, fileRoot='CCPN1'): if ( self.cNoesy or self.nNoesy ) and self.shiftList: run3dBacus(fileRoot,self.shiftList,self.cNoesy,self.nNoesy) def runBacus(self, fileRoot='CCPN1'): executable = self.executableEntry.get() if self.hNoesy and self.shiftList and executable: run2dBacus(fileRoot, executable, self.hNoesy, self.shiftList) def getPeakListlabel(self, peakList): return '%s:%s:%d' % (peakList.dataSource.experiment.name, peakList.dataSource.name, peakList.serial) def getShiftLists(self): shiftLists = [] if self.project: nmrProject = self.project.currentNmrProject shiftLists = nmrProject.findAllMeasurementLists(className='ShiftList') return list(shiftLists) def setShiftList(self, index, name=None): shiftLists = self.getShiftLists() if shiftLists: self.shiftList = shiftLists[index] else: self.shiftList = None def gethNoesys(self): peakLists = [] if self.project: for experiment in self.project.currentNmrProject.experiments: for spectrum in experiment.dataSources: isotopes = getSpectrumIsotopes(spectrum) if isotopes == ['1H', '1H']: for peakList in spectrum.peakLists: #if 'NOE' in experiment.name.upper(): # peakLists.insert(0, peakList) #else: peakLists.append(peakList) return peakLists def getNNoesys(self): peakLists = [] if self.project: for experiment in self.project.currentNmrProject.experiments: for spectrum in experiment.dataSources: isotopes = getSpectrumIsotopes(spectrum) isotopes.sort() if isotopes == ['15N', '1H', '1H']: for peakList in spectrum.peakLists: #if 'NOE' in experiment.name.upper(): # peakLists.insert(0, peakList) #else: peakLists.append(peakList) return peakLists def getCNoesys(self): peakLists = [] if self.project: for experiment in self.project.currentNmrProject.experiments: for spectrum in experiment.dataSources: isotopes = getSpectrumIsotopes(spectrum) isotopes.sort() if isotopes == ['13C', '1H', '1H']: for peakList in spectrum.peakLists: if 'NOE' in experiment.name.upper(): peakLists.insert(0, peakList) else: peakLists.append(peakList) return peakLists def setHNoesy(self, index, name=None): peakLists = self.gethNoesys() if peakLists: self.hNoesy = peakLists[index] else: self.hNoesy = None def setNNoesy(self, index, name=None): peakLists = self.getNNoesys() if peakLists: self.nNoesy = peakLists[index] else: self.nNoesy = None def setCNoesy(self, index, name=None): peakLists = self.getCNoesys() if peakLists: self.cNoesy = peakLists[index] else: self.cNoesy = None def destroy(self): BasePopup.destroy(self)
class SingleResonanceStatusPopup(BasePopup): def __init__(self, parent, message, nmrRes, optionList, title, urlFile=None): # Constructor doesn't do much except call body # The parent is self.parent (parent of the popup) self.singleResonanceStatus = None self.message = message self.optionList = optionList self.nmrRes = nmrRes if urlFile: self.help_url = joinPath(getHelpUrlDir(), urlFile + '.html') else: self.help_url = None # modal = true means that it won't continue unless this one returns value BasePopup.__init__(self, parent=parent, title=title, modal=True, transient=True) def body(self, master): master.grid_columnconfigure(0, weight=1) for i in range(3): master.grid_rowconfigure(i, weight=1) self.geometry('600x400') # Master is the owner widget (not self.parent) - parent of the widget here row = 0 label = Label(master, text="Residue %s-%d" % (self.nmrRes.molResidue.ccpCode, self.nmrRes.seqCode)) label.grid(row=row, column=0, sticky=Tkinter.W) row = row + 1 label = Label(master, text=self.message) label.grid(row=row, column=0, sticky=Tkinter.W) row = row + 1 self.menu = PulldownMenu(master, entries=self.optionList) self.menu.grid(row=row, column=0, sticky=Tkinter.EW) row = row + 1 texts = ['OK'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, column=0) def apply(self): self.singleResonanceStatus = self.optionList.index( self.menu.getSelected()) return True
class PopupTemplate(BasePopup): def __init__(self, parent, project=None, *args, **kw): self.project = project self.parent = parent self.objects = self.getObjects() self.object = None BasePopup.__init__(self, parent=parent, title='Popup Template', **kw) self.updateObjects() def body(self, mainFrame): mainFrame.grid_columnconfigure(1, weight=1, minsize=100) mainFrame.config(borderwidth=5, relief='solid') row = 0 label = Label(mainFrame, text="Frame (with sub-widgets):") label.grid(row=row, column=0, sticky=Tkinter.E) frame = Frame(mainFrame, relief='raised', border=2, background='#8080D0') # Frame expands East-West frame.grid(row=row, column=1, sticky=Tkinter.EW) # Last column expands => Widgets pusted to the West frame.grid_columnconfigure(3, weight=1) # Label is within the sub frame label = Label(frame, text='label ') label.grid(row=0, column=0, sticky=Tkinter.W) entry = Entry(frame, text='Entry', returnCallback=self.showWarning) entry.grid(row=0, column=1, sticky=Tkinter.W) self.check = CheckButton(frame, text='Checkbutton', selected=True, callback=self.updateObjects) self.check.grid(row=0, column=2, sticky=Tkinter.W) # stick a button to the East wall button = Button(frame, text='Button', command=self.pressButton) button.grid(row=0, column=3, sticky=Tkinter.E) row += 1 label = Label(mainFrame, text="Text:") label.grid(row=row, column=0, sticky=Tkinter.E) self.textWindow = Text(mainFrame, text='Initial Text\n', width=60, height=5) self.textWindow.grid(row=row, column=1, sticky=Tkinter.NSEW) row += 1 label = Label(mainFrame, text="CheckButtons:") label.grid(row=row, column=0, sticky=Tkinter.E) entries = ['Alpha','Beta','Gamma','Delta'] selected = entries[2:] self.checkButtons = CheckButtons(mainFrame, entries, selected=selected,select_callback=self.changedCheckButtons) self.checkButtons.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="PartitionedSelector:") label.grid(row=row, column=0, sticky=Tkinter.E) labels = ['Bool','Int','Float','String'] objects = [type(0),type(1),type(1.0),type('a')] selected = [type('a')] self.partitionedSelector= PartitionedSelector(mainFrame, labels=labels, objects=objects, colors = ['red','yellow','green','#000080'], callback=self.toggleSelector,selected=selected) self.partitionedSelector.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 label = Label(mainFrame, text="PulldownMenu") label.grid(row=row, column=0, sticky=Tkinter.E) entries = ['Frodo','Pipin','Merry','Sam','Bill','Gandalf','Strider','Gimli','Legolas'] self.pulldownMenu = PulldownMenu(mainFrame, callback=self.selectPulldown, entries=entries, selected_index=2, do_initial_callback=False) self.pulldownMenu.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="RadioButtons in a\nScrolledFrame.frame:") label.grid(row=row, column=0, sticky=Tkinter.EW) frame = ScrolledFrame(mainFrame, yscroll = False, doExtraConfig = True, width=100) frame.grid(row=row, column=1, sticky=Tkinter.EW) frame.grid_columnconfigure(0, weight=1) self.radioButtons = RadioButtons(frame.frame, entries=entries, select_callback=self.checkRadioButtons, selected_index=1, relief='groove') self.radioButtons.grid(row=0, column=0, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="LabelFrame with\nToggleLabels inside:") label.grid(row=row, column=0, sticky=Tkinter.E) labelFrame = LabelFrame(mainFrame, text='Frame Title') labelFrame.grid(row=row, column=1, sticky=Tkinter.NSEW) labelFrame.grid_rowconfigure(0, weight=1) labelFrame.grid_columnconfigure(3, weight=1) self.toggleLabel1 = ToggleLabel(labelFrame, text='ScrolledMatrix', callback=self.toggleFrame1) self.toggleLabel1.grid(row=0, column=0, sticky=Tkinter.W) self.toggleLabel1.arrowOn() self.toggleLabel2 = ToggleLabel(labelFrame, text='ScrolledGraph', callback=self.toggleFrame2) self.toggleLabel2.grid(row=0, column=1, sticky=Tkinter.W) self.toggleLabel3 = ToggleLabel(labelFrame, text='ScrolledCanvas', callback=self.toggleFrame3) self.toggleLabel3.grid(row=0, column=2, sticky=Tkinter.W) row += 1 mainFrame.grid_rowconfigure(row, weight=1) label = Label(mainFrame, text="changing/shrinking frames:") label.grid(row=row, column=0, sticky=Tkinter.E) self.toggleRow = row self.toggleFrame = Frame(mainFrame) self.toggleFrame.grid(row=row, column=1, sticky=Tkinter.NSEW) self.toggleFrame.grid_rowconfigure(0, weight=1) self.toggleFrame.grid_columnconfigure(0, weight=1) # option 1 self.intEntry = IntEntry(self, returnCallback = self.setNumber, width=8) self.multiWidget = MultiWidget(self, Entry, options=None, values=None, callback=self.setKeywords, minRows=3, maxRows=5) editWidgets = [None, None, self.intEntry, self.multiWidget] editGetCallbacks = [None, None, self.getNumber, self.getKeywords] editSetCallbacks = [None, None, self.setNumber, self.setKeywords] headingList = ['Name','Color','Number','Keywords'] self.scrolledMatrix = ScrolledMatrix(self.toggleFrame, headingList=headingList, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, callback=self.selectObject, multiSelect=False) self.scrolledMatrix.grid(row=0, column=0, sticky=Tkinter.NSEW) # option 2 self.scrolledGraph = ScrolledGraph(self.toggleFrame, width=400, height=300, symbolSize=5, symbols=['square','circle'], dataColors=['#000080','#800000'], lineWidths=[0,1] ) self.scrolledGraph.setZoom(1.3) dataSet1 = [[0,0],[1,1],[2,4],[3,9],[4,16],[5,25]] dataSet2 = [[0,0],[1,3],[2,6],[3,9],[4,12],[5,15]] self.scrolledGraph.update(dataSets=[dataSet1,dataSet2], xLabel = 'X axis label', yLabel = 'Y axis label', title = 'Main Title') self.scrolledGraph.draw() # option 3 self.scrolledCanvas = ScrolledCanvas(self.toggleFrame,relief = 'groove', borderwidth = 2, resizeCallback=None) canvas = self.scrolledCanvas.canvas font = 'Helvetica 10' box = canvas.create_rectangle(10,10,150,200, outline='grey', fill='grey90') line = canvas.create_line(0,0,200,200,fill='#800000', width=2) text = canvas.create_text(120,50, text='Text', font=font, fill='black') circle = canvas.create_oval(30,30,50,50,outline='#008000',fill='#404040',width=3) row += 1 label = Label(mainFrame, text="FloatEntry:") label.grid(row=row, column=0, sticky=Tkinter.E) self.floatEntry = FloatEntry(mainFrame, text=3.14159265, returnCallback=self.floatEntryReturn) self.floatEntry.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="Scale:") label.grid(row=row, column=0, sticky=Tkinter.E) self.scale = Scale(mainFrame, from_=10, to=90, value=50, orient=Tkinter.HORIZONTAL) self.scale.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="Value Ramp:") label.grid(row=row, column=0, sticky=Tkinter.E) self.valueRamp = ValueRamp(mainFrame, self.valueRampCallback, speed = 1.5, delay = 50) self.valueRamp.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(mainFrame, text="ButtonList:") label.grid(row=row, column=0, sticky=Tkinter.E) texts = ['Select File','Close','Quit'] commands = [self.selectFile, self.close, self.quit] bottomButtons = ButtonList(mainFrame, texts=texts, commands=commands, expands=True) bottomButtons.grid(row=row, column=1, sticky=Tkinter.EW) self.protocol('WM_DELETE_WINDOW', self.quit) def floatEntryReturn(self, event): value = self.floatEntry.get() self.textWindow.setText('%s\n' % value) def selectObject(self, object, row, col): self.object = object def getKeywords(self, object): if object : values = object.keywords self.multiWidget.set(values) def setKeywords(self, event): values = self.multiWidget.get() self.object.keywords = values self.updateObjects() def getNumber(self, object): if object : self.intEntry.set(object.quantity) def setNumber(self, event): value = self.intEntry.get() self.object.quantity = value self.updateObjects() def toggleFrame1(self, isHidden): if isHidden: self.scrolledMatrix.grid_forget() self.toggleFrame.grid_forget() else: self.scrolledGraph.grid_forget() self.scrolledCanvas.grid_forget() self.scrolledMatrix.grid(row=0, column=0, sticky=Tkinter.NSEW) self.toggleFrame.grid(row=self.toggleRow, column=1,sticky=Tkinter.NSEW) self.toggleLabel2.arrowOff() self.toggleLabel3.arrowOff() def toggleFrame2(self, isHidden): if isHidden: self.scrolledGraph.grid_forget() self.toggleFrame.grid_forget() else: self.scrolledMatrix.grid_forget() self.scrolledCanvas.grid_forget() self.scrolledGraph.grid(row=0, column=0, sticky=Tkinter.NSEW) self.toggleFrame.grid(row=self.toggleRow, column=1,sticky=Tkinter.NSEW) self.toggleLabel1.arrowOff() self.toggleLabel3.arrowOff() def toggleFrame3(self, isHidden): if isHidden: self.scrolledCanvas.grid_forget() self.toggleFrame.grid_forget() else: self.scrolledMatrix.grid_forget() self.scrolledGraph.grid_forget() self.scrolledCanvas.grid(row=0, column=0, sticky=Tkinter.NSEW) self.toggleFrame.grid(row=self.toggleRow, column=1,sticky=Tkinter.NSEW) self.toggleLabel1.arrowOff() self.toggleLabel2.arrowOff() def valueRampCallback(self, value): self.textWindow.setText('%s\n' % value) def checkRadioButtons(self, value): self.textWindow.setText('%s\n' % value) def selectPulldown(self, index, name): self.textWindow.setText('%d, %s\n' % (index, name)) def toggleSelector(self, value): self.textWindow.setText('%s\n' % value) def changedCheckButtons(self, values): self.textWindow.setText(','.join(values) + '\n') def getObjects(self): objects = [] objects.append( Fruit('Lemon', '#FFFF00',1,keywords=['Bitter','Tangy'] ) ) objects.append( Fruit('Orange', '#FF8000',4 ) ) objects.append( Fruit('Banana', '#FFF000',5 ) ) objects.append( Fruit('Pinapple','#FFD000',9 ) ) objects.append( Fruit('Kiwi', '#008000',12) ) objects.append( Fruit('Lime', '#00FF00',2 ) ) objects.append( Fruit('Apple', '#800000',5,keywords=['Crunchy'] ) ) objects.append( Fruit('Pear', '#408000',6 ) ) objects.append( Fruit('Peach', '#FFE0C0',2,keywords=['Sweet','Furry'] ) ) objects.append( Fruit('Plumb', '#800080',7 ) ) return objects def updateObjects(self, event=None): textMatrix = [] objectList = [] colorMatrix = [] for object in self.objects: datum = [] datum.append( object.name ) datum.append( None ) datum.append( object.quantity ) datum.append( ','.join(object.keywords) ) colors = [None, object.color, None, None] textMatrix.append(datum) objectList.append(object) colorMatrix.append(colors) if self.check.get(): self.scrolledMatrix.update(textMatrix=textMatrix, objectList=objectList) else: self.scrolledMatrix.update(textMatrix=textMatrix, objectList=objectList, colorMatrix=colorMatrix) def selectFile(self): fileSelectPopup = FileSelectPopup(self, title = 'Choose file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = fileSelectPopup.getFile() self.textWindow.setText('File Selected: %s\n' % fileName) def showWarning(self, eventObject): self.textWindow.setText('Text Entry Return Pressed\n') showWarning('Warning Title','Warning Message') return def pressButton(self): self.textWindow.setText('Button Pressed\n') if showYesNo('Title','Prompt: Clear text window?'): self.textWindow.clear() return def quit(self): BasePopup.destroy(self)
class HelpFrame(Frame): def __init__(self, parent, width=70, height=20, xscroll=False, yscroll=True, *args, **kw): apply(Frame.__init__, (self, parent) + args, kw) self.grid_columnconfigure(1, weight=1) row = 0 texts = ('back', 'forward', 'load') commands = (self.prevUrl, self.nextUrl, self.loadUrl) self.buttons = ButtonList(self, texts=texts, commands=commands) self.buttons.grid(row=row, column=0) self.url_entry = Entry(self, returnCallback=self.loadUrl) self.url_entry.grid(row=row, column=1, columnspan=2, sticky=Tkinter.EW) row = row + 1 frame = Frame(self) frame.grid(row=row, column=0, columnspan=3, sticky=Tkinter.W) self.createFindFrame(frame) row = row + 1 self.grid_rowconfigure(row, weight=1) self.help_text = ScrolledHtml(self, width=width, height=height, xscroll=xscroll, yscroll=yscroll, startUrlCallback=self.startOpenUrl, endUrlCallback=self.endOpenUrl, enterLinkCallback=self.setLinkLabel, leaveLinkCallback=self.setLinkLabel) self.help_text.grid(row=row, column=0, columnspan=3, sticky=Tkinter.NSEW) row = row + 1 self.link_label = Label(self) self.link_label.grid(row=row, column=0, columnspan=2, sticky=Tkinter.W) button = memops.gui.Util.createDismissButton(self, dismiss_cmd=self.close) button.grid(row=row, column=2) self.urls = [] self.current = -1 self.updateUrlList = True self.setButtonState() def close(self): if (self.popup): if (self.popup.modal): self.popup.do_grab() popup = self.parent while (not hasattr(popup, 'top')): popup = popup.parent popup.close() def createFindFrame(self, master): frame = Frame(master) frame.grid(row=0, column=0, sticky=Tkinter.W) arrow = ToggleArrow(frame, callback=self.toggleFindFrame) arrow.grid(row=0, column=0) button = Button(frame, text='find:', command=self.findPhrase) button.grid(row=0, column=1) self.find_entry = Entry(frame, width=20, returnCallback=self.findPhrase) self.find_entry.grid(row=0, column=2) self.find_frame = frame = Frame(master) entries = ('search forwards', 'search backwards') self.direction_buttons = PulldownMenu(frame, entries=entries) self.direction_buttons.grid(row=0, column=0, sticky=Tkinter.W, padx=5) self.forwards_entries = entries = ('wrap search', 'stop at end') self.backwards_entries = ('wrap search', 'stop at beginning') self.wrap_buttons = PulldownMenu(frame, entries=entries) self.wrap_buttons.grid(row=0, column=1, sticky=Tkinter.W, padx=5) self.direction_buttons.callback = self.setWrapText entries = ('case insensitive', 'case sensitive') self.case_buttons = PulldownMenu(frame, entries=entries) self.case_buttons.grid(row=0, column=2, sticky=Tkinter.W, padx=5) entries = ('literal search', 'regex search') self.pattern_buttons = PulldownMenu(frame, entries=entries) self.pattern_buttons.grid(row=0, column=3, sticky=Tkinter.W, padx=5) self.countVar = Tkinter.IntVar() def setWrapText(self, entry_ind, entry): if (entry_ind == 0): entries = self.forwards_entries else: entries = self.backwards_entries self.wrap_buttons.replace( entries, selected_index=self.wrap_buttons.getSelectedIndex()) def findPhrase(self, *extra): phrase = self.find_entry.get() if (not phrase): showError('No find phrase', 'Enter phrase in entry box.') return if (self.direction_buttons.getSelectedIndex() == 0): forwards = 1 backwards = 0 else: forwards = 0 backwards = 1 if (self.case_buttons.getSelectedIndex() == 0): nocase = 1 else: nocase = 0 if (self.pattern_buttons.getSelectedIndex() == 0): exact = 1 regexp = 0 else: exact = 0 regexp = 1 start = self.help_text.tag_nextrange(Tkinter.SEL, '1.0') if (start): start = start[0] if (forwards): start = '%s+1c' % start else: start = '%s-1c' % start else: start = Tkinter.CURRENT if (self.wrap_buttons.getSelectedIndex() == 0): match = self.help_text.search(phrase, start, count=self.countVar, forwards=forwards, backwards=backwards, nocase=nocase, exact=exact, regexp=regexp) elif (forwards): match = self.help_text.search(phrase, start, count=self.countVar, forwards=forwards, backwards=backwards, nocase=nocase, exact=exact, regexp=regexp, stopindex=Tkinter.END) else: match = self.help_text.search(phrase, start, count=self.countVar, forwards=forwards, backwards=backwards, nocase=nocase, exact=exact, regexp=regexp, stopindex='1.0') if (match): self.help_text.see(match) self.help_text.setSelection( match, '%s+%dc' % (match, self.countVar.get())) self.help_text.tag_config(Tkinter.SEL, background='gray70') else: showInfo('No match', 'No match found for phrase.') def toggleFindFrame(self, isClosed): if (isClosed): self.find_frame.grid_forget() else: self.find_frame.grid(row=1, column=0, sticky=Tkinter.W) def setButtonState(self): n = len(self.urls) if ((n >= 2) and (self.current > 0)): state = Tkinter.NORMAL else: state = Tkinter.DISABLED self.buttons.buttons[0].config(state=state) if ((n >= 2) and (self.current < (n - 1))): state = Tkinter.NORMAL else: state = Tkinter.DISABLED self.buttons.buttons[1].config(state=state) def setLinkLabel(self, url=''): self.link_label.set(url) def loadUrl(self, *extra): url = self.url_entry.get() if (url): if (url.find(':') == -1): if (url[:2] != '//'): url = '//' + url url = 'http:' + url self.showUrl(url, forceLoad=True) def newUrl(self, url): self.current = self.current + 1 self.urls[self.current:] = [[url, 0.0]] self.setButtonState() #print 'newUrl', self.current, self.urls def prevUrl(self): if (self.current > 0): # True if called via button (url, offset) = self.urls[self.current - 1] self.updateUrlList = False self.showUrl(url, offset=offset, allowModifyPath=False) self.updateUrlList = True self.current = self.current - 1 self.setButtonState() #print 'prevUrl', self.current, self.urls def nextUrl(self): if (self.current < (len(self.urls) - 1)): # True if called via button (url, offset) = self.urls[self.current + 1] self.updateUrlList = False self.showUrl(url, offset=offset, allowModifyPath=False) self.updateUrlList = True self.current = self.current + 1 self.setButtonState() #print 'nextUrl', self.current, self.urls def showText(self, message, popup=None): self.popup = popup if (popup): self.parent.modal = popup.modal self.help_text.setState(Tkinter.NORMAL) # so that can add text self.help_text.clear() # clear existing text self.help_text.append(message) self.help_text.setState(Tkinter.DISABLED) # make text read-only self.open() def startOpenUrl(self, yview): if (self.urls): self.urls[self.current][1] = yview[0] def endOpenUrl(self, url): #print 'endOpenUrl', url, self.updateUrlList self.url_entry.set(url) if (self.updateUrlList): self.newUrl(url) self.setLinkLabel() self.open() def showUrl(self, url, offset=None, forceLoad=False, allowModifyPath=True, popup=None): self.popup = popup if (popup): self.parent.modal = popup.modal self.help_text.openUrl(url, forceLoad=forceLoad, allowModifyPath=allowModifyPath) if (offset is not None): self.help_text.yview(Tkinter.MOVETO, str(offset))
class CreateShiftListPopup(BasePopup): help_url = joinPath(getHelpUrlDir(), 'CreateShiftList.html') def __init__(self, parent, project): self.project = project self.peakLists = [] BasePopup.__init__(self, parent=parent, title="Project '%s': " % project.name + 'Create shift list from peak lists', modal=False, transient=True) def body(self, master): # # Peaklist setup # self.peakListDict = {} for experiment in self.project.currentNmrProject.sortedExperiments(): for dataSource in experiment.sortedDataSources(): for peakList in dataSource.sortedPeakLists(): peakListLabel = "%s:%s:%d:%s" % ( experiment.name, dataSource.name, peakList.serial, peakList.name) self.peakListDict[peakListLabel] = peakList peakListLabels = self.peakListDict.keys() peakListLabels.sort() # # chemical shift list setup # self.shiftListDict = {} self.shiftListDict['None'] = None for shiftList in self.project.currentNmrProject.findAllMeasurementLists( className='ShiftList'): shiftListLabel = "%d:%s" % (shiftList.serial, shiftList.name) self.shiftListDict[shiftListLabel] = shiftList shiftListLabels = self.shiftListDict.keys() shiftListLabels.sort() row = 0 label = Label(master, text="Generation of chemical shift list") label.grid(row=row, column=0, columnspan=2, sticky=Tkinter.W) row += 1 label = Label(master, text="Peak lists:") label.grid(row=row, column=0, sticky=Tkinter.W) self.peakListBox = ScrolledListbox(master, width=50, height=5, selectmode=Tkinter.MULTIPLE, initial_list=peakListLabels) self.peakListBox.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 label = Label(master, text="Use existing shift list:") label.grid(row=row, column=0, sticky=Tkinter.W) self.shiftListSelect = PulldownMenu(master, entries=shiftListLabels) self.shiftListSelect.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 label = Label(master, text="Use multiple assignments:") label.grid(row=row, column=0, sticky=Tkinter.W) self.useAllContribs = CheckButton(master) self.useAllContribs.grid(row=row, column=1, sticky=Tkinter.W) # # Setup the default shift error per nucleus # self.defaultShiftError = {} for (nucl, text, defValue) in [('1H', 'proton', '0.002'), ('13C', 'carbon', '0.1'), ('15N', 'nitrogen', '0.1')]: row += 1 label = Label(master, text="Default %s shift error:" % text) label.grid(row=row, column=0, sticky=Tkinter.W) self.defaultShiftError[nucl] = Entry(master, text=defValue) self.defaultShiftError[nucl].grid(row=row, column=1, sticky=Tkinter.W) row += 1 texts = ['Create shift list'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, columnspan=2, column=0) def apply(self): selectedPeakLists = self.peakListBox.getSelectedItems() for peakListLabel in selectedPeakLists: self.peakLists.append(self.peakListDict[peakListLabel]) chemShiftList = self.shiftListDict[self.shiftListSelect.getSelected()] if not chemShiftList: chemShiftListName = askString("Enter chemical shift list name", "New chemical shift list name", '', self) else: chemShiftListName = chemShiftList.name useAllContribs = self.useAllContribs.isSelected() defaultShiftError = {} for nucl in self.defaultShiftError.keys(): defaultShiftError[nucl] = returnFloat( self.defaultShiftError[nucl].get()) listCreated = createChemShifts(self.peakLists, guiParent=self.parent, multiDialog=self.parent.multiDialog, shiftList=chemShiftList, useAllContribs=useAllContribs, defaultShiftError=defaultShiftError, shiftListName=chemShiftListName) if listCreated: showInfo( "Success", "Succesfully created a chemical shift list from peaklist(s)") return True
class WindowFunctionSelect(BasePopup): help_url = joinPath(getHelpUrlDir(), 'WindowFunctionSelect.html') def __init__(self, parent, format, dim, getValue): # # General setup # self.maxArgs = 4 self.nmrPipe = 'nmrPipe' self.azara = 'azara' self.format = format self.freqDataDim = parent.freqDataDims[format][dim] self.expDimRef = parent.expDimRefs[dim] # # Window function settings (different per program) # self.windowFunctions = {} specWidth = self.freqDataDim.spectralWidthOrig # TODO: these for azara still have to change a bit... self.windowFunctions[self.azara] = [ ['sine', 'sinebell', [['Angle (deg)', 0, 'deg']]], ['sine^2', 'sinebell2', [['Angle (deg)', 0, 'deg']]], ['exponential (fixed)', 'decay', [['End value', 0.5, 'end']]], [ 'exponential', 'decay_sw', [['Line broadening (Hz)', 10, 'lb'], ['Spectral width (Hz)', specWidth, 'sw']] ], [ 'gaussian (fixed)', 'gaussian', [['Total points fraction for max', 0.25, 'frac'], ['End value', 1, 'end']] ], [ 'gaussian', 'gaussian_sw', [['Line broadening (Hz)', 10, 'lb'], ['Sharpening factor', 0.7, 'shrp'], ['Spectral width (Hz)', specWidth, 'sw']] ], [ 'inverse cosine', 'inv_cosine', [['Frequency (Hz)', 0, 'freq'], ['Spectral width (Hz)', specWidth, 'sw']] ] ] self.windowFunctions[self.nmrPipe] = [ [ 'sine', 'SP', [['Start sine at (pi)', 0, 'off'], ['End sine at (pi)', 1, 'end'], ['Sine to power', 1, 'pow']] ], ['exponential', 'EM', [['Line broadening (Hz)', 10, 'lb']]], [ 'lorentz-gauss', 'GM', [['Inverse exp width (Hz)', 0, 'g1'], ['Gaussian width (Hz)', 0, 'g2'], ['Center (0-1)', 0, 'g3']] ], [ 'gaussian', 'GMB', [['Exponential term', 0, 'lb'], ['Gaussian term', 0, 'gb']] ], [ 'trapezoid', 'TM', [['Ramp length left', 0, 't1'], ['Ramp length right', 0, 't2']] ], [ 'triangle', 'TRI', [['Point loc of apex', 0, 'loc'], ['Left edge height', 0, 'lHi'], ['Right edge height', 0, 'rHi']] ] ] # # Make list of names for pulldown menu # self.windowFuncList = [] for (winFunc, winFuncAppl, winFuncArgs) in self.windowFunctions[format]: self.windowFuncList.append(winFunc) # # Get the right window function from appldata (if there) # self.windowFunctionKeyword = 'windowFunction' self.winFuncIndex = self.getWindowFunctionIndex() # # Set defaults depending on nucleus type if no window function set # if self.winFuncIndex == -1: if format == self.nmrPipe: self.winFuncIndex = 0 if self.expDimRef.isotopeCodes[0] == '1H': # use SP '-off 0.3333 -pow 2.0' self.windowFunctions[self.nmrPipe][ self.winFuncIndex][2][0][1] = 0.3333 self.windowFunctions[self.nmrPipe][ self.winFuncIndex][2][2][1] = 2.0 else: # for non-H, use SP '-off 0.5 -pow 2.0' self.windowFunctions[self.nmrPipe][ self.winFuncIndex][2][0][1] = 0.5 self.windowFunctions[self.nmrPipe][ self.winFuncIndex][2][2][1] = 2.0 elif format == self.azara: self.winFuncIndex = 1 if self.expDimRef.isotopeCodes[0] == '1H': # use sinebell2 60 self.windowFunctions[self.azara][ self.winFuncIndex][2][0][1] = 60 else: # for non-H, use sinebell2 90 self.windowFunctions[self.azara][ self.winFuncIndex][2][0][1] = 90 # Get actual values for arguments from appldata if they exists! self.updateWindowFunctions() # Also using this to return the current window function 'string value' if not getValue: # modal = true means that it won't continue unless this one returns value BasePopup.__init__( self, parent=parent, title='Select window function', modal=False, transient=True, ) def body(self, master): # Master is the owner widget (not self.parent) - parent of the widget here # # Popup window # self.entries = [] self.labels = [] value = 0 row = 0 label = Label(master, text="Window function:") label.grid(row=row, column=0, sticky=Tkinter.EW) self.menuRow = row self.menu = PulldownMenu(master, entries=self.windowFuncList, selected_index=self.winFuncIndex) self.menu.grid(row=row, column=1, sticky=Tkinter.W, ipadx=20) self.menulabel = Label( master, text="(" + self.windowFunctions[self.format][self.winFuncIndex][1] + ")") self.menulabel.grid(row=row, column=2, sticky=Tkinter.E) # # Setup arguments - make room for four # for argIndex in range(0, self.maxArgs): row = row + 1 try: argRef = self.windowFunctions[self.format][ self.winFuncIndex][2][argIndex] argName = argRef[0] argValue = argRef[1] except: argName = None argValue = None self.labels.append(Label(master, text="%s" % argName)) self.labels[-1].grid(row=row, column=0, sticky=Tkinter.EW) self.entries.append(Entry(master, text=str(argValue))) self.entries[-1].grid(row=row, column=1, columnspan=2, sticky=Tkinter.W) if not argName: self.labels[-1].grid_forget() self.entries[-1].grid_forget() # # Add callback to menu after setup # self.menu.callback = self.updateWindow row = row + 1 texts = ['OK'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, column=0, columnspan=3) def getApplDataAndReturnString(self): keyword = self.windowFunctionKeyword returnString = self.windowFunctions[self.format][self.winFuncIndex][0] winFuncName = self.windowFunctions[self.format][self.winFuncIndex][1] for (argName, argValue, argShort ) in self.windowFunctions[self.format][self.winFuncIndex][2]: applData = self.freqDataDim.findFirstApplicationData( application=self.format, keyword=keyword + winFuncName + argShort) returnString += ' ' + argShort if not applData: returnString += ' ' + str(argValue) else: returnString += ' ' + str(applData.value) return returnString def updateWindowFunctions(self): keyword = self.windowFunctionKeyword winFuncName = self.windowFunctions[self.format][self.winFuncIndex][1] # # Update windowfunction parameters # for i in range( 0, len(self.windowFunctions[self.format][self.winFuncIndex][2])): (argName, argValue, argShort ) = self.windowFunctions[self.format][self.winFuncIndex][2][i] applData = self.freqDataDim.findFirstApplicationData( application=self.format, keyword=keyword + winFuncName + argShort) if applData: self.windowFunctions[self.format][ self.winFuncIndex][2][i][1] = str(applData.value) def setApplData(self): keyword = self.windowFunctionKeyword winFuncName = self.windowFunctions[self.format][self.winFuncIndex][1] # # Set windowfunction # applData = self.freqDataDim.findFirstApplicationData( application=self.format, keyword=keyword) if not applData: applData = createAppData(self.freqDataDim, application=self.format, keyword=keyword, value=winFuncName) else: applData.value = winFuncName # # Set windowfunction parameters # for (argName, argValue, argShort ) in self.windowFunctions[self.format][self.winFuncIndex][2]: applData = self.freqDataDim.findFirstApplicationData( application=self.format, keyword=keyword + winFuncName + argShort) if not applData: applData = createAppData(self.freqDataDim, application=self.format, keyword=keyword + winFuncName + argShort, value=str(argValue)) else: applData.value = str(argValue) def getWindowFunctionIndex(self): keyword = self.windowFunctionKeyword applData = self.freqDataDim.findFirstApplicationData( application=self.format, keyword=keyword) if applData: origWinFuncAppl = applData.value for i in range(0, len(self.windowFunctions[self.format])): (winFunc, winFuncAppl, winFuncArgs) = self.windowFunctions[self.format][i] if winFuncAppl == origWinFuncAppl: return i return -1 def updateWindow(self, *args): # # First do a value update of the current stuff? # # # Reset arguments # row = self.menuRow self.winFuncIndex = self.menu.getSelectedIndex() self.menulabel.set( "(" + self.windowFunctions[self.format][self.winFuncIndex][1] + ")") for argIndex in range(0, self.maxArgs): row = row + 1 try: argRef = self.windowFunctions[self.format][ self.winFuncIndex][2][argIndex] argName = argRef[0] argValue = argRef[1] except: argName = None argValue = None self.labels[argIndex].set(argName) self.labels[argIndex].grid(row=row, column=0, sticky=Tkinter.W) self.entries[argIndex].set(str(argValue)) self.entries[argIndex].grid(row=row, column=1, columnspan=2, sticky=Tkinter.W) if not argName: self.entries[argIndex].grid_forget() self.labels[argIndex].grid_forget() def setWindowFunctionsValues(self): self.winFuncIndex for argIndex in range( 0, len(self.windowFunctions[self.format][self.winFuncIndex][2])): argValue = returnFloat(self.entries[argIndex].get()) self.windowFunctions[self.format][ self.winFuncIndex][2][argIndex][1] = argValue def apply(self): self.winFuncIndex = self.menu.getSelectedIndex() self.setWindowFunctionsValues() self.setApplData() return True
class SelectionListPopup(TemporaryBasePopup): def __init__(self, parent, selectionList, title = 'Select', text = 'Select', topText = None, dismissText = None, selected = None, selectionDict = None, urlFile = None, dismissButton = True, modal = False): self.selectionList = selectionList self.selectionDict = selectionDict self.text = text self.dismissButton = dismissButton if dismissButton: if dismissText: self.dismissText = dismissText else: self.dismissText = 'dismiss' self.topText = topText self.isSelected = None if not selected: self.selectedIndex = 0 else: self.selectedIndex = self.selectionList.index(selected) if urlFile: self.help_url = joinPath(getHelpUrlDir(),urlFile + '.html') else: self.help_url = None TemporaryBasePopup.__init__(self,parent = parent, title = title, modal = modal, transient=True) def body(self, master): # # Popup window # row = 0 if self.topText: label = Label(master, text= self.topText) label.grid(row=row, column=0, columnspan = 2, sticky=Tkinter.EW) row = row + 1 label = Label(master, text= self.text) label.grid(row=row, column=0, sticky=Tkinter.EW) self.menu = PulldownMenu(master, entries = self.selectionList, selected_index = self.selectedIndex) self.menu.grid(row=row, column=1, sticky=Tkinter.E, ipadx = 20) row = row + 1 texts = [ 'OK' ] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here if self.dismissButton: buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text = self.dismissText, help_url=self.help_url) else: buttons = createHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, column=0, columnspan = 3) def apply(self): self.isSelected = self.menu.getSelected() if self.selectionDict: self.selection = self.selectionDict[self.isSelected] else: self.selection = self.isSelected return True
class LinkResonancesPopup(TemporaryBasePopup): help_url = joinPath(getHelpUrlDir(), 'LinkResonances.html') def __init__(self, parent, formatNamesList, formatNamesDict, title='Link resonances setup'): self.guiParent = parent self.formatNamesList = formatNamesList self.formatNamesDict = formatNamesDict self.status = False TemporaryBasePopup.__init__(self, parent=parent, title=title, modal=False, transient=False) def body(self, master): row = 0 label = Label(master, text='File format reference:') label.grid(row=row, column=0, sticky=Tkinter.E) self.menu = PulldownMenu(master, entries=self.formatNamesList) self.menu.grid(row=row, column=1, sticky=Tkinter.E, ipadx=20) row = row + 1 label = Label(master, text='Try to link unrecognized atom names') label.grid(row=row, column=0, sticky=Tkinter.E) self.linkRes = CheckButton(master, selected=True) self.linkRes.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Try IUPAC names (as backup)') label.grid(row=row, column=0, sticky=Tkinter.E) self.iupacNames = CheckButton(master) self.iupacNames.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Use ambiguous name information') label.grid(row=row, column=0, sticky=Tkinter.E) self.useAmb = CheckButton(master) self.useAmb.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Complete stereospecific assignment') label.grid(row=row, column=0, sticky=Tkinter.E) self.allStereo = CheckButton(master) self.allStereo.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Force shift merges') label.grid(row=row, column=0, sticky=Tkinter.E) self.shiftMerge = CheckButton(master) self.shiftMerge.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Status other atom for all single prochiral atoms') label.grid(row=row, column=0, sticky=Tkinter.E) self.allSingleProchiral = PulldownMenu( master, entries=['Unknown', 'Same information', 'Always ignore']) self.allSingleProchiral.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label( master, text='Status other atom for all possibly equivalent single atoms') label.grid(row=row, column=0, sticky=Tkinter.E) self.allSinglePossEquiv = PulldownMenu( master, entries=['Unknown', 'Always equivalent', 'Always ignore']) self.allSinglePossEquiv.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label( master, text= 'Automatically connect ambiguous resonances to stereospecific ones' ) label.grid(row=row, column=0, sticky=Tkinter.E) self.connStereo = CheckButton(master) self.connStereo.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Use minimal number of popups') label.grid(row=row, column=0, sticky=Tkinter.E) self.minimalPopups = CheckButton(master) self.minimalPopups.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label(master, text='Verbose output') label.grid(row=row, column=0, sticky=Tkinter.E) self.verbose = CheckButton(master, selected=True) self.verbose.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 label = Label( master, text= 'Warning: it is recommended you save your project first,\nin case linkResonances is interrupted (this might corrupt the data).', fg='red') label.grid(row=row, column=0, columnspan=2, ipady=15, sticky=Tkinter.EW) row = row + 1 texts = ['Link resonances to atoms'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, column=0, columnspan=3) def apply(self): self.assignFormat = self.formatNamesDict[self.menu.getSelected()] self.globalStereoAssign = self.allStereo.isSelected() self.useIupacMatching = self.iupacNames.isSelected() self.useLinkResonancePopup = self.linkRes.isSelected() self.minimalPrompts = self.minimalPopups.isSelected() self.verbose = self.verbose.isSelected() self.forceShiftMerge = self.shiftMerge.isSelected() self.useAmbiguity = self.useAmb.isSelected() self.autoConnectStereo = self.connStereo.isSelected() self.setSingleProchiral = self.allSingleProchiral.getSelected() self.setSinglePossEquiv = self.allSinglePossEquiv.getSelected() self.status = True return True
class GroupChemShiftsPopup(BasePopup): help_url = joinPath(getHelpUrlDir(), 'GroupChemShifts.html') def __init__(self, parent, project): # # Info for writing file... # self.groupText = {} # # Set up molSystem information # self.project = project self.molSysList = list(project.sortedMolSystems()) self.molSystems = None self.molSysLabelList = [] self.molSysLabelDict = {} self.molSysRelationDict = {} molSysLabel = 'All molSystems' if self.setChainLabels(molSysLabel, self.molSysList): self.molSysLabelList.append(molSysLabel) self.molSysLabelDict[molSysLabel] = self.molSysList for molSys in self.molSysList: molSysLabel = '%s' % molSys.code if self.setChainLabels(molSysLabel, [molSys]): self.molSysLabelList.append(molSysLabel) self.molSysLabelDict[molSysLabel] = [molSys] if not self.molSysLabelList: showWarning('Warning', 'No chemical shift lists available! Exiting...') return # # Some initializing... # self.chains = None self.shiftList = None self.shiftListLabel = None self.results = None # modal = true means that it won't continue unless this one returns value BasePopup.__init__(self, parent=parent, title="Project '%s': " % project.name + 'Group chemical shift values', modal=False, transient=True) def setChainLabels(self, molSysLabel, molSysList): # # Set up chain information # chainLabelList = [] chainLabelDict = {} chainLabelShiftListDict = {} self.molSysRelationDict[molSysLabel] = [ chainLabelList, chainLabelDict, chainLabelShiftListDict ] chains = [] for molSys in molSysList: chains.extend(list(molSys.sortedChains())) chainLabel = 'All chains' if self.setShiftListLabels(chainLabel, chains, self.molSysRelationDict[molSysLabel][2]): self.molSysRelationDict[molSysLabel][0].append(chainLabel) self.molSysRelationDict[molSysLabel][1][chainLabel] = chains for chain in chains: chainLabel = "'%s' (mol. '%s')" % (chain.code, chain.molecule.name) if self.setShiftListLabels( chainLabel, [chain], self.molSysRelationDict[molSysLabel][2]): self.molSysRelationDict[molSysLabel][0].append(chainLabel) self.molSysRelationDict[molSysLabel][1][chainLabel] = [chain] return self.molSysRelationDict[molSysLabel][0] def setShiftListLabels(self, chainLabel, chains, chainLabelShiftListDict): # # Set up chemical shift list information (slooooww so done at start) # shiftLists = [] shiftListCount = {} resonanceTracker = [] shiftListLabels = [] shiftListLabelsDict = {} atomCount = 0 for chain in chains: for residue in chain.residues: for atom in residue.atoms: atomCount += 1 if atom.atomSet: for resonanceSet in atom.atomSet.resonanceSets: for resonance in resonanceSet.resonances: if resonance in resonanceTracker: continue resonanceTracker.append(resonance) for shift in resonance.shifts: if shift.parentList not in shiftLists: shiftLists.append(shift.parentList) shiftListCount[shift.parentList] = 0 shiftListCount[shift.parentList] += 1 for shiftList in shiftLists: percentage = (shiftListCount[shift.parentList] * 100.0) / atomCount shiftListLabel = "%d:%s (%.1f%%)" % (shiftList.serial, shiftList.name, percentage) shiftListLabels.append(shiftListLabel) shiftListLabelsDict[shiftListLabel] = shiftList chainLabelShiftListDict[chainLabel] = [ shiftListLabels, shiftListLabelsDict ] return shiftListLabels def body(self, master): # # Setup header # row = 0 self.columnSpan = 3 label = Label( master, text= 'Select molecular system, chains and chemical shift list to be analyzed:' ) label.grid(row=row, column=0, columnspan=self.columnSpan, sticky=Tkinter.EW) row += 1 self.molSysSelect = PulldownMenu(master, entries=self.molSysLabelList, callback=self.setupChains) self.molSysSelect.grid(row=row, column=0, sticky=Tkinter.W) self.chainSelect = PulldownMenu(master, entries=self.chainLabelList, callback=self.setupShiftList) self.chainSelect.grid(row=row, column=1, sticky=Tkinter.W) self.shiftListSelect = PulldownMenu(master, entries=self.shiftListLabels, callback=self.setupPercentageFrame, do_initial_callback=False) self.shiftListSelect.grid(row=row, column=2, sticky=Tkinter.W) row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.EW) row += 1 master.grid_rowconfigure(row, weight=1) for i in range(self.columnSpan): master.grid_columnconfigure(i, weight=1) self.percentageFrame = ScrolledFrame(master, height=180, doExtraConfig=False) self.percentageFrame.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.NSEW) self.percentageFrameRow = row self.percentageFrameMaster = master row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.EW) row += 1 master.grid_rowconfigure(row, weight=1) self.resultsFrame = ScrolledFrame(master, height=180, doExtraConfig=False) self.resultsFrame.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.NSEW) self.resultsFrameRow = row self.resultsFrameMaster = master row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.EW) row += 1 texts = ['Recalculate', 'Write to file'] commands = [ self.recalc, self.writeFile ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Exit', help_url=self.help_url) buttons.grid(row=row, columnspan=self.columnSpan, sticky=Tkinter.EW) self.shiftListSelect.callback(0, self.shiftListLabels[0]) def setupChains(self, listIndex, molSysLabel): molSystems = self.molSysLabelDict[molSysLabel] if self.molSystems == molSystems: return self.molSystems = molSystems self.chainLabelList = self.molSysRelationDict[molSysLabel][0] self.chainLabelDict = self.molSysRelationDict[molSysLabel][1] self.chainLabelShiftListDict = self.molSysRelationDict[molSysLabel][2] if hasattr(self, 'chainSelect'): self.chains = None self.chainSelect.callback(0, self.chainLabelList[0]) def setupShiftList(self, listIndex, chainLabel): chains = self.chainLabelDict[chainLabel] if self.chains == chains: return self.chains = chains # # Reset the pulldown menu # if hasattr(self, 'chainSelect'): self.chainSelect.replace(self.chainLabelList) # # Set up chemical shift lists # self.shiftListLabels = self.chainLabelShiftListDict[chainLabel][0] self.shiftListLabelsDict = self.chainLabelShiftListDict[chainLabel][1] if hasattr(self, 'percentageFrame'): self.shiftList = None self.shiftListLabel = None self.setupPercentageFrame(0, self.shiftListLabels[0]) def setupPercentageFrame(self, listIndex, shiftListLabel): if self.shiftListLabel == shiftListLabel: return self.shiftList = self.shiftListLabelsDict[shiftListLabel] self.shiftListLabel = shiftListLabel # # Reset chemical shift groups... # self.shiftGroupsList = [] for i in range(1, 10): shiftGroupLabel = 'Group_%s' % i self.shiftGroupsList.append(shiftGroupLabel) # # Reset the pulldown menu # if hasattr(self, 'shiftListSelect'): if hasattr(self.shiftListSelect, 'entries') and tuple(self.shiftListLabels) != tuple( self.shiftListSelect.entries): # HACK # otherwise can get infinite recursion but even with above could # if no self.shiftListLabels because of "None" entry in PulldownMenu self.shiftListSelect.replace(self.shiftListLabels) self.shiftListSelect.setSelected(shiftListLabel) # # Reset frame... # self.percentageFrame.destroy() self.percentageFrame = ScrolledFrame(self.percentageFrameMaster, height=180, doExtraConfig=False) self.percentageFrame.grid(row=self.percentageFrameRow, columnspan=self.columnSpan, sticky=Tkinter.NSEW) # # Recalculate results # self.results = makeChemShiftSelections(self.parent, self.chains, self.shiftList) resultKeys = self.results.keys() resultKeys.sort() # # Set up the information # frameRow = 0 frame = self.percentageFrame.frame self.shiftGroupObjects = {} for resultKey in resultKeys: allAtoms = self.results[resultKey][0] shiftAtoms = self.results[resultKey][1] percentage = shiftAtoms * 100.0 / allAtoms label = Label(frame, text=resultKey) label.grid(row=frameRow, column=0, sticky=Tkinter.W) label = Label(frame, text="%.1f%%" % percentage) label.grid(row=frameRow, column=1, sticky=Tkinter.W) label = Label(frame, text="(%d/%d)" % (shiftAtoms, allAtoms)) label.grid(row=frameRow, column=2, sticky=Tkinter.W) self.shiftGroupObjects[resultKey] = PulldownMenu( frame, entries=self.shiftGroupsList) self.shiftGroupObjects[resultKey].grid(row=frameRow, column=3, sticky=Tkinter.E) frameRow += 1 return True def recalc(self): groups = {} groupsInfo = {} for resultKey in self.shiftGroupObjects: group = self.shiftGroupObjects[resultKey].getSelected() if not groups.has_key(group): groups[group] = [] groupsInfo[group] = [0, 0] (allAtoms, shiftAtoms) = self.results[resultKey] groupsInfo[group][0] += allAtoms groupsInfo[group][1] += shiftAtoms groups[group].append(resultKey) # # Reset frame... # self.resultsFrame.destroy() self.resultsFrame = ScrolledFrame(self.resultsFrameMaster, height=180, doExtraConfig=False) self.resultsFrame.grid(row=self.resultsFrameRow, columnspan=self.columnSpan, sticky=Tkinter.NSEW) # # Set info in lower frame # frameRow = 0 frame = self.resultsFrame.frame groupKeys = groups.keys() groupKeys.sort() self.groupText = {} for group in groupKeys: percentage = groupsInfo[group][1] * 100.0 / groupsInfo[group][0] label = Label(frame, text=group) label.grid(row=frameRow, column=0, sticky=Tkinter.W) label = Label(frame, text=groups[group][0]) label.grid(row=frameRow, column=1, sticky=Tkinter.W) label = Label(frame, text="%.1f%%" % percentage) label.grid(row=frameRow, column=2, sticky=Tkinter.W) label = Label(frame, text="(%d/%d)" % (groupsInfo[group][1], groupsInfo[group][0])) label.grid(row=frameRow, column=3, sticky=Tkinter.W) self.groupText[group] = "%-10s %-20s %8.1f%% (%d/%d)%s" % ( group, groups[group][0], percentage, groupsInfo[group][1], groupsInfo[group][0], newline) frameRow += 1 for otherResultKey in groups[group][1:]: label = Label(frame, text=otherResultKey) label.grid(row=frameRow, column=2, sticky=Tkinter.W) self.groupText[group] += "%-10s %-20s%s" % ('', otherResultKey, newline) frameRow += 1 return True def writeFile(self): filePopup = FormatFilePopup(self, component='text') if filePopup.fileSelected: groupKeys = self.groupText.keys() groupKeys.sort() fout = open(filePopup.file, 'w') fout.write("Project: %s" % self.project.name + newline) fout.write("Molsystems: %s" % self.molSysSelect.getSelected() + newline) fout.write("Chains: %s" % self.chainSelect.getSelected() + newline) fout.write("Shiftlist: %s" % self.shiftListSelect.getSelected() + newline * 2) for group in groupKeys: fout.write(self.groupText[group]) print "Wrote file %s..." % filePopup.file def apply(self): return True
class TableExportPopup(BasePopup): def __init__(self, parent, headings, entries, title='', file='', *args, **kw): headings = [heading.replace('\n', ' ') for heading in headings] if (headings[0].lower() == 'number'): self.addNumber = False else: self.addNumber = True headings.insert(0, 'Number') if (not title): title = 'Export data' self.exportSelection = parent.tableExportSelection self.headings = headings self.entries = entries self.file = file kw['title'] = title kw['transient'] = True kw['modal'] = True BasePopup.__init__(self, parent=parent, *args, **kw) def body(self, master): master.grid_columnconfigure(2, weight=1) row = 0 label = Label(master, text='Data to export:') label.grid(row=row, column=0, columnspan=3, sticky=Tkinter.W) self.check_buttons = {} i = 0 for heading in self.headings: row = row + 1 isSelected = self.exportSelection.get(row, True) self.check_buttons[i] = c = CheckButton( master, selected=isSelected, callback=self.toggleCheckButton) c.grid(row=row, column=1) label = Label(master, text=heading) label.grid(row=row, column=2, sticky=Tkinter.W) i += 1 row = row + 1 button = Button(master, text='File:', command=self.findFile) button.grid(row=row, column=0, sticky=Tkinter.W) self.file_entry = Entry(master, text=self.file, width=30) self.file_entry.grid(row=row, column=1, columnspan=2, sticky=Tkinter.EW) row = row + 1 label = Label(master, text='Format:') label.grid(row=row, column=0, sticky=Tkinter.W) self.format_menu = PulldownMenu(master, entries=exportFormats) self.format_menu.grid(row=row, column=1, columnspan=2, sticky=Tkinter.W) row = row + 1 master.grid_rowconfigure(row, weight=1) texts = ['Save'] commands = [self.ok] buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Cancel') buttons.grid(row=row, column=0, columnspan=3, sticky=Tkinter.EW) def toggleCheckButton(self, isSelected): for i in self.check_buttons.keys(): self.exportSelection[i] = self.check_buttons[i].get() def apply(self): file = self.file_entry.get() format = self.format_menu.getSelected() join = exportJoin[format] n = 0 headings = [] for heading in self.headings: if self.check_buttons[n].get(): headings.append(n) n += 1 if (not headings): showError('Nothing selected', 'No data selected to export.', parent=self) return False try: fp = open(file, 'w') except IOError, e: showError('File error', str(e)) return False for n in headings: if (n != headings[0]): fp.write(join) fp.write(self.headings[n].encode('utf-8')) fp.write('\n') m = 0 for data in self.entries: if data: for n in headings: if (n != headings[0]): fp.write(join) if (self.addNumber): if (n == 0): x = m + 1 else: x = data[n - 1] else: x = data[n] if (type(x) == type(float(1))): if (x == 0): t = '0' elif ((abs(x) > 10000) or (abs(x) < 0.001)): t = '%6.5e' % x else: t = '%6.5f' % x else: t = str(x) fp.write(t) fp.write('\n') m = m + 1 fp.close() return True
class EditResStructuresPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.structure = None self.constraintSet = None self.cloud = None self.cloudRmsdDict = {} self.strucRmsdDict = {} self.waiting = False BasePopup.__init__(self, parent=parent, title="Resonance Cloud Structures", **kw) def body(self, guiFrame): row = 0 guiFrame.grid_columnconfigure(1, weight=1) guiFrame.grid_rowconfigure(0, weight=0) guiFrame.grid_rowconfigure(1, weight=1) self.generationLabel = Label(guiFrame, text='Structure Generation:') constraintSets = [] constraintSetNames = [] index = -1 for constraintSet in self.project.nmrConstraintStores: index += 1 constraintSets.append(constraintSet) constraintSetNames.append(str(constraintSet.serial)) self.constraintSet = constraintSet self.constrSetPulldown = PulldownMenu(guiFrame, self.changeConstraintSet, constraintSetNames, selected_index=index, do_initial_callback=False) self.generationLabel.grid(row=row, column=0, columnspan=1, sticky='e') self.constrSetPulldown.grid(row=row, column=1, columnspan=1, sticky='w') strucLabel = Label(guiFrame, text='Comparison structure') strucLabel.grid(row=row, column=2, sticky='e') self.strucPulldown = PulldownMenu(guiFrame, entries=self.getStructures(), callback=self.setStructure, selected_index=0, do_initial_callback=False) self.strucPulldown.grid(row=row, column=3, sticky='w') sdTolLabel = Label(guiFrame, text='Tolerance (SDs):') sdTolLabel.grid(row=row, column=4, sticky='e') self.sdToleranceEntry = FloatEntry(guiFrame, text=2.0, width=6) self.sdToleranceEntry.grid(row=row, column=5, stick='w') row += 1 colHeadings = ['#', 'File name', 'RMSD to mean', 'RMSD to structure'] self.scrolledMatrix = ScrolledMatrix(guiFrame, initialRows=10, headingList=colHeadings, callback=self.selectCell, objectList=[], textMatrix=[ [], ]) self.scrolledMatrix.grid(row=row, column=0, columnspan=6, sticky='nsew') row += 1 texts = [ 'Calc\nRMSD', 'Make Cloud\nfrom structure', 'Delete', 'Delete\nbad' ] commands = [ self.calcRmsd, self.makeStrucCloud, self.deleteCloud, self.filterClouds ] self.bottomButtons = UtilityButtonList(guiFrame, texts=texts, expands=False, commands=commands, helpUrl=self.help_url) self.bottomButtons.grid(row=row, column=0, columnspan=6, sticky='nsew') self.update() for func in ('__init__', 'delete'): self.registerNotify(self.updateStructureGen, 'ccp.nmr.Nmr.StructureGeneration', func) def open(self): self.updateAfter() BasePopup.open(self) def getStructures(self): names = [ '<None>', ] for molSystem in self.project.sortedMolSystems(): for structure in molSystem.sortedStructureEnsembles(): names.append('%s:%d' % (molSystem.name, structure.ensembleId)) return names def setStructure(self, index, name=None): if index < 1: self.structure = None else: structures = [] for molSystem in self.project.sortedMolSystems(): for structure in molSystem.sortedStructureEnsembles(): structures.append(structure) self.structure = structures[index - 1] def filterClouds(self): if self.constraintSet: sdTolerance = self.sdToleranceEntry.get() or 2.0 keptClouds = [] clouds = self.guiParent.application.getValues( self.constraintSet, 'clouds') meanGroupRmsds = [] for cloud in clouds: rmsd = self.cloudRmsdDict.get(cloud) if rmsd is not None: meanGroupRmsds.append(rmsd) meanRmsd = 0.0 N = 0 for rmsd in meanGroupRmsds: meanRmsd += rmsd N += 1 if N > 0: meanRmsd /= float(N) sd = 0.0 for rmsd in meanGroupRmsds: sd += (rmsd - meanRmsd) * (rmsd - meanRmsd) if N > 0: sd /= float(N - 1) sd = sqrt(sd) print meanRmsd, '+/-', sd n = 0 for cloud in clouds: rmsd = self.cloudRmsdDict.get(cloud) if rmsd is None: keptClouds.append(cloud) elif abs(rmsd - meanRmsd) > (sdTolerance * sd): print 'Cloud %s is bad' % (cloud) else: keptClouds.append(cloud) self.guiParent.application.setValues(self.constraintSet, 'clouds', values=keptClouds) self.updateAfter() def makeStrucCloud(self): if self.structure: serials = self.guiParent.application.getValues( self.constraintSet, 'cloudsResonances') pdbFileName = 'CloudForStructure.pdb' #from ccpnmr.clouds.AtomCoordList import AtomCoordList from ccpnmr.c.AtomCoordList import AtomCoordList atomCoordList = AtomCoordList() resDict = {} hmass = 25 print "L1", len(serials) for resonance in self.nmrProject.resonances: resDict[resonance.serial] = resonance print "L2", len(resDict) resonances = [] for serial in serials: if resDict.get(serial) is not None: resonances.append(resDict[serial]) print "L3", len(resonances) C = 0 for resonance in resonances: resonanceSet = resonance.resonanceSet if resonanceSet: i = resonanceSet.sortedResonances().index(resonance) atomSet = resonance.resonanceSet.sortedAtomSets()[i] coords = getAtomSetCoords(atomSet, self.structure) coord = coords[0] atomCoordList.add(hmass, coord.x, coord.y, coord.z) C += 1 print "L4", len(atomCoordList) from ccpnmr.clouds.FilterClouds import writeTypedPdbCloud writeTypedPdbCloud(atomCoordList, pdbFileName, resonances) clouds = self.guiParent.application.getValues( self.constraintSet, 'clouds') clouds.append(pdbFileName) self.guiParent.application.setValues(self.constraintSet, 'clouds', values=clouds) self.updateAfter() def calcRmsd(self): if self.constraintSet: clouds = self.guiParent.application.getValues( self.constraintSet, 'clouds') from ccpnmr.clouds.FilterClouds import filterClouds rmsds = filterClouds(clouds) n = len(clouds) for i in range(n): cloud = clouds[i] rmsd = rmsds[i] self.cloudRmsdDict[cloud] = rmsd self.updateAfter() def changeConstraintSet(self, i, name): project = self.project if project.nmrConstraintStores: constraintSet = project.nmrConstraintStores[i] else: constraintSet = None if constraintSet is not self.constraintSet: self.constraintSet = constraintSet self.cloud = None self.updateAfter() def deleteCloud(self): if self.constraintSet and self.cloud and showOkCancel( 'Confirm', 'Really delete resonance cloud?', parent=self): clouds = self.guiParent.application.getValues( self.constraintSet, 'clouds') if clouds: clouds.remove(self.cloud) self.cloud = None self.guiParent.application.setValues(self.constraintSet, 'clouds', values=clouds) self.updateAfter() def selectCell(self, cloud, row, col): self.cloud = cloud self.bottomButtons.buttons[1].enable() def updateAfter(self, *opt): if self.waiting: return else: self.waiting = True self.after_idle(self.update) def getConstraintSetNames(self): names = [] constraintSets = self.project.nmrConstraintStores for set in constraintSets: names.append('%d' % set.serial) return names def updateStructureGen(self, *opt): project = self.project constraintSets = self.project.sortedNmrConstraintStores if constraintSets: constraintSetNames = self.getConstraintSetNames() # set defaults if self.constraintSet not in constraintSets: self.constraintSet = constraintSets[0] self.cloud = None i = constraintSets.index(self.constraintSet) self.constrSetPulldown.setup(constraintSetNames, i) else: self.constraintSet = None self.cloud = None self.constrSetPulldown.setup([], -1) def destroy(self): for func in ('__init__', 'delete'): self.unregisterNotify(self.updateStructureGen, 'ccp.nmr.Nmr.StructureGeneration', func) BasePopup.destroy(self) def update(self): objectList = [] textMatrix = [] if self.constraintSet: clouds = self.guiParent.application.getValues( self.constraintSet, 'clouds') if clouds: objectList = list(clouds) i = 0 for cloud in objectList: i += 1 datum = [] datum.append(i) datum.append(cloud) datum.append(self.cloudRmsdDict.get(cloud) or '-') datum.append(self.strucRmsdDict.get(cloud) or '-') textMatrix.append(datum) if not self.cloud: self.bottomButtons.buttons[1].disable() self.scrolledMatrix.update(objectList=objectList, textMatrix=textMatrix) self.waiting = False
class PredictKarplusPopup(BasePopup): def __init__(self, parent, *args, **kw): self.waiting = False self.molSystem = None self.residue = None self.jCouplings = [] self.atomNames = [] self.measureJCouplingList = None self.predictJCouplingList = None self.coeffAtomNames = [] self.coefficients = {} self.coefficient = None for i in range(3): self.coefficients[i] = {} BasePopup.__init__( self, parent=parent, title='Predict Karplus Coefficients from J Coupling', **kw) self.updateJCouplingLists() self.updateMolSystems() self.updateAfter() def body(self, guiFrame): guiFrame.grid_columnconfigure(0, weight=1, minsize=500) row = 0 frame = LabelFrame(guiFrame, text='General Options') frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(1, weight=1) label = Label(frame, text='Molecular System:') label.grid(row=0, column=0, sticky='w') self.molSystemPulldown = PulldownMenu(frame, self.changeMolSystem, do_initial_callback=False) self.molSystemPulldown.grid(row=0, column=1, sticky='w') label = Label(frame, text='Measured J coupling list:') label.grid(row=0, column=2, sticky='w') self.measureCouplingListPulldown = PulldownMenu( frame, self.changeMeasureCouplingList) self.measureCouplingListPulldown.grid(row=0, column=3, sticky='w') label = Label(frame, text='Predicted J coupling list:') label.grid(row=0, column=4, sticky='w') self.predictCouplingListPulldown = PulldownMenu( frame, self.changePredictCouplingList) self.predictCouplingListPulldown.grid(row=0, column=5, sticky='w') row += 1 guiFrame.grid_rowconfigure(row, weight=1) frame = LabelFrame(guiFrame, text='Angles & 3J Couplings') frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) headingList = ['Residue', 'Phi', 'Chi^2'] editWidgets = [None, None, None] editGetCallbacks = [None, None, None] editSetCallbacks = [None, None, None] self.jCouplingEntry = FloatEntry( self, width=8, returnCallback=lambda event: self.setJCoupling()) i = 0 for names in couplingAtoms: headingList.extend( ['Pred\nJ(%s,%s)' % names, 'Expt\nJ(%s,%s)' % names]) editWidgets.extend([None, self.jCouplingEntry]) editGetCallbacks.extend( [None, lambda obj, i=i: self.getJCoupling(obj, i)]) editSetCallbacks.extend( [None, lambda event, i=i: self.setJCoupling(i)]) i += 1 self.couplingMatrix = ScrolledMatrix(frame, headingList=headingList, editWidgets=editWidgets, editGetCallbacks=editGetCallbacks, editSetCallbacks=editSetCallbacks, callback=self.selectJCoupling, multiSelect=False) self.couplingMatrix.grid(row=0, column=0, sticky='nsew') self.couplingMatrix.doEditMarkExtraRules = self.doEditMarkExtraRules row += 1 frame = LabelFrame(guiFrame, text='Karplus Coefficients') frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) headingList = ['Phase'] editWidgets = [ None, ] editGetCallbacks = [ None, ] editSetCallbacks = [ None, ] self.coefficientEntry = FloatEntry( self, width=8, returnCallback=lambda event: self.setCoefficient()) for names in couplingAtoms: headingList.append('J(%s,%s)' % names) editWidgets.append(self.coefficientEntry) editGetCallbacks.append( lambda obj, n=names: self.getCoefficient(obj, n)) editSetCallbacks.append( lambda event, n=names: self.setCoefficient(n)) headingList = [ 'Phase', 'J(H,HA)', 'J(H,C)', 'J(H,CB)', 'J(C,HA)', 'J(C,C)', 'J(C,CB)' ] self.coefficientMatrix = ScrolledMatrix( frame, headingList=headingList, editWidgets=editWidgets, editGetCallbacks=editGetCallbacks, editSetCallbacks=editSetCallbacks, callback=self.selectCoefficient, maxRows=3, multiSelect=False) self.coefficientMatrix.grid(row=0, column=0, sticky='nsew') row += 1 texts = [] commands = [] self.bottomButtons = UtilityButtonList(guiFrame, commands=commands, texts=texts, helpUrl=self.help_url) self.bottomButtons.grid(row=row, column=0, sticky='ew') for func in ('__init__', 'delete', 'setValue', 'setError'): for clazz in ('ccp.nmr.Nmr.JCoupling', ): self.registerNotify(self.updateAfter, clazz, func) for func in ('__init__', 'delete'): for clazz in ('ccp.nmr.Nmr.JCouplingList', ): self.registerNotify(self.updateJCouplingLists, clazz, func) def getJCouplingLists(self, isSimulated=False): jCouplingLists = self.nmrProject.findAllMeasurementLists( className='JCouplingList', isSimulated=isSimulated) return jCouplingLists def updateJCouplingLists(self, *obj): jCouplingLists = self.getJCouplingLists(isSimulated=False) names = [ '%d:%s' % (jcl.serial, jcl.name or '') for jcl in jCouplingLists ] names.append('<New>') index = -1 if jCouplingLists: if self.measureJCouplingList in jCouplingLists: index = jCouplingLists.index(self.measureJCouplingList) else: self.measureJCouplingList = jCouplingLists[0] index = 0 else: self.measureJCouplingList = None self.measureCouplingListPulldown.setup(names, index) jCouplingLists = self.getJCouplingLists(isSimulated=True) names = ['%d:%s' % (jcl.serial, jcl.name) for jcl in jCouplingLists] names.append('<New>') index = -1 if jCouplingLists: if self.predictJCouplingList in jCouplingLists: index = jCouplingLists.index(self.predictJCouplingList) else: self.predictJCouplingList = jCouplingLists[0] index = 0 else: self.predictJCouplingList = None self.predictCouplingListPulldown.setup(names, index) def changeMeasureCouplingList(self, index, name): if name == '<New>': self.measureJCouplingList = None else: jCouplingLists = self.getJCouplingLists() jCouplingList = jCouplingLists[index] if jCouplingList is not self.measureJCouplingList: self.measureJCouplingList = jCouplingList if self.predictJCouplingList is self.measureJCouplingList: for jCouplingList2 in jCouplingLists: if self.measureJCouplingList is not jCouplingList2: self.predictJCouplingList = jCouplingList2 break else: self.predictJCouplingList = None self.updateAfter() def changePredictCouplingList(self, index, name): if name == '<New>': self.predictJCouplingList = None self.updateAfter() else: jCouplingLists = self.getJCouplingLists() jCouplingList = jCouplingLists[index] if jCouplingList is not self.predictJCouplingList: self.predictJCouplingList = jCouplingList if self.predictJCouplingList is self.measureJCouplingList: for jCouplingList2 in jCouplingLists: if self.predictJCouplingList is not jCouplingList2: self.measureJCouplingList = jCouplingList2 break else: self.measureJCouplingList = None self.updateAfter() def doEditMarkExtraRules(self, obj, row, col): i = (col - 3) / 2 if i > -1: atoms = couplingAtoms[i] residue = obj[0] for atomName in atoms: if not residue.findFirstAtom(name=atomName): return False return True def open(self): self.updateMolSystems() BasePopup.open(self) def selectJCoupling(self, object, row, col): self.residue = object[0] self.jCouplings = object[1:] def selectCoefficient(self, object, row, col): self.coefficient = object def getCoefficient(self, object, atomNames): self.coeffAtomNames = atomNames coefficient = self.coefficients[object].get(atomNames) self.coefficientEntry.set(coefficient) def setCoefficient(self, atomNames=None): if not atomNames: atomNames = self.coeffAtomNames value = self.coefficientEntry.get() if atomNames and (self.coefficient is not None): self.coefficients[self.coefficient][atomNames] = value #print self.coefficient, atomNames, value self.updateCoefficients() def getJCoupling(self, object, index): atomNames = couplingAtoms[index] self.atomNames = atomNames coupling = object[index + 1] if not coupling: residue = object[0] coupling = self.getResidueJCoupling(self.measureJCouplingList, residue, atomNames) if coupling: value = coupling.value else: value = None self.jCouplingEntry.set(value) def setJCoupling(self, index=None): if not index: atomNames = self.atomNames index = couplingAtoms.index(atomNames) else: atomNames = couplingAtoms[index] value = self.jCouplingEntry.get() if self.residue and atomNames: coupling = self.jCouplings[index] if value is None: if coupling: if showOkCancel('Confirm', 'Really remove J coupling?', parent=self): coupling.delete() else: if not coupling: self.setResidueJCoupling(self.measureJCouplingList, self.residue, atomNames, value, isSimulated=False) else: coupling.setValue(value) def getResidueJCoupling(self, jCouplingList, residue, atomNames): if jCouplingList: return getResidueJCoupling(jCouplingList, residue, atomNames) def setResidueJCoupling(self, jCouplingList, residue, atomNames, value, isSimulated=False): if jCouplingList is None: jCouplingList = self.nmrProject.newJCouplingList( isSimulated=isSimulated) if isSimulated: self.predictJCouplingList = jCouplingList else: self.measureJCouplingList = jCouplingList setResidueJCoupling(jCouplingList, self.residue, atomNames, value) def updateMolSystems(self, *obj): index = -1 names = [] molSystems = self.project.sortedMolSystems() if molSystems: if self.molSystem not in molSystems: self.molSystem = molSystems[0] names = [ms.code for ms in molSystems] index = molSystems.index(self.molSystem) self.molSystemPulldown.setup(names, index) def changeMolSystem(self, index, name): molSystems = self.project.sortedMolSystems() if molSystems: molSystem = molSystems[index] else: molSystem = None if molSystem is not self.molSystem: self.molSystem = molSystem self.updateAfter() def updateAfter(self, object=None): current = False if object and (object.className == 'JCoupling'): for resonance in object.resonances: resonanceSet = resonance.resonanceSet if resonanceSet: molSystem = resonanceSet.findFirstAtomSet().findFirstAtom( ).topObject if molSystem is self.molSystem: current = True break else: current = True if self.waiting or (not current): return else: self.waiting = True self.after_idle(self.update) def update(self): textMatrix = [] objectList = [] if self.molSystem: chains = self.molSystem.sortedChains() if len(chains) > 1: doChains = False else: doChains = True for chain in chains: if doChains: chainCode = chain.code else: chainCode = '' for residue in chain.sortedResidues(): name = '%s%d%s' % (chainCode, residue.seqCode, getResidueCode(residue)) phi = 0.0 chiSq = 0.0 datum = [name, phi, chiSq] object = [ residue, ] for atomNames in couplingAtoms: couplingM = self.getResidueJCoupling( self.measureJCouplingList, residue, atomNames) couplingP = self.getResidueJCoupling( self.predictJCouplingList, residue, atomNames) pred = None expt = None if couplingM: expt = couplingM.value if couplingP: pred = couplingP.value datum.append(pred) datum.append(expt) object.append(couplingM) objectList.append(object) textMatrix.append(datum) self.couplingMatrix.update(textMatrix=textMatrix, objectList=objectList) self.updateCoefficients() self.waiting = False def updateCoefficients(self): textMatrix = [] objectList = [] for i in range(3): name = 'C%d' % i datum = [ name, ] for atomNames in couplingAtoms: datum.append(self.coefficients[i].get(atomNames)) textMatrix.append(datum) objectList.append(i) self.coefficientMatrix.update(textMatrix=textMatrix, objectList=objectList) def destroy(self): for func in ('__init__', 'delete', 'setValue', 'setError'): for clazz in ('ccp.nmr.Nmr.JCoupling', ): self.unregisterNotify(self.updateAfter, clazz, func) for func in ('__init__', 'delete'): for clazz in ('ccp.nmr.Nmr.JCouplingList', ): self.unregisterNotify(self.updateJCouplingLists, clazz, func) BasePopup.destroy(self)
class AtomSelectPopup(TemporaryBasePopup): def __init__(self, parent, matchName, chemAtomList, chemAtomDict, propagateList, ccpCode, shifts, matchType='Resonance', matchInfoPopup=None, selectedIndex=4, title='Select resonance atom match', helpUrl='AtomSelect.html', headerLines=None, modal=False): self.help_url = joinPath(getHelpUrlDir(), helpUrl) # Constructor doesn't do much except call body # The parent is self.parent (parent of the popup) self.chemAtomOrSets = None self.propagate = None self.matchName = matchName self.matchType = matchType self.matchInfoPopup = matchInfoPopup self.chemAtomList = chemAtomList self.chemAtomDict = chemAtomDict self.propagateList = propagateList self.ccpCode = ccpCode self.shifts = shifts self.guiParent = parent self.headerLines = headerLines self.selectedIndex = selectedIndex # modal = true means that it won't continue unless this one returns value TemporaryBasePopup.__init__(self, parent=parent, title=title, modal=modal, transient=True) def showAllAtoms(self): self.chemAtomList = self.chemAtomDict.keys() self.chemAtomList.sort() self.menu.replace(self.chemAtomList) def body(self, master): # # Popup window # row = 0 if self.headerLines: for headerLine in self.headerLines: label = Label(master, text=headerLine) label.grid(row=row, column=0, columnspan=3, sticky=Tkinter.EW) row += 1 label = Label(master, text="Residue type '%s'" % self.ccpCode) label.grid(row=row, column=0, columnspan=3, sticky=Tkinter.EW) row = row + 1 matchNameString = "[%s]" % self.matchName if self.matchInfoPopup: label = Label(master, text="%s:" % self.matchType) label.grid(row=row, column=0, sticky=Tkinter.E) button = Tkinter.Button( master, text=matchNameString, command=lambda: self.matchInfoPopup(self, self.matchName), fg='blue') button.grid(row=row, column=1, columnspan=2) else: label = Label(master, text="%s:" % self.matchType) label.grid(row=row, column=0, sticky=Tkinter.E) label = Label(master, text=matchNameString, fg='blue') label.grid(row=row, column=1, columnspan=2) if self.shifts: row = row + 1 label = Label(master, text="(shifts: %s ppm)" % self.shifts) label.grid(row=row, column=1, columnspan=2, sticky=Tkinter.EW) row = row + 1 label = Label(master, text="Pick atom:") label.grid(row=row, column=0, sticky=Tkinter.E) self.menu = PulldownMenu(master, entries=self.chemAtomList) self.menu.grid(row=row, column=1, columnspan=2, ipadx=20) row = row + 1 label = Label(master, text="Propagate\nmapping to:") label.grid(row=row, column=0, sticky=Tkinter.E) self.propagateMenu = PulldownMenu(master, entries=self.propagateList, selected_index=self.selectedIndex) self.propagateMenu.grid(row=row, column=1, columnspan=2) row = row + 1 texts = ['OK', 'Show all atoms'] commands = [ self.ok, self.showAllAtoms ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Do not link', dismiss_cmd=self.doNotLink, help_url=self.help_url) buttons.grid(row=row, column=0, columnspan=3) def apply(self): selectionText = self.menu.getSelected() if selectionText == '<None>': return False self.chemAtomOrSets = self.chemAtomDict[selectionText] self.propagate = self.propagateMenu.getSelectedIndex() return True def doNotLink(self): self.propagate = self.propagateMenu.getSelectedIndex() self.close()
class EditSymmetryPopup(BasePopup): def __init__(self, parent, project): self.parent = parent self.ccpnProject = project self.hProject = project.currentHaddockProject self.molPartner = None self.molecules = [] self.symmetrySet = None self.symmetryOp = None self.symmetryCode = None self.waiting = False BasePopup.__init__(self, parent=parent, title='Symmetry Operations') self.font = 'Helvetica 12' self.setFont() def body(self, guiFrame): guiFrame.grid_columnconfigure(0, weight=1) guiFrame.grid_rowconfigure(1, weight=1) frame = LabelFrame(guiFrame, text='Options') frame.grid(row=0,column=0,sticky='ew') frame.grid_columnconfigure(5, weight=1) # Choose type of symmetry set to define or change (if allready present in the model) self.molLabel = Label(frame, text='Symmetry Operator:') self.molLabel.grid(row=0,column=2,sticky='w') self.symmCodePulldown = PulldownMenu(frame, callback=self.setSymmCode, entries=['NCS','C2','C3','C5'], do_initial_callback=False) self.symmCodePulldown.grid(row=0,column=3,sticky='w') frame = LabelFrame(guiFrame, text='Symmetry Operations') frame.grid(row=1,column=0,sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) self.molSysPulldown = PulldownMenu(self, callback=self.setMolSystem, do_initial_callback=False) self.chainSelect = MultiWidget(self, CheckButton, callback=self.setChains, minRows=0, useImages=False) self.segStartEntry = IntEntry(self, returnCallback=self.setSegStart, width=6) self.segLengthEntry = IntEntry(self, returnCallback=self.setSegLength, width=6) headings = ['#','Symmetry\noperator','Mol System','Chains','Start\nresidue','Segment\nlength'] editWidgets = [None, None, self.molSysPulldown, self.chainSelect, self.segStartEntry, self.segLengthEntry] editGetCallbacks = [None, None, self.getMolSystem, self.getChains, self.getSegStart, self.getSegLength] editSetCallbacks = [None, self.setSymmCode, self.setMolSystem, self.setChains, self.setSegStart, self.setSegLength] self.symmetryMatrix = ScrolledMatrix(frame,headingList=headings, callback=self.selectSymmetry, editWidgets=editWidgets, editGetCallbacks=editGetCallbacks, editSetCallbacks=editSetCallbacks) self.symmetryMatrix.grid(row=0,column=0,sticky='nsew') texts = ['Add Symmetry Set','Remove Symmetry Set'] commands = [self.addSymmetrySet,self.removeSymmetrySet] self.buttonList = createDismissHelpButtonList(guiFrame, texts=texts, commands=commands, expands=True) self.buttonList.grid(row=2,column=0,sticky='ew') self.updateMolPartners() self.notify(self.registerNotify) #Temporary report of parameters print self.molSystem print self.molecules print self.symmetrySet print self.symmetryOp print self.symmetryCode def getMolSystem(self, partner): """Select molecular system from list of molsystems stored in the project""" names = []; index = -1 molSystem = partner.molSystem molSystems = self.ccpnProject.sortedMolSystems() if molSystems: names = [ms.code for ms in molSystems] if molSystem not in molSystems: molSystem = molSystems[0] index = molSystems.index(molSystem) self.molSysPulldown.setup(names, index) def getChains(self, partner): names = [] values = [] molSystem = partner.molSystem if molSystem: for chain in molSystem.sortedChains(): names.append(chain.code) if not partner.chains: values.append(True) elif partner.findFirstChain(chain=chain): values.append(True) else: values.append(False) self.chainSelect.set(values=values,options=names) else: showWarning('Warning','Set Mol System or ensemble first',parent=self) self.symmetryMatrix.keyPressEscape() def getSegLength(self, symmetryOp): if symmetryOp and symmetryOp.segmentLength: self.segLengthEntry.set(symmetryOp.segmentLength) def getSegStart(self): pass def setMolSystem(self, partner, name=None): """Get all molsystems as stored in the project as list""" index = self.molSysPulldown.getSelectedIndex() molSystems = self.ccpnProject.sortedMolSystems() if molSystems: molSystem = molSystems[index] self.molPartner.molSystem = molSystem chains = molSystem.sortedChains() if (not self.molPartner.chains) and chains: setPartnerChains(self.molPartner,chains) self.updateAllAfter() def setChains(self, obj): """Get the list of chains for the selected molsystem""" if self.molPartner and self.molPartner.molSystem: if obj is not None: chains = self.molPartner.molSystem.sortedChains() values = self.chainSelect.get() chains = [chains[i] for i in range(len(values)) if values[i]] setPartnerChains(self.molPartner,chains) self.symmetryMatrix.keyPressEscape() self.updateAllAfter() def setSegLength(self, event): value = self.segLengthEntry.get() or 1 self.symmetryOp.segmentLength = value def setSegStart(self): pass def setSymmCode(self, index, name=None): self.symmetryCode = self.symmCodePulldown.getSelected() def selectSymmetry(self, obj, row, col): self.symmetryOp = obj self.updateMolSysPulldown() def notify(self, notifyFunc): for func in ('__init__', 'delete', 'setSymmetryCode','setSegmentLength'): notifyFunc(self.updateAllAfter, 'molsim.Symmetry.Symmetry', func) for func in ('__init__', 'delete','setfirstSeqId'): notifyFunc(self.updateAllAfter, 'molsim.Symmetry.Segment', func) def addSymmetrySet(self): if not self.ccpnProject.molSystems: showWarning('Warning','No molecular systems present in CCPN project',parent=self) return molSystem = self.ccpnProject.findFirstMolSystem() partner = self.hProject.newHaddockPartner(code=molSystem.code, molSystem=molSystem) setPartnerChains(partner, molSystem.chains) self.updateAllAfter() def removeSymmetrySet(self): pass def updateAllAfter(self, obj=None): if self.waiting: return else: self.waiting = True self.after_idle(self.updateSymmetries, self.updateMolPartners) def updateMolPartners(self): textMatrix = [] objectList = [] for partner in self.hProject.sortedHaddockPartners(): datum = [partner.code, self.symmetryCode, partner.molSystem.code, ','.join([c.chain.code for c in partner.chains]), partner.autoHistidinePstate and 'Yes' or 'No', partner.isDna and 'Yes' or 'No'] objectList.append(partner) textMatrix.append(datum) self.symmetryMatrix.update(objectList=objectList, textMatrix=textMatrix) self.updateMolSysPulldown() def updateMolSysPulldown(self): names = [] index = -1 partners = self.hProject.sortedHaddockPartners() if partners: if self.molPartner not in partners: self.molPartner = partners[0] names = ['Partner %s' % p.code for p in partners] index = partners.index(self.molPartner) else: self.molPartner = None self.molSysPulldown.setup(names, index) def updateSymmetries(self): textMatrix = []; objectList = [] if self.symmetrySet: for symmetryOp in self.symmetrySet.symmetries: chains = []; segments = [] length = symmetryOp.segmentLength for segment in symmetryOp.sortedSegments(): code = segment.chainCode chain = self.molSystem.findFirstChain(code=code) if chain: chains.append(code) seqId = segment.firstSeqId residue1 = chain.findFirstResidue(seqId=seqId) residue2 = chain.findFirstResidue(seqId=seqId+length-1) segments.append('%s:%d-%d' % (code,residue1.seqCode,residue2.seqCode)) datum = [symmetryOp.serial, symmetryOp.symmetryCode, length, '\n'.join(chains), '\n'.join(segments)] objectList.append(symmetryOp) textMatrix.append(datum) self.symmetryMatrix.update(objectList=objectList, textMatrix=textMatrix) self.waiting = False def destroy(self): self.notify(self.unregisterNotify) BasePopup.destroy(self)
def setupProchiralList(self, listIndex, chainLabel): chain = self.resParentChainLabelDict[self.resParent][chainLabel] self.chain = chain self.prochiralListFrame.destroy() self.prochiralListFrame = ScrolledFrame(self.prochiralListFrameMaster, width=200, doExtraConfig=False) self.prochiralListFrame.grid(row=self.prochiralListFrameRow, column=0, columnspan=2, sticky=Tkinter.NSEW) # # TODO: also handle case one resonance, two atomSets!?!? # frameRow = 0 x = y = 0 frame = self.prochiralListFrame.frame self.resonanceObjects = {} self.resonanceLabelDict = {} # # Reuse previous settings... # if len(self.chainResonancesDict[self.resParent][chain]) == len( self.chainAtomSetsDict[self.resParent][chain]): usePreviousSettings = True else: usePreviousSettings = False for i in range(0, len(self.chainAtomSetsDict[self.resParent][chain])): atomSetGroup = self.chainAtomSetsDict[self.resParent][chain][i] isStereo = False hasResonances = False isValidCase = False resonances = [] if usePreviousSettings and self.chainResonancesDict[ self.resParent][chain][i]: resonances = self.chainResonancesDict[ self.resParent][chain][i][3] isStereo = self.chainResonancesDict[ self.resParent][chain][i][0] hasResonances = True isValidCase = True else: for atomSet in atomSetGroup: resonanceSets = atomSet.sortedResonanceSets() if resonanceSets: hasResonances = True for resonanceSet in resonanceSets: for resonance in resonanceSet.sortedResonances(): if resonance not in resonances: resonances.append(resonance) if len(resonanceSets) == 1: isValidCase = True if len(resonanceSet.atomSets) == 1: isStereo = True else: # Case only one resonance but stereo assigned resonances.append(0) if len(resonances) == 1: # Case only one resonance, not stereo assigned resonances.append(None) # # Set up only for valid cases # if hasResonances and isValidCase: if not usePreviousSettings: self.chainResonancesDict[self.resParent][chain].append( [isStereo, False, False, resonances]) residue = atomSetGroup[0].findFirstAtom().residue ccpCode = residue.molResidue.ccpCode seqCode = residue.seqCode rowspan = 2 checkButton = CheckButton( frame, selected=isStereo, callback=lambda status=isStereo, fr=frameRow, item=i, setup =False: self.toggleResonances(status, fr, item, setup)) checkButton.grid(row=frameRow, rowspan=rowspan, column=0, sticky=Tkinter.EW) label = Label(frame, text=ccpCode, width=5) label.grid(row=frameRow, rowspan=rowspan, column=1, sticky=Tkinter.E) label = Label(frame, text=str(seqCode), width=5) label.grid(row=frameRow, rowspan=rowspan, column=2, sticky=Tkinter.W) # # Set up the atom names # for j in range(0, len(atomSetGroup)): atomSet = atomSetGroup[j] label = Label(frame, text=atomSet.name) label.grid(row=frameRow + j, column=3, sticky=Tkinter.E, ipadx=4) # # Set up the resonances # self.resonanceObjects[frameRow] = { True: [[], []], False: [[], []] } resonanceLabelList = [] for resonance in resonances: if not resonance: resonanceLabel = 'unknown' else: if hasattr(resonance, 'shifts') and resonance.shifts: shiftLabel = " (shifts: " for shift in resonance.sortedShifts(): shiftLabel += "%.2f, " % shift.value shiftLabel = shiftLabel[:-2] + ")" else: shiftLabel = "" resonanceLabel = "'%d.%s'%s" % ( seqCode, resonance.name, shiftLabel) self.resonanceLabelDict[resonanceLabel] = resonance resonanceLabelList.append(resonanceLabel) separator = Separator(frame, height=1, width=30) separator.setColor('black', bgColor='black') separator.grid(row=frameRow, column=4, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][0].append(separator) separator = CrossLine(frame, height=20, width=30, canvas_bg=frame['bg'], color='dimgray') self.resonanceObjects[frameRow][False][0].append(separator) resonanceList = PulldownMenu( frame, entries=resonanceLabelList, callback=lambda selInd=x, selItem=y, fr=frameRow, item=i: self.setProchiralLabels(selInd, selItem, fr, item), do_initial_callback=False, label_color='red') resonanceList.grid(row=frameRow, column=5, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][0].append(resonanceList) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[0], fg='dimgray') self.resonanceObjects[frameRow][False][0].append( resonanceLabel) separator = Separator(frame, height=1, width=30) separator.setColor('black', bgColor='black') separator.grid(row=frameRow + 1, column=4) self.resonanceObjects[frameRow][True][1].append(separator) self.resonanceObjects[frameRow][False][1].append(None) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[1], fg='red') resonanceLabel.grid(row=frameRow + 1, column=5, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][1].append(resonanceLabel) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[1], fg='dimgray') self.resonanceObjects[frameRow][False][1].append( resonanceLabel) if not isStereo: checkButton.callback(isStereo, setup=True) separator = Separator(frame, height=1) separator.setColor('black', bgColor='black') separator.grid(row=frameRow + rowspan, columnspan=6, sticky=Tkinter.EW) frameRow += rowspan + 1 elif not usePreviousSettings: self.chainResonancesDict[self.resParent][chain].append(None) return True
class CloudHomologueAssignPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.project = parent.getProject() self.molSystem = None self.chain = None self.assignment = None self.scores = [] BasePopup.__init__(self, parent, title="Cloud Threader", **kw) def body(self, guiFrame): guiFrame.grid_columnconfigure(3, weight=1) row = 0 label = Label(guiFrame, text='Molecular system: ') label.grid(row=row, column=0, sticky=Tkinter.NW) self.molSysPulldown = PulldownMenu(guiFrame, self.changeMolSystem, selected_index=-1, do_initial_callback=0) self.molSysPulldown.grid(row=row, column=1, sticky=Tkinter.NW) label = Label(guiFrame, text='Clouds files: ') label.grid(row=row, column=2, sticky=Tkinter.NW) self.filenameEntry = Entry(guiFrame,text='perfect00.pdb') self.filenameEntry.grid(row=row, column=3, sticky=Tkinter.NW) row += 1 label = Label(guiFrame, text='Chain: ') label.grid(row=row, column=0, sticky=Tkinter.NW) self.chainPulldown = PulldownMenu(guiFrame, self.changeChain, selected_index=-1, do_initial_callback=0) self.chainPulldown.grid(row=row, column=1, sticky=Tkinter.NW) label = Label(guiFrame, text='Thread steps: ') label.grid(row=row, column=2, sticky=Tkinter.NW) self.numStepsEntry = IntEntry(guiFrame,text=3000) self.numStepsEntry.grid(row=row, column=3, sticky=Tkinter.NW) row += 1 label = Label(guiFrame, text='Homologue PDB file: ') label.grid(row=row, column=0, sticky=Tkinter.NW) self.pdbEntry = Entry(guiFrame,text='') self.pdbEntry.grid(row=row, column=1, sticky=Tkinter.NW) label = Label(guiFrame, text='Dist. Threshold: ') label.grid(row=row, column=2, sticky=Tkinter.NW) self.distEntry = FloatEntry(guiFrame,text=3.0) self.distEntry.grid(row=row, column=3, sticky=Tkinter.NW) row += 1 label = Label(guiFrame, text='Global score: ') label.grid(row=row, column=0, sticky=Tkinter.NW) self.globalScoreLabel = Label(guiFrame, text='') self.globalScoreLabel.grid(row=row, column=1, sticky=Tkinter.NW) label = Label(guiFrame, text='Assignment Threshold: ') label.grid(row=row, column=2, sticky=Tkinter.NW) self.thresholdEntry = FloatEntry(guiFrame,text=-4.5) self.thresholdEntry.grid(row=row, column=3, sticky=Tkinter.NW) row += 1 guiFrame.grid_rowconfigure(row, weight=1) self.graph = ScrolledGraph(guiFrame, width=300, height=200) self.graph.grid(row=row, column=0, columnspan=4, sticky = Tkinter.NSEW) row += 1 texts = ['Run','Assign!'] commands = [self.run, self.assignSpinSystems] bottomButtons = createDismissHelpButtonList(guiFrame,texts=texts,commands=commands,expands=0,help_url=None) bottomButtons.grid(row=row, column=0, columnspan=4, sticky=Tkinter.EW) self.assignButton = bottomButtons.buttons[1] for func in ('__init__','delete'): Implementation.registerNotify(self.updateMolSystems, 'ccp.molecule.MolSystem.MolSystem', func) Implementation.registerNotify(self.updateChains, 'ccp.molecule.MolSystem.Chain', func) self.updateMolSystems() self.updateChains() def update(self): if self.assignment and self.scores: self.assignButton.enable() else: self.assignButton.disable() def run(self): if self.chain: pattern = self.filenameEntry.get() nSteps = self.numStepsEntry.get() or 4000 pdbFile = self.pdbEntry.get() dist = self.distEntry.get() or 3.0 pgb = ProgressBar(self, text='Searching', total=nSteps) files = getFileNamesFromPattern(pattern , '.') if not files: return clouds = getCloudsFromFile(files, self.chain.root) score, self.scores, self.assignment = cloudHomologueAssign(self.chain, clouds, pdbFile, dist, nSteps, self.graph, pgb) pgb.destroy() self.globalScoreLabel.set(str(score)) self.update() def assignSpinSystems(self): if self.assignment and self.scores: if showWarning('Query','Are you sure?'): threshold = self.thresholdEntry.get() or -4.0 i = 0 for residue in self.assignment.keys(): if self.scores[residue] > threshold: spinSystem = self.assignment[residue] assignSpinSystemResidue(spinSystem,residue=None) for residue in self.assignment.keys(): if self.scores[residue] > threshold: i += 1 spinSystem = self.assignment[residue] assignSpinSystemResidue(spinSystem,residue=residue) showWarning('Done','%d residues assigned' % i) def getMolSystems(self): names = [] for molSystem in self.project.molSystems: if molSystem.chains: names.append( '%s' % (molSystem.code) ) return names def changeMolSystem(self, i, name): self.molSystem = self.project.findFirstMolSystem(code=name) def updateMolSystems(self, *opt): names = self.getMolSystems() if names: if not self.molSystem: self.molSystem = self.project.findFirstMolSystem(code=names[0]) self.molSysPulldown.setup(names, names.index(self.molSystem.code)) def getChains(self): chains = [] if self.molSystem: for chain in self.molSystem.chains: chains.append( [chain.code, chain] ) return chains def changeChain(self, i, name=None): if not name: i = self.chainPulldown.selected_index chains = self.getChains() if chains: self.chain = chains[i][1] def updateChains(self, *chain): chains = self.getChains() if chains: names = [x[0] for x in chains] if (not self.chain) or (self.chain.code not in names): self.chain = chains[0][1] self.chainPulldown.setup(names, names.index(self.chain.code) ) self.update() def destroy(self): for func in ('__init__','delete'): Implementation.unregisterNotify(self.updateMolSystems, 'ccp.molecule.MolSystem.MolSystem', func) Implementation.unregisterNotify(self.updateChains, 'ccp.molecule.MolSystem.Chain', func) BasePopup.destroy(self)
class ProchiralStatusPopup(TemporaryBasePopup): help_url = joinPath(getHelpUrlDir(), 'ProchiralStatus.html') def __init__(self, parent, chainList, chainAtomSetsDict): self.chainList = chainList self.chainAtomSetsDict = chainAtomSetsDict self.resParentDict = {} self.resParentList = [] self.resParentChainLabelDict = {} self.resParentChainLabelList = {} self.chainResonancesDict = {} for resParent in self.chainAtomSetsDict.keys(): if isinstance(resParent, NmrConstraint.NmrConstraintStore): strucGens = resParent.structureGenerations strucGenSerials = [str(sg.serial) for sg in strucGens] strucGenLabel = string.join(strucGenSerials, ',') resParentLabel = "Constraint set %d (strucGens %s)" % ( resParent.serial, strucGenSerials) else: resParentLabel = "Nmr project %s" % resParent.name self.resParentDict[resParentLabel] = resParent self.resParentList.append(resParentLabel) self.chainResonancesDict[resParent] = {} self.resParentChainLabelDict[resParent] = {} self.resParentChainLabelList[resParent] = [] for chain in self.chainList: self.project = chain.root if self.chainAtomSetsDict[resParent].has_key( chain) and self.chainAtomSetsDict[resParent][chain]: chainLabel = "Molecular system '%s':Chain '%s' (molecule '%s')" % ( chain.molSystem.code, chain.code, chain.molecule.name) self.resParentChainLabelList[resParent].append(chainLabel) self.resParentChainLabelDict[resParent][chainLabel] = chain self.chainResonancesDict[resParent][chain] = [] # modal = true means that it won't continue unless this one returns value TemporaryBasePopup.__init__( self, parent=parent, title="Project '%s': " % self.project.name + 'Set status prochiral atoms/resonances', modal=False, transient=True) def body(self, master): # # Setup header # row = 0 label = Label(master, text='Select the resonance list:') label.grid(row=row, column=0, sticky=Tkinter.EW) label = Label(master, text='Select the chain:') label.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 self.resParentSelect = PulldownMenu(master, entries=self.resParentList, callback=self.setupResParentList, do_initial_callback=False) self.resParentSelect.grid(row=row, column=0, sticky=Tkinter.EW) self.chainSelect = PulldownMenu(master, entries=[], callback=self.setupProchiralList, do_initial_callback=False) self.chainSelect.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, columnspan=2, sticky=Tkinter.EW) row += 1 # THIS BIT TELLS MASTER TO CONFIGURE WINDOW ON INSIDE WIDGET!! master.grid_rowconfigure(row, weight=1) for i in range(2): master.grid_columnconfigure(i, weight=1) self.prochiralListFrame = ScrolledFrame(master, width=200, doExtraConfig=False) self.prochiralListFrame.grid(row=row, column=0, columnspan=2, sticky=Tkinter.NSEW) self.prochiralListFrameRow = row self.prochiralListFrameMaster = master row = row + 1 texts = ['Set all', 'Set chain'] commands = [ self.ok, self.setStereo ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, dismiss_text='Exit', help_url=self.help_url) buttons.grid(row=row, column=0, columnspan=2, sticky=Tkinter.EW) self.resParentSelect.callback(0, self.resParentList[0]) def setupResParentList(self, listIndex, resParentLabel): resParent = self.resParentDict[resParentLabel] self.resParent = resParent self.chainSelect.setup(self.resParentChainLabelList[self.resParent], 0) self.chainSelect.callback( 0, self.resParentChainLabelList[self.resParent][0]) def setupProchiralList(self, listIndex, chainLabel): chain = self.resParentChainLabelDict[self.resParent][chainLabel] self.chain = chain self.prochiralListFrame.destroy() self.prochiralListFrame = ScrolledFrame(self.prochiralListFrameMaster, width=200, doExtraConfig=False) self.prochiralListFrame.grid(row=self.prochiralListFrameRow, column=0, columnspan=2, sticky=Tkinter.NSEW) # # TODO: also handle case one resonance, two atomSets!?!? # frameRow = 0 x = y = 0 frame = self.prochiralListFrame.frame self.resonanceObjects = {} self.resonanceLabelDict = {} # # Reuse previous settings... # if len(self.chainResonancesDict[self.resParent][chain]) == len( self.chainAtomSetsDict[self.resParent][chain]): usePreviousSettings = True else: usePreviousSettings = False for i in range(0, len(self.chainAtomSetsDict[self.resParent][chain])): atomSetGroup = self.chainAtomSetsDict[self.resParent][chain][i] isStereo = False hasResonances = False isValidCase = False resonances = [] if usePreviousSettings and self.chainResonancesDict[ self.resParent][chain][i]: resonances = self.chainResonancesDict[ self.resParent][chain][i][3] isStereo = self.chainResonancesDict[ self.resParent][chain][i][0] hasResonances = True isValidCase = True else: for atomSet in atomSetGroup: resonanceSets = atomSet.sortedResonanceSets() if resonanceSets: hasResonances = True for resonanceSet in resonanceSets: for resonance in resonanceSet.sortedResonances(): if resonance not in resonances: resonances.append(resonance) if len(resonanceSets) == 1: isValidCase = True if len(resonanceSet.atomSets) == 1: isStereo = True else: # Case only one resonance but stereo assigned resonances.append(0) if len(resonances) == 1: # Case only one resonance, not stereo assigned resonances.append(None) # # Set up only for valid cases # if hasResonances and isValidCase: if not usePreviousSettings: self.chainResonancesDict[self.resParent][chain].append( [isStereo, False, False, resonances]) residue = atomSetGroup[0].findFirstAtom().residue ccpCode = residue.molResidue.ccpCode seqCode = residue.seqCode rowspan = 2 checkButton = CheckButton( frame, selected=isStereo, callback=lambda status=isStereo, fr=frameRow, item=i, setup =False: self.toggleResonances(status, fr, item, setup)) checkButton.grid(row=frameRow, rowspan=rowspan, column=0, sticky=Tkinter.EW) label = Label(frame, text=ccpCode, width=5) label.grid(row=frameRow, rowspan=rowspan, column=1, sticky=Tkinter.E) label = Label(frame, text=str(seqCode), width=5) label.grid(row=frameRow, rowspan=rowspan, column=2, sticky=Tkinter.W) # # Set up the atom names # for j in range(0, len(atomSetGroup)): atomSet = atomSetGroup[j] label = Label(frame, text=atomSet.name) label.grid(row=frameRow + j, column=3, sticky=Tkinter.E, ipadx=4) # # Set up the resonances # self.resonanceObjects[frameRow] = { True: [[], []], False: [[], []] } resonanceLabelList = [] for resonance in resonances: if not resonance: resonanceLabel = 'unknown' else: if hasattr(resonance, 'shifts') and resonance.shifts: shiftLabel = " (shifts: " for shift in resonance.sortedShifts(): shiftLabel += "%.2f, " % shift.value shiftLabel = shiftLabel[:-2] + ")" else: shiftLabel = "" resonanceLabel = "'%d.%s'%s" % ( seqCode, resonance.name, shiftLabel) self.resonanceLabelDict[resonanceLabel] = resonance resonanceLabelList.append(resonanceLabel) separator = Separator(frame, height=1, width=30) separator.setColor('black', bgColor='black') separator.grid(row=frameRow, column=4, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][0].append(separator) separator = CrossLine(frame, height=20, width=30, canvas_bg=frame['bg'], color='dimgray') self.resonanceObjects[frameRow][False][0].append(separator) resonanceList = PulldownMenu( frame, entries=resonanceLabelList, callback=lambda selInd=x, selItem=y, fr=frameRow, item=i: self.setProchiralLabels(selInd, selItem, fr, item), do_initial_callback=False, label_color='red') resonanceList.grid(row=frameRow, column=5, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][0].append(resonanceList) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[0], fg='dimgray') self.resonanceObjects[frameRow][False][0].append( resonanceLabel) separator = Separator(frame, height=1, width=30) separator.setColor('black', bgColor='black') separator.grid(row=frameRow + 1, column=4) self.resonanceObjects[frameRow][True][1].append(separator) self.resonanceObjects[frameRow][False][1].append(None) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[1], fg='red') resonanceLabel.grid(row=frameRow + 1, column=5, sticky=Tkinter.EW) self.resonanceObjects[frameRow][True][1].append(resonanceLabel) resonanceLabel = Label(frame, text="%s" % resonanceLabelList[1], fg='dimgray') self.resonanceObjects[frameRow][False][1].append( resonanceLabel) if not isStereo: checkButton.callback(isStereo, setup=True) separator = Separator(frame, height=1) separator.setColor('black', bgColor='black') separator.grid(row=frameRow + rowspan, columnspan=6, sticky=Tkinter.EW) frameRow += rowspan + 1 elif not usePreviousSettings: self.chainResonancesDict[self.resParent][chain].append(None) return True def setProchiralLabels(self, selInd, selItem, fr, item): resonanceLabel = self.resonanceObjects[fr][True][0][1].entries[selInd] self.resonanceObjects[fr][False][0][1].set(resonanceLabel) selInd = not selInd resonanceLabel = self.resonanceObjects[fr][True][0][1].entries[selInd] self.resonanceObjects[fr][True][1][1].set(resonanceLabel) self.resonanceObjects[fr][False][1][1].set(resonanceLabel) self.chainResonancesDict[self.resParent][ self.chain][item][2] = not self.chainResonancesDict[ self.resParent][self.chain][item][2] self.chainResonancesDict[self.resParent][self.chain][item][3].reverse() def toggleResonances(self, status, frameRow, item, setup): if not setup: self.chainResonancesDict[self.resParent][ self.chain][item][0] = status self.chainResonancesDict[self.resParent][ self.chain][item][1] = not self.chainResonancesDict[ self.resParent][self.chain][item][1] for i in range(0, len(self.resonanceObjects[frameRow])): # # Remove other widgets from grid # rpds = self.resonanceObjects[frameRow][not status][i] for rpd in rpds: if rpd: rpd.grid_forget() # # Set current widgets # rpds = self.resonanceObjects[frameRow][status][i] for j in range(0, len(rpds)): rpd = rpds[j] if rpd: keywds = {} if j == 1: keywds['sticky'] = Tkinter.W if j == 0: if not status: keywds['rowspan'] = 2 rpd.grid(row=frameRow + i, column=4 + j, **keywds) def setStereo(self, chain=None): if not chain: chain = self.chain if self.chainResonancesDict[self.resParent][chain]: for i in range( 0, len(self.chainResonancesDict[self.resParent][chain])): atomSetGroup = self.chainAtomSetsDict[self.resParent][chain][i] (stereoStatus, stereoStatusChanged, resChanged, resonances ) = self.chainResonancesDict[self.resParent][chain][i] if stereoStatusChanged or (stereoStatus and resChanged): residue = atomSetGroup[0].findFirstAtom().residue ccpCode = residue.molResidue.ccpCode seqCode = residue.seqCode atomText = "%s/%s" % (atomSetGroup[0].name, atomSetGroup[1].name) if stereoStatusChanged: if stereoStatus: stereoText = "non-stereospecific to stereospecific." else: stereoText = "stereospecific to non-stereospecific." print " Warning: Changed '%s.%d' prochiral resonances for atoms %s from %s" % ( ccpCode, seqCode, atomText, stereoText) self.chainResonancesDict[ self.resParent][chain][i][1] = False self.chainResonancesDict[ self.resParent][chain][i][2] = False if stereoStatus: resonanceSet = atomSetGroup[ 0].findFirstResonanceSet() if resonances[0]: resonanceSet.removeAtomSet(atomSetGroup[1]) if resonances[1]: if not resonances[0]: # Remove right atom set if only one resonance... resonanceSet.removeAtomSet(atomSetGroup[0]) else: # Only create a new resonance set if two resonances present! resonanceSet.removeResonance(resonances[1]) if isinstance( self.resParent, NmrConstraint.NmrConstraintStore): newResonanceSet = self.resParent.newFixedResonanceSet( resonances=[resonances[1]], atomSets=[atomSetGroup[1]]) else: newResonanceSet = self.resParent.newResonanceSet( resonances=[resonances[1]], atomSets=[atomSetGroup[1]]) else: if resonances[0]: resonanceSet = atomSetGroup[ 0].findFirstResonanceSet() if resonances[1]: atomSetGroup[1].findFirstResonanceSet( ).delete() resonanceSet.addResonance(resonances[1]) resonanceSet.addAtomSet(atomSetGroup[1]) elif resonances[1]: resonanceSet = atomSetGroup[1].resonanceSets[0] resonanceSet.addAtomSet(atomSetGroup[0]) elif stereoStatus and resChanged: print " Warning: Changed resonance assignment for '%s.%d' stereospecifically assigned atoms %s." % ( ccpCode, seqCode, atomText) self.chainResonancesDict[ self.resParent][chain][i][2] = False resonanceSets = [] for i in range(0, 2): if atomSetGroup[i].resonanceSets: resonanceSets.append( atomSetGroup[i].findFirstResonanceSet()) else: resonanceSets.append(None) for i in range(0, 2): resonanceSet = resonanceSets[i] if resonanceSet: resonanceSet.addAtomSet(atomSetGroup[not i]) resonanceSet.removeAtomSet(atomSetGroup[i]) def apply(self): for chain in self.chainList: self.setStereo(chain=chain) return True
class RegionSelector(Frame): def __init__(self, parent, label='', world_region=None, view_region=None, orient=Tkinter.HORIZONTAL, allow_resize=True, width=20, callback=None, borderwidth=1, show_text=True, text_color='#000000', text_decimals=2, units_scroll=0.1, pages_scroll=1.0, menu_entries=None, menu_callback=None, min_thickness=None, *args, **kw): self.menu_entries = menu_entries self.myCallback = callback Frame.__init__(self, parent, *args, **kw) self.text_decimals = text_decimals self.label = Label(self, text=label, width=4) self.menu = PulldownMenu(self, callback=menu_callback, entries=menu_entries) self.entry = FloatEntry(self, width=6, returnCallback=self.adjustScrollbar) self.region_scrollbar = RegionScrollbar(self, world_region=world_region, view_region=view_region, orient=orient, allow_resize=allow_resize, width=width, callback=self.doCallback, borderwidth=borderwidth, show_text=show_text, text_color=text_color, text_decimals=text_decimals, units_scroll=units_scroll, pages_scroll=pages_scroll, min_thickness=min_thickness) self.gridAll() def gridAll(self): col = 0 if (self.menu_entries and len(self.menu_entries) > 1): self.menu.grid(row=0, column=col, sticky=Tkinter.EW) col = col + 1 else: self.menu.grid_forget() self.label.grid(row=0, column=col, sticky=Tkinter.EW) col = col + 1 self.entry.grid(row=0, column=col, sticky=Tkinter.EW) self.grid_columnconfigure(col, weight=0) col = col + 1 self.region_scrollbar.grid(row=0, column=col, sticky=Tkinter.NSEW) self.grid_columnconfigure(col, weight=1) col = col + 1 self.grid_columnconfigure(col, weight=0) def setMinThickness(self, min_thickness): self.region_scrollbar.setMinThickness(min_thickness) def setMenuEntries(self, menu_entries): self.menu_entries = menu_entries self.menu.replace(menu_entries) self.gridAll() def getMenuEntry(self): return self.menu.getSelected() def adjustScrollbar(self, *event): try: x = float(self.entry.get()) except: showError('Entry error', 'Need to enter float in scrollbar box') self.setEntry() return (v0, v1) = self.region_scrollbar.view_region d = 0.5 * (v1 - v0) self.region_scrollbar.setViewRegion(x - d, x + d, do_callback=True) def doCallback(self, view_region): if (self.myCallback): self.myCallback(view_region) #print 'doCallback', view_region self.setEntry(view_region) def setEntry(self, view_region=None): if (not view_region): view_region = self.region_scrollbar.view_region (v0, v1) = view_region x = 0.5 * (v0 + v1) s = formatDecimals(x, decimals=self.text_decimals) self.entry.set(s) def __getattr__(self, name): # dispatch everything not defined by RegionSelector to scrollbar widget try: return getattr(self.__dict__['region_scrollbar'], name) except: raise AttributeError, "RegionSelector instance has no attribute '%s'" % name
class SetupStructureCalcFrame(Frame): def __init__(self, parent, application, *args, **kw): self.parent = parent self.molSystem = None self.constraintSet = None self.application = application self.project = application.project self.waiting = False self.tableObj = None Frame.__init__(self, parent=parent, **kw) self.grid_columnconfigure(3, weight=1) label = Label(self, text='Molecular system: ') label.grid(row=0, column=0, sticky='nw') self.molSysPulldown = PulldownMenu( self, self.changeMolSystem, tipText='Select which molecular system to use in the calculation') self.molSysPulldown.grid(row=0, column=1, sticky='nw') label = Label(self, text='Constraint Set: ') label.grid(row=0, column=2, sticky='nw') self.constraintSetPulldown = PulldownMenu( self, self.changeConstraintSet, tipText='Select which set of restraints to use in the calculation') self.constraintSetPulldown.grid(row=0, column=3, sticky='nw') self.shiftListPulldown = PulldownMenu( parent, callback=self.setShiftList, do_initial_callback=False, tipText='select the shift list to use in the calculation') tipTexts = [ 'The type of ccp object used in the calculation', 'The identifier for the input data', 'A toggle whether to use the data', 'Whether to filter violated restraints', 'Whether to keep CCPN assignments (otherwise new restraint assignments will be used)', 'Whether the restraints are overly anbiguous and need refining', 'The shift list to use for shift-peak matching' ] headingList = [ 'Input Class', 'Id', 'Use?', 'Filter\nViolated', 'Keep\nAssignments?', 'Ambiguous\nProtocol', 'Shift List' ] editWidgets = [ None, None, None, None, None, None, self.shiftListPulldown ] editGetCallbacks = [ None, None, self.toggleUse, self.toggleFilterViol, self.toggleKeepAssign, self.toggleAmbig, self.getShiftList ] editSetCallbacks = [ None, None, None, None, None, None, self.setShiftList ] self.grid_rowconfigure(1, weight=1) self.scrolledMatrix = ScrolledMatrix(self, headingList=headingList, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, multiSelect=True, tipTexts=tipTexts, callback=self.selectCell) self.scrolledMatrix.grid(row=1, column=0, columnspan=4, sticky='nsew') self.scrolledMatrix.doEditMarkExtraRules = self.doEditMarkExtraRules #texts = ['','',''] #commands = [None,None,None] #self.bottomButtons = ButtonList(self, texts=texts, expands=True, commands=commands) #self.bottomButtons.grid(row=2, column=0, columnspan=4, sticky='ew') self.updateMolSystems() self.updateConstraintSets() notify = self.application.registerNotify for func in ('__init__', 'delete'): notify(self.updateAfter, 'ccp.nmr.Nmr.PeakList', func) notify(self.updateConstraintSets, 'ccp.nmr.NmrConstraint.NmrConstraintStore', func) notify(self.updateMolSystems, 'ccp.molecule.MolSystem.MolSystem', func) notify(self.updateMolSystems, 'ccp.molecule.MolSystem.Chain', func) for func in ('__init__', 'delete', 'setName'): notify(self.updateAfter, 'ccp.nmr.Nmr.Experiment', func) notify(self.updateAfter, 'ccp.nmr.Nmr.DataSource', func) def doEditMarkExtraRules(self, obj, row, col): className = obj.className if className == 'PeakList': if col == 5: return False elif className == 'DistanceConstraintList': if col in (4, 6): return False else: if col in (4, 5, 6): return False return True def toggleUse(self, obj): bool = not obj.setupStructureCalcFrameDict['use'] obj.setupStructureCalcFrameDict['use'] = bool self.updateAfter() def toggleFilterViol(self, obj): bool = not obj.setupStructureCalcFrameDict['filter'] obj.setupStructureCalcFrameDict['filter'] = bool self.updateAfter() def toggleKeepAssign(self, obj): bool = not obj.setupStructureCalcFrameDict['preserve'] obj.setupStructureCalcFrameDict['preserve'] = bool self.updateAfter() def toggleAmbig(self, obj): bool = not obj.setupStructureCalcFrameDict['ambig'] obj.setupStructureCalcFrameDict['ambig'] = bool self.updateAfter() def selectCell(self, obj, row, col): self.tableObj = obj def getShiftList(self, peakList): names = [] index = -1 shiftLists = getShiftLists(self.project.currentNmrProject) if shiftLists: shiftList = peakList.dataSource.experiment.shiftList if shiftList not in shiftLists: shiftList = shiftLists[0] names = [sl.name or str(sl.serial) for sl in shiftLists] index = shiftLists.index(shiftList) print "getShiftList", names, index self.shiftListPulldown.setup(names, index) def setShiftList(self, index, name=None): print "setShiftList", index, name if not name: index = self.shiftListPulldown.getSelectedIndex() shiftList = getShiftLists(self.project.currentNmrProject)[index] self.tableObj.setupStructureCalcFrameDict['shiftList'] = shiftList self.updateAfter() def updateMolSystems(self, *opt): names = [] index = -1 molSystems = self.getMolSystems() if molSystems: names = [ms.code for ms in molSystems] if self.molSystem not in molSystems: self.molSystem = molSystems[0] index = molSystems.index(self.molSystem) self.molSysPulldown.setup(names, index) def getMolSystems(self): molSystems = [] if self.project: for molSystem in self.project.molSystems: if molSystem.chains: molSystems.append(molSystem) return molSystems def getTableObjects(self): objs = [] if self.project: objs = getThroughSpacePeakLists(self.project) if self.constraintSet: objs.extend(list(self.constraintSet.constraintLists)) return objs def updateConstraintSets(self, obj=None): names = [] index = -1 if self.project and self.project.currentNmrProject: constraintSets = self.project.currentNmrProject.sortedNmrConstraintStores( ) if constraintSets: if self.constraintSet not in constraintSets: self.constraintSet = constraintSets[0] names = [str(cs.serial) for cs in constraintSets] index = constraintSets.index(self.constraintSet) names.append('<None>') self.constraintSetPulldown.setup(names, index) def changeMolSystem(self, i, name): self.molSystem = self.project.findFirstMolSystem(code=name) self.updateAfter() def changeConstraintSet(self, i, name): if name == '<None>': self.constraintSet = None else: self.constraintSet = self.project.currentNmrProject.sortedNmrConstraintStores( )[i] self.updateAfter() def update(self): textMatrix = [] objectList = [] #headingList = ['Input Class','Use?','Filter\nViolated', # 'Keep\nAssignments?','Ambigous\nProtocol','Shift List'] for obj in self.getTableObjects(): if not hasattr(obj, 'setupStructureCalcFrameDict'): obj.setupStructureCalcFrameDict = dict = {} dict['use'] = True dict['filter'] = True dict['preserve'] = False dict['ambig'] = False dict['shiftList'] = None new = True else: dict = obj.setupStructureCalcFrameDict new = False className = obj.className if className == 'PeakList': spectrum = obj.dataSource experiment = spectrum.experiment shiftList = dict['shiftList'] or experiment.shiftList if shiftList: shiftListName = shiftList.name else: shiftListName = '<None>' if new and (self.molSystem not in experiment.molSystems): dict['use'] = False ident = '%s:%s:%d' % (experiment.name, spectrum.name, obj.serial) used = dict['use'] and 'Yes' or 'No' filtered = dict['filter'] and 'Yes' or 'No' preserved = dict['preserve'] and 'Yes' or 'No' ambig = None elif className == 'DistanceConstraintList': shiftListName = None if new: dict['filter'] = True dict['ambig'] = False ident = '%s:%d' % (obj.name or '', obj.serial) used = dict['use'] and 'Yes' or 'No' filtered = dict['filter'] and 'Yes' or 'No' preserved = None ambig = dict['ambig'] and 'Yes' or 'No' else: shiftListName = None if new: dict['filter'] = False dict['ambig'] = False ident = '%s:%d' % (obj.name or '', obj.serial) used = dict['use'] and 'Yes' or 'No' filtered = None preserved = None ambig = None datum = [ className, ident, used, filtered, preserved, ambig, shiftListName ] textMatrix.append(datum) objectList.append(obj) self.waiting = False self.scrolledMatrix.update(textMatrix=textMatrix, objectList=objectList) def getAriaData(self): if not self.project: showWarning('Failure', 'No active project', parent=self) return if not self.molSystem: showWarning('Failure', 'No molecular system selected', parent=self) return if len(self.molSystem.chains) > 1: code = self.molSystem.findFirstChain().code code = askString('Multiple chains', 'Enter chain code:', code, parent=self) chain = self.molSystem.findFirstChain(code=code) else: chain = self.molSystem.findFirstChain() peakData = [] dihedrals = [] ambigs = [] unambigs = [] jCouplings = [] for obj in self.scrolledMatrix.objectList: opts = obj.setupStructureCalcFrameDict if not opts['use']: continue className = obj.className key = getObjectKeyString(obj) if className == 'PeakList': shiftList = opts['shiftList'] if not shiftList: continue datum = { 'shifts': { KEY_ID: getObjectKeyString(shiftList) }, 'peaks': { KEY_ID: key }, 'use_assignments': opts['preserve'], 'trust_assigned_peaks': opts['filter'] } peakData.append(datum) elif className == 'DistanceConstraintList': if opts['ambig']: ambigs.append({ KEY_ID: key, 'filter_contributions': opts['filter'] }) else: unambigs.append({ KEY_ID: key, 'filter_contributions': opts['filter'] }) elif className == 'JCouplingConstraintList': jCouplings.append({KEY_ID: key}) elif className == 'DihedralConstraintList': dihedrals.append({KEY_ID: key}) projFileName = os.path.join(self.project.url.path, self.project.path) dict = { KEY_GENERAL: { 'project_name': self.project.name }, KEY_CCPN: { 'filename': projFileName }, KEY_MOLECULAR_SYSTEM: { KEY_ID: getObjectKeyString(chain) }, KEY_NOES: peakData, KEY_DIHEDRALS: dihedrals, KEY_DISTANCES_AMBIG: ambigs, KEY_DISTANCES_UNAMBIG: unambigs, KEY_JCOUPLINGS: jCouplings } return dict def updateAll(self): self.project = self.application.project self.updateMolSystems() self.updateConstraintSets() self.updateAfter() def updateAfter(self, obj=None): if self.waiting: return else: self.waiting = True self.after_idle(self.update) def destroy(self): notify = self.application.unregisterNotify for func in ('__init__', 'delete'): notify(self.updateAfter, 'ccp.nmr.Nmr.PeakList', func) notify(self.updateConstraintSets, 'ccp.nmr.NmrConstraint.NmrConstraintStore', func) notify(self.updateMolSystems, 'ccp.molecule.MolSystem.MolSystem', func) notify(self.updateMolSystems, 'ccp.molecule.MolSystem.Chain', func) for func in ('__init__', 'delete', 'setName'): notify(self.updateAfter, 'ccp.nmr.Nmr.Experiment', func) notify(self.updateAfter, 'ccp.nmr.Nmr.DataSource', func) Frame.destroy(self)
class CloudsPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.project = parent.getProject() self.waiting = 0 self.specFreq = 800.13 self.maxIter = 50 self.mixTime = 60 self.corrTime = 11.5 self.leakRate = 2.0 self.peakListDict = {} self.noesyPeakList = None self.tocsyPeakList = None self.noesy3dPeakList = None self.hsqcPeakList = None self.maxIntens = 37000000 self.resonances = None self.origResonances = None self.noesyPeaks = None self.distanceConstraintList = None self.antiDistConstraintList = None self.numClouds = 100 self.filePrefix = 'cloud_' self.cloudsFiles = [] self.adcAtomTypes = 'HN' self.structure = None # step num, initial temp, final temp, cooling steps, MD steps, MD tau, rep scale self.coolingScheme = [] self.coolingScheme.append([1, 1, 1, 3, 500, 0.001, 0]) self.coolingScheme.append([2, 80000, 4000, 19, 1000, 0.001, 0]) self.coolingScheme.append([3, 4000, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([4, 15000, 1, 3, 1000, 0.001, 0]) self.coolingScheme.append([5, 1, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([6, 8000, 1, 3, 1000, 0.001, 0]) self.coolingScheme.append([7, 1, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([8, 3000, 25, 60, 2500, 0.001, 1]) self.coolingScheme.append([9, 25, 25, 1, 7500, 0.001, 1]) self.coolingScheme.append([10, 10, 10, 1, 7500, 0.001, 1]) self.coolingScheme.append([11, 0.01, 0.01, 1, 7500, 0.0005, 1]) self.coolingStep = None BasePopup.__init__(self, parent, title="Resonance Clouds Analysis", **kw) def body(self, guiFrame): self.specFreqEntry = IntEntry(self, text=self.specFreq, width=8, returnCallback=self.setSpecFreq) self.maxIterEntry = IntEntry(self, text=self.maxIter, width=8, returnCallback=self.setMaxIter) self.mixTimeEntry = FloatEntry(self, text=self.mixTime, width=8, returnCallback=self.setMixTime) self.corrTimeEntry = FloatEntry(self, text=self.corrTime, width=8, returnCallback=self.setCorrTime) self.leakRateEntry = FloatEntry(self, text=self.leakRate, width=8, returnCallback=self.setLeakRate) self.maxIntensEntry = IntEntry(self, text=self.maxIntens, width=8, returnCallback=self.setMaxIntens) self.mdInitTempEntry = FloatEntry(self, text='', returnCallback=self.setMdInitTemp) self.mdFinTempEntry = FloatEntry(self, text='', returnCallback=self.setMdFinTemp) self.mdCoolStepsEntry = IntEntry(self, text='', returnCallback=self.setMdCoolSteps) self.mdSimStepsEntry = IntEntry(self, text='', returnCallback=self.setMdSimSteps) self.mdTauEntry = FloatEntry(self, text='', returnCallback=self.setMdTau) self.mdRepScaleEntry = FloatEntry(self, text='', returnCallback=self.setMdRepScale) guiFrame.grid_columnconfigure(0, weight=1) row = 0 frame0 = LabelFrame(guiFrame, text='Setup peak lists') frame0.grid(row=row, column=0, sticky=Tkinter.NSEW) frame0.grid(row=row, column=0, sticky=Tkinter.NSEW) frame0.grid_columnconfigure(1, weight=1) f0row = 0 label00 = Label(frame0, text='1H-1H NOESY spectrum') label00.grid(row=f0row, column=0, sticky=Tkinter.NW) self.noesyPulldown = PulldownMenu(frame0, entries=self.getNoesys(), callback=self.setNoesy, selected_index=0, do_initial_callback=0) self.noesyPulldown.grid(row=f0row, column=1, sticky=Tkinter.NW) f0row += 1 label01 = Label(frame0, text='15N HSQC spectrum') label01.grid(row=f0row, column=0, sticky=Tkinter.NW) self.hsqcPulldown = PulldownMenu(frame0, entries=self.getHsqcs(), callback=self.setHsqc, selected_index=0, do_initial_callback=0) self.hsqcPulldown.grid(row=f0row, column=1, sticky=Tkinter.NW) f0row += 1 label02 = Label(frame0, text='15N HSQC TOCSY spectrum') label02.grid(row=f0row, column=0, sticky=Tkinter.NW) self.tocsyPulldown = PulldownMenu(frame0, entries=self.getTocsys(), callback=self.setTocsy, selected_index=0, do_initial_callback=0) self.tocsyPulldown.grid(row=f0row, column=1, sticky=Tkinter.NW) f0row += 1 label02 = Label(frame0, text='15N HSQC NOESY spectrum') label02.grid(row=f0row, column=0, sticky=Tkinter.NW) self.noesy3dPulldown = PulldownMenu(frame0, entries=self.getNoesy3ds(), callback=self.setNoesy3d, selected_index=0, do_initial_callback=0) self.noesy3dPulldown.grid(row=f0row, column=1, sticky=Tkinter.NW) f0row += 1 texts = ['Setup resonances & peaks', 'Show Peaks', 'Show resonances'] commands = [self.setupResonances, self.showPeaks, self.showResonances] self.setupButtons = ButtonList(frame0, expands=1, texts=texts, commands=commands) self.setupButtons.grid(row=f0row, column=0, columnspan=2, sticky=Tkinter.NSEW) f0row += 1 self.label03a = Label(frame0, text='Resonances found: 0') self.label03a.grid(row=f0row, column=0, sticky=Tkinter.NW) self.label03b = Label(frame0, text='NOESY peaks found: 0') self.label03b.grid(row=f0row, column=1, sticky=Tkinter.NW) row += 1 frame1 = LabelFrame(guiFrame, text='Calculate distance constraints') frame1.grid(row=row, column=0, sticky=Tkinter.NSEW) frame1.grid_columnconfigure(3, weight=1) f1row = 0 frame1.grid_rowconfigure(f1row, weight=1) data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate, self.maxIntens ] colHeadings = [ 'Spectrometer\nfrequency', 'Max\niterations', 'Mixing\ntime (ms)', 'Correl.\ntime (ns)', 'Leak\nrate', 'Max\nintensity' ] editWidgets = [ self.specFreqEntry, self.maxIterEntry, self.mixTimeEntry, self.corrTimeEntry, self.leakRateEntry, self.maxIntensEntry, ] editGetCallbacks = [ self.getSpecFreq, self.getMaxIter, self.getMixTime, self.getCorrTime, self.getLeakRate, self.getMaxIntens, ] editSetCallbacks = [ self.setSpecFreq, self.setMaxIter, self.setMixTime, self.setCorrTime, self.setLeakRate, self.setMaxIntens, ] self.midgeParamsMatrix = ScrolledMatrix( frame1, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, maxRows=1, initialCols=5, headingList=colHeadings, callback=None, objectList=[ 'None', ], textMatrix=[ data, ]) self.midgeParamsMatrix.grid(row=f1row, column=0, columnspan=4, sticky=Tkinter.NSEW) f1row += 1 label10 = Label(frame1, text='Benchmark structure') label10.grid(row=f1row, column=0, sticky=Tkinter.NW) self.structurePulldown = PulldownMenu(frame1, entries=self.getStructures(), callback=self.setStructure, selected_index=0, do_initial_callback=0) self.structurePulldown.grid(row=f1row, column=1, sticky=Tkinter.NW) label11 = Label(frame1, text='ADC atom types:') label11.grid(row=f1row, column=2, sticky=Tkinter.NW) self.adcAtomsPulldown = PulldownMenu(frame1, entries=self.getAdcAtomTypes(), callback=self.setAdcAtomTypes, selected_index=0, do_initial_callback=0) self.adcAtomsPulldown.grid(row=f1row, column=3, sticky=Tkinter.NW) f1row += 1 texts = [ 'Calculate distances', 'Show distance\nconstraints', 'Show anti-distance\nconstraints' ] commands = [ self.calculateDistances, self.showConstraints, self.showAntiConstraints ] self.midgeButtons = ButtonList(frame1, expands=1, texts=texts, commands=commands) self.midgeButtons.grid(row=f1row, column=0, columnspan=4, sticky=Tkinter.NSEW) f1row += 1 self.distConstrLabel = Label(frame1, text='Distance constraints:') self.distConstrLabel.grid(row=f1row, column=0, columnspan=2, sticky=Tkinter.NW) self.antiConstrLabel = Label(frame1, text='Anti-distance constraints:') self.antiConstrLabel.grid(row=f1row, column=2, columnspan=2, sticky=Tkinter.NW) row += 1 guiFrame.grid_rowconfigure(row, weight=1) frame2 = LabelFrame(guiFrame, text='Proton cloud molecular dynamics') frame2.grid(row=row, column=0, sticky=Tkinter.NSEW) frame2.grid_columnconfigure(1, weight=1) f2row = 0 frame2.grid_rowconfigure(f2row, weight=1) data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate ] colHeadings = [ 'Step', 'Initial temp.', 'Final temp.', 'Cooling steps', 'MD steps', 'MD tau', 'Rep. scale' ] editWidgets = [ None, self.mdInitTempEntry, self.mdFinTempEntry, self.mdCoolStepsEntry, self.mdSimStepsEntry, self.mdTauEntry, self.mdRepScaleEntry ] editGetCallbacks = [ None, self.getMdInitTemp, self.getMdFinTemp, self.getMdCoolSteps, self.getMdSimSteps, self.getMdTau, self.getMdRepScale ] editSetCallbacks = [ None, self.setMdInitTemp, self.setMdFinTemp, self.setMdCoolSteps, self.setMdSimSteps, self.setMdTau, self.setMdRepScale ] self.coolingSchemeMatrix = ScrolledMatrix( frame2, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, maxRows=9, initialRows=12, headingList=colHeadings, callback=self.selectCoolingStep, objectList=self.coolingScheme, textMatrix=self.coolingScheme) self.coolingSchemeMatrix.grid(row=f2row, column=0, columnspan=4, sticky=Tkinter.NSEW) f2row += 1 texts = ['Move earlier', 'Move later', 'Add step', 'Remove step'] commands = [ self.moveStepEarlier, self.moveStepLater, self.addCoolingStep, self.removeCoolingStep ] self.coolingSchemeButtons = ButtonList(frame2, expands=1, commands=commands, texts=texts) self.coolingSchemeButtons.grid(row=f2row, column=0, columnspan=4, sticky=Tkinter.EW) f2row += 1 label20 = Label(frame2, text='Number of clouds:') label20.grid(row=f2row, column=0, sticky=Tkinter.NW) self.numCloudsEntry = FloatEntry(frame2, text=100, returnCallback=self.setNumClouds, width=10) self.numCloudsEntry.grid(row=f2row, column=1, sticky=Tkinter.NW) label21 = Label(frame2, text='Cloud file prefix:') label21.grid(row=f2row, column=2, sticky=Tkinter.NW) self.filePrefixEntry = Entry(frame2, text='cloud_', returnCallback=self.setFilePrefix, width=10) self.filePrefixEntry.grid(row=f2row, column=3, sticky=Tkinter.NW) f2row += 1 texts = ['Start molecular dynamics', 'Show dynamics progress'] commands = [self.startMd, self.showMdProgress] self.mdButtons = ButtonList(frame2, expands=1, commands=commands, texts=texts) self.mdButtons.grid(row=f2row, column=0, columnspan=4, sticky=Tkinter.NSEW) row += 1 self.bottomButtons = createDismissHelpButtonList(guiFrame, expands=0, help_url=None) self.bottomButtons.grid(row=row, column=0, sticky=Tkinter.EW) self.setButtonStates() def getStructures(self): names = [ '<None>', ] for molSystem in self.project.sortedMolSystems(): for structure in molSystem.sortedStructureEnsembles(): names.append('%s:%d' % (molSystem.name, structure.ensembleId)) return names def setStructure(self, index, name=None): if index < 1: self.structure = None else: structures = [] for molSystem in self.project.molSystems: for structure in molSystem.structureEnsembles: structures.append(structure) self.structure = structures[index - 1] def getAdcAtomTypes(self): return ['HN', 'HN HA', 'HN HA HB'] def setAdcAtomTypes(self, index, name=None): if name is None: name = self.adcAtomsPulldown.getSelected() self.adcAtomTypes = name def startMd(self): self.setNumClouds() self.setFilePrefix() if (self.distanceConstraintList and self.antiDistConstraintList and (self.numClouds > 0) and self.filePrefix): resDict = {} for resonance in self.guiParent.project.currentNmrProject.resonances: resDict[resonance.serial] = resonance resonances = [] for constraint in self.distanceConstraintList.constraints: for item in constraint.items: for fixedResonance in item.resonances: if resDict.get( fixedResonance.resonanceSerial) is not None: resonances.append( resDict[fixedResonance.resonanceSerial]) resDict[fixedResonance.resonanceSerial] = None startMdProcess(self.numClouds, self.distanceConstraintList, resonances, self.coolingScheme, self.filePrefix) #structGen = self.distanceConstraintList.structureGeneration serials = [] for resonance in resonances: serials.append(resonance.serial) clouds = [] for i in range(self.numClouds): clouds.append('%s%3.3d.pdb' % (self.filePrefix, i)) self.guiParent.application.setValues( self.distanceConstraintList.nmrConstraintStore, 'clouds', values=clouds) self.guiParent.application.setValues( self.distanceConstraintList.nmrConstraintStore, 'cloudsResonances', values=serials) # do better than this check for creation def showMdProgress(self): n = 0 m = self.numClouds for i in range(m): pdbFileName = '%s%3.3d.pdb' % (self.filePrefix, i) if os.path.exists(pdbFileName): n += 1 p = n * 100 / float(m) text = 'Done %d of %d clouds (%1.2f)%%' % (n, m, p) showInfo('MD Progress', text) def setFilePrefix(self, text=None): if not text: text = self.filePrefixEntry.get() if text: self.filePrefix = text def setNumClouds(self, n=None, *event): if not n: n = self.numCloudsEntry.get() if n: self.numClouds = int(n) def calculateDistances(self): # setup normalisation factor intensityMax # self.maxIter # what if failure ? resDict = {} for resonance in self.project.currentNmrProject.resonances: resDict[resonance.serial] = resonance self.resonances = self.origResonances intensityFactors = [1.0 for x in range(len(self.resonances))] # optimiseRelaxation will remove unconstrained resonances self.distanceConstraintList = optimiseRelaxation( self.resonances, self.noesyPeaks, intensityMax=self.maxIntens, intensityFactors=intensityFactors, tmix=self.mixTime, sf=self.specFreq, tcor=self.corrTime, rleak=self.leakRate) constrainSpinSystems(self.distanceConstraintList) # for testing calculate distances from structure overrides any resonances: uses assigned ones #(self.distanceConstraintList, self.resonances) = self.cheatForTesting() #self.antiDistConstraintList = self.distanceConstraintList protonNumbs = {'CH3': 3, 'Haro': 2, 'HN': 1, 'H': 1} PI = 3.1415926535897931 GH = 2.6752e4 HB = 1.05459e-27 CONST = GH * GH * GH * GH * HB * HB tc = 1.0e-9 * self.corrTime wh = 2.0 * PI * self.specFreq * 1.0e6 j0 = CONST * tc j1 = CONST * tc / (1.0 + wh * wh * tc * tc) j2 = CONST * tc / (1.0 + 4.0 * wh * wh * tc * tc) #jself = 6.0*j2 + 3.0*j1 + j0 jcross = 6.0 * j2 - j0 if self.distanceConstraintList: constraintStore = self.distanceConstraintList.nmrConstraintStore dict = { 'HN': ['H'], 'HN HA': ['H', 'HA', 'HA1', 'HA2'], 'HN HA HB': ['H', 'HA', 'HA1', 'HA2', 'HB', 'HB2', 'HB3'] } self.antiDistConstraintList = makeNoeAdcs( self.resonances, self.noesyPeakList.dataSource, constraintStore, allowedAtomTypes=dict[self.adcAtomTypes]) if self.structure: N = len(self.resonances) sigmas = [[] for i in range(N)] for i in range(N): sigmas[i] = [0.0 for j in range(N)] for constraint in self.distanceConstraintList.constraints: resonances = list(constraint, findFirstItem().resonances) ri = resDict[resonances[0].resonanceSerial] rj = resDict[resonances[1].resonanceSerial] i = self.resonances.index(ri) j = self.resonances.index(rj) atomSets1 = list(ri.resonanceSet.atomSets) atomSets2 = list(rj.resonanceSet.atomSets) if atomSets1 == atomSets2: ass = list(atomSets1) atomSets1 = [ ass[0], ] atomSets2 = [ ass[-1], ] distance = getAtomSetsDistance(atomSets1, atomSets2, self.structure) r = distance * 1e-8 nhs = protonNumbs[rj.name] sigma = 0.1 * jcross * nhs / (r**6) sigmas[i][j] = sigma constraint.setDetails('Known Dist: %4.3f' % (distance)) #for constraint in self.antiDistConstraintList.constraints: # atomSets1 = list(resonances[0].resonanceSet.atomSets) # atomSets2 = list(resonances[1].resonanceSet.atomSets) # distance = getAtomSetsDistance(atomSets1, atomSets2, self.structure) # constraint.setDetails('Known Dist: %4.3f' % (distance)) fp = open('sigmas.out', 'w') for i in range(N - 1): for j in range(i + 1, N): if sigmas[i][j] != 0.0: fp.write('%3.1d %3.1d %9.2e\n' % (i, j, sigmas[i][j])) #fp.write('\n') fp.close() self.setButtonStates() def cheatForTesting(self, atomSelection='H'): """ Makes a perfect cloud from a structure. """ project = self.project structure = self.guiParent.argumentServer.getStructure() constraintStore = makeNmrConstraintStore(project) distConstraintList = NmrConstraint.DistanceConstraintList( constraintStore) chain = structure.findFirstCoodChain() structureGeneration.hydrogenResonances = [] molSystem = structure.molSystem atomSets = [] resonances = [] i = 0 for resonance in project.currentNmrProject.resonances: if resonance.isotopeCode == '1H': if resonance.resonanceSet: atomSet = resonance.resonanceSet.findFirstAtomSet() atom = atomSet.findFirstAtom() seqId = atom.residue.seqId if (seqId < 9) or (seqId > 78): continue if atom.residue.chain.molSystem is molSystem: if atomSelection == 'methyl': if len(atomSet.atoms) == 3: if atom.residue.ccpCode not in ('Ala', 'Val', 'Ile', 'Leu', 'Thr', 'Met'): continue elif atom.name != 'H': continue elif atomSelection == 'amide': if atom.name != 'H': continue if atom.name == 'H': resonance.name = 'HN' else: resonance.name = 'H' resonances.append(resonance) atomSets.append(list(resonance.resonanceSet.atomSets)) i += 1 print "Found %d atomSets" % (len(atomSets)) weight = 1 adcWeight = 1 constrDict = {} N = len(atomSets) for i in range(N - 1): atomSets0 = atomSets[i] residue0 = atomSets0[0].findFirstAtom().residue.seqId print "R", residue0 for j in range(i + 1, N): if j == i: continue atomSets1 = atomSets[j] dist = getAtomSetsDistance(atomSets0, atomSets1, structure) if not dist: continue if dist < 5.5: fixedResonance0 = getFixedResonance( constraintStore, resonances[i]) fixedResonance1 = getFixedResonance( constraintStore, resonances[j]) constrDict[i] = 1 constrDict[j] = 1 constraint = NmrConstraint.DistanceConstraint( distConstraintList, weight=weight, targetValue=dist, upperLimit=dist + (dist / 10), lowerLimit=dist - (dist / 10), error=dist / 5) item = NmrConstraint.DistanceConstraintItem( constraint, resonances=[fixedResonance0, fixedResonance1]) elif (atomSets1[0].findFirstAtom().name == 'H') and (atomSets0[0].findFirstAtom().name == 'H') and (dist > 7): #else: fixedResonance0 = getFixedResonance( constraintStore, resonances[i]) fixedResonance1 = getFixedResonance( constraintStore, resonances[j]) constrDict[i] = 1 constrDict[j] = 1 constraint = NmrConstraint.DistanceConstraint( distConstraintList, weight=adcWeight, targetValue=75, upperLimit=175, lowerLimit=5.0, error=94.5) item = NmrConstraint.DistanceConstraintItem( constraint, resonances=[fixedResonance0, fixedResonance1]) return (distConstraintList, resonances) def showConstraints(self): if self.distanceConstraintList: self.guiParent.browseConstraints( constraintList=self.distanceConstraintList) def showAntiConstraints(self): if self.antiDistConstraintList: self.guiParent.browseConstraints( constraintList=self.antiDistConstraintList) def showPeaks(self): self.guiParent.viewPeaks(peaks=self.noesyPeaks) def showResonances(self): pass #self.guiParent.viewResonances(resonances=self.resonances) def setupResonances(self): if self.noesyPeakList and self.noesy3dPeakList and self.tocsyPeakList and self.hsqcPeakList: disambiguateNoesyPeaks(self.noesyPeakList, self.noesy3dPeakList, self.tocsyPeakList, self.hsqcPeakList) (self.origResonances, self.noesyPeaks, null) = getCloudsResonanceList(self.guiParent.argumentServer, hsqcPeakList=self.hsqcPeakList, tocsy3dPeakList=self.tocsyPeakList, noesy2dPeakList=self.noesyPeakList) self.setButtonStates() def setButtonStates(self): if self.origResonances: self.label03a.set('Resonances found: %d' % (len(self.origResonances))) if self.noesyPeaks: self.label03b.set('NOESY peaks found: %d' % (len(self.noesyPeaks))) if self.noesyPeakList and self.tocsyPeakList and self.hsqcPeakList: self.setupButtons.buttons[0].enable() else: self.setupButtons.buttons[0].disable() if self.noesyPeaks: self.setupButtons.buttons[1].enable() else: self.setupButtons.buttons[1].disable() if self.origResonances: self.setupButtons.buttons[2].enable() else: self.setupButtons.buttons[2].disable() if self.noesyPeaks and self.origResonances: self.midgeButtons.buttons[0].enable() else: self.midgeButtons.buttons[0].disable() if self.distanceConstraintList: self.midgeButtons.buttons[1].enable() self.distConstrLabel.set( 'Distance constraints: %d' % len(self.distanceConstraintList.constraints)) else: self.distConstrLabel.set('Distance constraints:') self.midgeButtons.buttons[1].disable() if self.antiDistConstraintList: self.antiConstrLabel.set( 'Anti-distance constraints: %d' % len(self.antiDistConstraintList.constraints)) self.midgeButtons.buttons[2].enable() else: self.antiConstrLabel.set('Anti-distance constraints:') self.midgeButtons.buttons[2].disable() if (self.distanceConstraintList and self.antiDistConstraintList and (self.numClouds > 0) and self.filePrefix): self.mdButtons.buttons[0].enable() self.mdButtons.buttons[1].enable() else: self.mdButtons.buttons[0].disable() self.mdButtons.buttons[1].disable() def getNoesys(self): names = [] spectra = getSpectraByType(self.project, '2dNOESY') for spectrum in spectra: for peakList in spectrum.peakLists: name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict[name] = peakList if not self.noesyPeakList: self.noesyPeakList = peakList return names def setNoesy(self, index, name=None): if not name: name = self.noesyPulldown.getSelected() self.noesyPeakList = self.peakListDict[name] self.setButtonStates() def getTocsys(self): names = [] spectra = getSpectraByType(self.project, '3dTOCSY') for spectrum in spectra: for peakList in spectrum.peakLists: name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict[name] = peakList if not self.tocsyPeakList: self.tocsyPeakList = peakList return names def getNoesy3ds(self): names = [] spectra = getSpectraByType(self.project, '3dNOESY') for spectrum in spectra: for peakList in spectrum.peakLists: name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict[name] = peakList if not self.noesy3dPeakList: self.noesy3dPeakList = peakList return names def setTocsy(self, index, name=None): if not name: name = self.tocsyPulldown.getSelected() self.tocsyPeakList = self.peakListDict[name] self.setButtonStates() def setNoesy3d(self, index, name=None): if not name: name = self.noesy3dPulldown.getSelected() self.noesy3dPeakList = self.peakListDict[name] self.setButtonStates() def getHsqcs(self): names = [] spectra = getSpectraByType(self.project, 'HSQC') for spectrum in spectra: for peakList in spectrum.peakLists: name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict[name] = peakList if not self.hsqcPeakList: self.hsqcPeakList = peakList return names def setHsqc(self, index, name=None): if not name: name = self.hsqcPulldown.getSelected() self.hsqcPeakList = self.peakListDict[name] self.setButtonStates() def getMdInitTemp(self, coolingStep): self.mdInitTempEntry.set(coolingStep[1]) def getMdFinTemp(self, coolingStep): self.mdFinTempEntry.set(coolingStep[2]) def getMdCoolSteps(self, coolingStep): self.mdCoolStepsEntry.set(coolingStep[3]) def getMdSimSteps(self, coolingStep): self.mdSimStepsEntry.set(coolingStep[4]) def getMdTau(self, coolingStep): self.mdTauEntry.set(coolingStep[5]) def getMdRepScale(self, coolingStep): self.mdRepScaleEntry.set(coolingStep[6]) def setMdInitTemp(self, event): value = self.mdInitTempEntry.get() if value is not None: self.coolingStep[1] = value self.updateCoolingScheme() def setMdFinTemp(self, event): value = self.mdFinTempEntry.get() if value is not None: self.coolingStep[2] = value self.updateCoolingScheme() def setMdCoolSteps(self, event): value = self.mdCoolStepsEntry.get() if value is not None: self.coolingStep[3] = value self.updateCoolingScheme() def setMdSimSteps(self, event): value = self.mdSimStepsEntry.get() if value is not None: self.coolingStep[4] = value self.updateCoolingScheme() def setMdTau(self, event): value = self.mdTauEntry.get() if value is not None: self.coolingStep[5] = value self.updateCoolingScheme() def setMdRepScale(self, event): value = self.mdRepScaleEntry.get() if value is not None: self.coolingStep[6] = value self.updateCoolingScheme() def selectCoolingStep(self, object, row, col): self.coolingStep = object def moveStepEarlier(self): if self.coolingStep: i = self.coolingStep[0] - 1 if i > 0: coolingStep = self.coolingScheme[i - 1] coolingStep[0] = i + 1 self.coolingStep[0] = i self.coolingScheme[i - 1] = self.coolingStep self.coolingScheme[i] = coolingStep self.updateCoolingScheme() self.coolingSchemeMatrix.hilightObject(self.coolingStep) def moveStepLater(self): if self.coolingStep: i = self.coolingStep[0] - 1 if i < len(self.coolingScheme) - 1: coolingStep = self.coolingScheme[i + 1] coolingStep[0] = i + 1 self.coolingStep[0] = i + 2 self.coolingScheme[i + 1] = self.coolingStep self.coolingScheme[i] = coolingStep self.updateCoolingScheme() self.coolingSchemeMatrix.hilightObject(self.coolingStep) def addCoolingStep(self): i = len(self.coolingScheme) + 1 datum = [i, 3000, 100, 10, 2500, 0.001, 1] self.coolingScheme.append(datum) self.updateCoolingScheme() def removeCoolingStep(self): if self.coolingStep: coolingScheme = [] i = 0 for coolingStep in self.coolingScheme: if coolingStep is not self.coolingStep: i += 1 coolingStep[0] = i coolingScheme.append(coolingStep) self.coolingScheme = coolingScheme self.updateCoolingScheme() def updateCoolingScheme(self): objectList = self.coolingScheme textMatrix = self.coolingScheme self.coolingSchemeMatrix.update(objectList=objectList, textMatrix=textMatrix) def updateMidgeParams(self): data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate, self.maxIntens ] self.midgeParamsMatrix.update(textMatrix=[ data, ]) def getSpecFreq(self, obj): self.specFreqEntry.set(self.specFreq) def getMaxIter(self, obj): self.maxIterEntry.set(self.maxIter) def getMixTime(self, obj): self.mixTimeEntry.set(self.mixTime) def getCorrTime(self, obj): self.corrTimeEntry.set(self.corrTime) def getLeakRate(self, obj): self.leakRateEntry.set(self.leakRate) def getMaxIntens(self, obj): self.maxIntensEntry.set(self.maxIntens) def setSpecFreq(self, event): value = self.specFreqEntry.get() if value is not None: self.specFreq = value self.updateMidgeParams() def setMaxIter(self, event): value = self.maxIterEntry.get() if value is not None: self.maxIter = value self.updateMidgeParams() def setMixTime(self, event): value = self.mixTimeEntry.get() if value is not None: self.mixTime = value self.updateMidgeParams() def setCorrTime(self, event): value = self.corrTimeEntry.get() if value is not None: self.corrTime = value self.updateMidgeParams() def setLeakRate(self, event): value = self.leakRateEntry.get() if value is not None: self.leakRate = value self.updateMidgeParams() def setMaxIntens(self, event): value = self.maxIntensEntry.get() if value is not None: self.maxIntens = value self.updateMidgeParams() def destroy(self): BasePopup.destroy(self)
class EditSymmetryPopup(BasePopup): def __init__(self, parent, project): self.parent = parent self.project = project self.singleMolecule = True self.molSystem = None self.molecules = [] self.symmetrySet = None self.symmetryOp = None self.waiting = False BasePopup.__init__(self, parent=parent, title='Symmetry Operations') def body(self, guiFrame): guiFrame.grid_columnconfigure(0, weight=1) guiFrame.grid_rowconfigure(1, weight=1) frame = LabelFrame(guiFrame, text='Options') frame.grid(row=0, column=0, sticky='ew') frame.grid_columnconfigure(5, weight=1) label = Label(frame, text='MolSystem:') label.grid(row=0, column=0, sticky='w') self.molSystemPulldown = PulldownMenu(frame, callback=self.selectMolSystem) self.molSystemPulldown.grid(row=0, column=1, sticky='w') self.molLabel = Label(frame, text='Molecule:') self.molLabel.grid(row=0, column=2, sticky='w') self.moleculePulldown = PulldownMenu(frame, callback=self.selectMolecule) self.moleculePulldown.grid(row=0, column=3, sticky='w') label = Label(frame, text='Same Molecule Symmetry:') label.grid(row=0, column=4, sticky='w') self.molSelect = CheckButton(frame, callback=self.toggleSingleMolecule) self.molSelect.grid(row=0, column=5, sticky='w') self.molSelect.set(self.singleMolecule) frame = LabelFrame(guiFrame, text='Symmetry Operations') frame.grid(row=1, column=0, sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) self.symmCodePulldown = PulldownMenu(self, callback=self.setSymmCode, do_initial_callback=False) self.segLengthEntry = IntEntry(self, returnCallback=self.setSegLength, width=6) self.setChainMulti = MultiWidget(self, CheckButton, callback=self.setChains, minRows=0, useImages=False) self.setSegmentMulti = MultiWidget(self, IntEntry, callback=self.setSegments, minRows=0, useImages=False) editWidgets = [ None, self.symmCodePulldown, self.segLengthEntry, self.setChainMulti, self.setSegmentMulti ] editGetCallbacks = [ None, self.getSymmCode, self.getSegLength, self.getChains, self.getSegments ] editSetCallbacks = [ None, self.setSymmCode, self.setSegLength, self.setChains, self.setSegments ] headings = [ '#', 'Symmetry\nType', 'Segment\nLength', 'Chains', 'Segment\nPositions' ] self.symmetryMatrix = ScrolledMatrix(frame, headingList=headings, callback=self.selectSymmetry, editWidgets=editWidgets, editGetCallbacks=editGetCallbacks, editSetCallbacks=editSetCallbacks) self.symmetryMatrix.grid(row=0, column=0, sticky='nsew') texts = ['Add Symmetry Op', 'Remove Symmetrey Op'] commands = [self.addSymmOp, self.removeSymmOp] buttonList = createDismissHelpButtonList(guiFrame, texts=texts, commands=commands, expands=True) buttonList.grid(row=2, column=0, sticky='ew') self.updateMolSystems() self.updateMolecules() self.updateSymmetriesAfter() self.notify(self.registerNotify) def open(self): self.updateMolSystems() self.updateMolecules() self.updateSymmetriesAfter() BasePopup.open(self) def notify(self, notifyFunc): for func in ('__init__', 'delete', 'setSymmetryCode', 'setSegmentLength'): notifyFunc(self.updateSymmetriesAfter, 'molsim.Symmetry.Symmetry', func) for func in ('__init__', 'delete', 'setfirstSeqId'): notifyFunc(self.updateSymmetriesAfter, 'molsim.Symmetry.Segment', func) def getSymmCode(self, symmetryOp): """Get allowed symmetry operators from the model""" symmetryOpCodes = symmetryOp.parent.metaclass.container.getElement( 'SymmetryOpCode').enumeration index = 0 if symmetryOp.symmetryCode in symmetryOpCodes: index = symmetryOpCodes.index(symmetryOp.symmetryCode) self.symmCodePulldown.setup(symmetryOpCodes, index) def getSegLength(self, symmetryOp): if symmetryOp and symmetryOp.segmentLength: self.segLengthEntry.set(symmetryOp.segmentLength) def getChains(self, symmetryOp): chains = [] for chain in self.molSystem.chains: if chain.residues: if chain.molecule in self.molecules: chains.append(chain.code) chains.sort() values = [] for chain in chains: if symmetryOp.findFirstSegment(chainCode=chain): values.append(True) else: values.append(False) self.setChainMulti.set(values=values, options=chains) def getSegments(self, symmetryOp): values = [] names = [] if symmetryOp: for segment in symmetryOp.sortedSegments(): names.append(segment.chainCode) values.append(segment.firstSeqId) n = len(values) self.setSegmentMulti.maxRows = n self.setSegmentMulti.minRows = n self.setSegmentMulti.set(values=values, options=names) def setSymmCode(self, index, name=None): """Set the symmetry code as NCS,C2,C3,C4,C5,C6""" if self.symmetryOp: symmCode = self.symmCodePulldown.getSelected() self.symmetryOp.symmetryCode = symmCode def setSegLength(self, event): value = self.segLengthEntry.get() or 1 self.symmetryOp.segmentLength = value def setChains(self, obj): if self.symmetryOp and obj: codes = self.setChainMulti.options segment = self.symmetryOp.findFirstSegment() values = self.setChainMulti.get() if segment: seqId0 = segment.firstSeqId else: seqId0 = 1 for i in range(len(values)): segment = self.symmetryOp.findFirstSegment(chainCode=codes[i]) if segment and not values[i]: segment.delete() elif values[i] and not segment: chain = self.molSystem.findFirstChain(code=codes[i]) residue = chain.findFirstResidue(seqid=seqId0) if residue: seqId = seqId0 else: residue = chain.sortedResidues()[0] seqId = residue.seqId residue2 = chain.findFirstResidue( seqid=seqId + self.symmetryOp.segmentLength) if not residue2: residue2 = chain.sortedResidues()[-1] self.symmetryOp.segmentLength = (residue2.seqId - seqId) + 1 segment = self.symmetryOp.newSegment(chainCode=codes[i], firstSeqId=seqId) self.symmetryMatrix.keyPressEscape() def setSegments(self, obj): if self.symmetryOp and obj: segments = self.symmetryOp.sortedSegments() values = self.setSegmentMulti.get() for i in range(len(values)): seqCode = values[i] chain = self.molSystem.findFirstChain( code=segments[i].chainCode) residue = chain.findFirstResidue(seqCode=seqCode) if residue: seqId = residue.seqId if segments[i].firstSeqId != seqId: segments[i].delete() segments[i] = self.symmetryOp.newSegment( chainCode=chain.code, firstSeqId=seqId) self.symmetryMatrix.keyPressEscape() def selectSymmetry(self, obj, row, col): self.symmetryOp = obj def addSymmOp(self): if self.molSystem: if not self.symmetrySet: self.symmetrySet = self.molSystem.findFirstMolSystemSymmetrySet( ) if not self.symmetrySet: objGen = self.project.newMolSystemSymmetrySet self.symmetrySet = objGen(symmetrySetId=1, molSystem=self.molSystem) segLen = len(self.molSystem.findFirstChain().residues) symmetry = self.symmetrySet.newSymmetry(segmentLength=segLen) def removeSymmOp(self): if self.symmetryOp: self.symmetryOp.delete() def toggleSingleMolecule(self, boolean): self.singleMolecule = not boolean self.updateMolSystems() self.updateMolecules() def setMolecules(self, molecules): self.molecules = molecules if self.symmetrySet: for symmetryOp in self.symmetrySet.symmetries: for segment in symmetryOp.segments: chain = self.molSystem.findFirstChain( code=segment.chainCode) if chain and (chain.molecule not in molecules): segment.delete() def selectMolecule(self, index, name): self.setMolecules(self.getMolecules()[index]) self.updateSymmetries() def getMolecules(self): counts = {} moleculesList = [] for chain in self.molSystem.chains: molecule = chain.molecule counts[molecule] = counts.get(molecule, 0) + 1 molecules = counts.keys() if self.singleMolecule: for molecule in counts: if counts[molecule] > 1: moleculesList.append([ molecule, ]) elif molecules: molecules = counts.keys() n = len(molecules) moleculesList.append([ molecules[0], ]) if n > 1: moleculesList.append([ molecules[1], ]) moleculesList.append([molecules[0], molecules[1]]) if n > 2: moleculesList.append([ molecules[2], ]) moleculesList.append([molecules[1], molecules[2]]) moleculesList.append( [molecules[0], molecules[1], molecules[2]]) if n > 3: moleculesList.append([ molecules[3], ]) moleculesList.append([molecules[0], molecules[3]]) moleculesList.append([molecules[1], molecules[3]]) moleculesList.append([molecules[2], molecules[3]]) moleculesList.append( [molecules[0], molecules[1], molecules[3]]) moleculesList.append( [molecules[0], molecules[2], molecules[3]]) moleculesList.append( [molecules[1], molecules[2], molecules[3]]) moleculesList.append( [molecules[0], molecules[1], molecules[2], molecules[3]]) return moleculesList def updateMolecules(self): names = [] index = -1 moleculesList = self.getMolecules() if moleculesList: if self.molecules not in moleculesList: self.setMolecules(moleculesList[0]) self.symmetrySet = self.molSystem.findFirstMolSystemSymmetrySet( ) index = moleculesList.index(self.molecules) names = [] for molecules in moleculesList: names.append(','.join([mol.name for mol in molecules])) else: self.molecules = [] self.moleculePulldown.setup(names, index) def selectMolSystem(self, index, name): self.molSystem = self.getMolSystems()[index] self.symmetrySet = self.molSystem.findFirstMolSystemSymmetrySet() self.updateSymmetries() def getMolSystems(self): molSystems = [] for molSystem in self.project.sortedMolSystems(): n = len(molSystem.chains) if self.singleMolecule and (n > 1): molSystems.append(molSystem) elif n > 0: molSystems.append(molSystem) return molSystems def updateMolSystems(self): names = [] index = -1 molSystems = self.getMolSystems() if molSystems: if self.molSystem not in molSystems: self.molSystem = molSystems[0] index = molSystems.index(self.molSystem) names = [ms.code for ms in molSystems] else: self.molSystem = None self.molSystemPulldown.setup(names, index) def updateSymmetriesAfter(self, obj=None): if self.waiting: return else: self.waiting = True self.after_idle(self.updateSymmetries) def updateSymmetries(self): textMatrix = [] objectList = [] if self.symmetrySet: for symmetryOp in self.symmetrySet.symmetries: chains = [] segments = [] length = symmetryOp.segmentLength for segment in symmetryOp.sortedSegments(): code = segment.chainCode chain = self.molSystem.findFirstChain(code=code) if chain: chains.append(code) seqId = segment.firstSeqId residue1 = chain.findFirstResidue(seqId=seqId) residue2 = chain.findFirstResidue(seqId=seqId + length - 1) segments.append( '%s:%d-%d' % (code, residue1.seqCode, residue2.seqCode)) datum = [ symmetryOp.serial, symmetryOp.symmetryCode, length, '\n'.join(chains), '\n'.join(segments) ] objectList.append(symmetryOp) textMatrix.append(datum) self.symmetryMatrix.update(objectList=objectList, textMatrix=textMatrix) self.waiting = False def destroy(self): self.notify(self.unregisterNotify) BasePopup.destroy(self)
class FilterCloudsPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.structure = None self.name = None self.clouds = [] self.rmsds = [] self.names = [] self.atomTypes = None self.waiting = 0 BasePopup.__init__(self, parent=parent, title="Filter Clouds", **kw) def body(self, guiFrame): row = 0 guiFrame.grid_columnconfigure(3, weight=1) label = Label(guiFrame, text='Cloud file names:') label.grid(row=row, column=0, sticky=Tkinter.W) self.fileNameEntry = Entry(guiFrame, text='testHistone\d+.pdb', returnCallback=self.loadClouds) self.fileNameEntry.grid(row=row, column=1, sticky=Tkinter.W) strucLabel = Label(guiFrame, text='Comparison structure') strucLabel.grid(row=row, column=2, sticky=Tkinter.W) self.strucPulldown = PulldownMenu(guiFrame, entries=self.getStructures(), callback=self.setStructure, selected_index=0, do_initial_callback=0) self.strucPulldown.grid(row=row, column=3, sticky=Tkinter.W) row += 1 sdTolLabel = Label(guiFrame, text='Tolerance (SDs):') sdTolLabel.grid(row=row, column=0, sticky=Tkinter.W) self.sdToleranceEntry = FloatEntry(guiFrame, text=2.0, width=6) self.sdToleranceEntry.grid(row=row, column=1, stick=Tkinter.W) atomTypes = ['All', 'H', 'H HA', 'H HA HB'] label = Label(guiFrame, text='RMSD Atom Types:') label.grid(row=row, column=2, sticky=Tkinter.W) self.atomsPulldown = PulldownMenu(guiFrame, entries=atomTypes, callback=self.setAtomTypes, selected_index=0, do_initial_callback=0) self.atomsPulldown.grid(row=row, column=3, sticky=Tkinter.W) row += 1 guiFrame.grid_rowconfigure(row, weight=1) colHeadings = ['#', 'File name', 'RMSD to mean'] self.scrolledMatrix = ScrolledMatrix(guiFrame, initialRows=10, headingList=colHeadings, callback=self.selectCell, objectList=[], textMatrix=[ [], ], multiSelect=1) self.scrolledMatrix.grid(row=row, column=0, columnspan=4, sticky=Tkinter.NSEW) row += 1 texts = [ 'Load\nClouds', 'Align\nClouds', 'Calc\nRMSD', 'Make Cloud\nfrom structure', 'Remove', 'Remove\nbad' ] commands = [ self.loadClouds, self.alignClouds, self.calcRmsd, self.makeStrucCloud, self.deleteClouds, self.filterClouds ] self.bottomButtons = createDismissHelpButtonList( guiFrame, texts=texts, expands=1, commands=commands, help_url=self.help_url) self.bottomButtons.grid(row=row, column=0, columnspan=4, sticky=Tkinter.NSEW) self.update() def alignClouds(self): pattern = self.fileNameEntry.get() self.names = getFileNamesFromPattern(pattern, '.') self.clouds = getCloudsFromFile(self.names, self.guiParent.project) alignClouds(self.clouds, self.names) def loadClouds(self): pattern = self.fileNameEntry.get() self.names = getFileNamesFromPattern(pattern, '.') self.clouds = getCloudsFromFile(self.names, self.guiParent.project) self.name = None self.rmsds = [None for x in range(len(self.clouds))] self.updateAfter() def getStructures(self): names = [ '<None>', ] for molSystem in self.project.sortedMolSystems(): for structure in molSystem.sortedStructureEnsembles(): names.append('%s:%d' % (molSystem.name, structure.ensembleId)) return names def setStructure(self, index, name=None): if index < 1: self.structure = None else: structures = [] for molSystem in self.project.molSystems: for structure in molSystem.structures: structures.append(structure) self.structure = structures[index - 1] self.updateButtons() def setAtomTypes(self, index, name=None): self.atomTypes = atomTypeList[index] def filterClouds(self): if self.clouds: sdTolerance = self.sdToleranceEntry.get() or 2.0 keptClouds = [] meanRmsd = 0.0 N = 0 for rmsd in self.rmsds: meanRmsd += rmsd or 0.0 N += 1 if N > 0: meanRmsd /= float(N) sd = 0.0 for r in self.rmsds: rmsd = r or 0.0 sd += (rmsd - meanRmsd) * (rmsd - meanRmsd) if N > 0: sd /= float(N - 1) sd = sqrt(sd) print meanRmsd, '+/-', sd for i in range(len(self.clouds), 0, -1): rmsd = self.rmsds[i] if abs(rmsd - meanRmsd) > (sdTolerance * sd): self.rmsds.pop(i) self.names.pop(i) self.clouds.pop(i) #print 'Cloud %s is bad' % (cloud) self.updateAfter() def makeStrucCloud(self): if self.structure and self.clouds: pdbFileName = 'CloudForStructure.pdb' atomCoordList = [] atomCoordList0 = [] resDict = {} hmass = 25 resonances = self.clouds[0].keys() resonances2 = [] C = 0 for resonance in resonances: if resonance == 'rmsd': continue resonanceSet = resonance.resonanceSet if resonanceSet: i = list(resonanceSet.resonances).index(resonance) atomSet = list(resonance.resonanceSet.atomSets)[i] coords = getAtomSetCoords(atomSet, self.structure) coord = coords[0] atomCoordList.append([coord.x, coord.y, coord.z]) atomCoordList0.append([coord.x, coord.y, coord.z]) resonances2.append(resonance) C += 1 print len(atomCoordList) print len(resonances), len(resonances2) print "Generating Mean" cloudsList = [] for cloud in self.clouds: orderCloud = [] for resonance in resonances2: x, y, z = cloud.get(resonance) or (0.0, 0.0, 0.0) orderCloud.append([-x, -y, -z]) cloudsList.append(orderCloud) (meanCloud, cloudsList) = alignToMeanCloud(cloudsList) weights = [1.0 for x in atomCoordList] centerCoords(atomCoordList) print "init cen", getMeanCoords(atomCoordList) print "mean cen", getMeanCoords(meanCloud) print "Print aligning struct clouds to mean", len(meanCloud), len( atomCoordList), len(weights) atomCoordsList, error, rotMat = alignCoordinates( meanCloud, atomCoordList, weights) print " Rotation", rotMat writeTypedPdbCloud(atomCoordList, pdbFileName, resonances2) print "Getting centres" oldCentre = getMeanCoords(atomCoordList0) newCentre = getMeanCoords(atomCoordList) delta = [ newCentre[i] - oldCentre[i] for i in range(len(oldCentre)) ] print " New centre", newCentre print " Old centre", oldCentre print " Delta", delta #inverseRot = inverseMatrix(rotMat) model = self.structure.findFirstModel() coordinates = model.coordinates offset = 0 iis = (0, 1, 2) for atom in self.structure.orderedAtoms: next = offset + 3 coords = [coordinates[offset + ii] + delta[ii] for ii in iis] coords = matrixVecMultiply(rotMat, coords) coordinates[offset:next] = coords offset = next model.setSubmatrixData('coordinates', coordinates) clouds = getCloudsFromFile([ pdbFileName, ], self.structure.root) self.clouds.append(clouds[0]) self.rmsds.append(None) self.names.append(pdbFileName) self.updateAfter() def calcRmsd(self): if self.clouds: if len(self.scrolledMatrix.currentObjects) < 2: clouds = self.clouds else: clouds = [] for name in self.scrolledMatrix.currentObjects: clouds.append(self.clouds[self.names.index(name)]) self.rmsds = filterClouds(clouds, atomTypes=self.atomTypes) self.updateAfter() def deleteClouds(self): if self.names and self.name and showOkCancel( 'Confirm', 'Really remove selected clouds?'): indices = [] for name in self.scrolledMatrix.currentObjects: i = self.names.index(name) indices.append(i) indices.sort() indices.reverse() for i in indices: self.clouds.pop(i) self.rmsds.pop(i) self.names.pop(i) self.name = None self.updateAfter() def selectCell(self, name, row, col): self.name = name self.updateButtons() def updateAfter(self, *opt): if self.waiting: return else: self.waiting = 1 self.after_idle(self.update) def destroy(self): BasePopup.destroy(self) def updateButtons(self): if self.names: self.bottomButtons.buttons[1].enable() self.bottomButtons.buttons[2].enable() self.bottomButtons.buttons[5].enable() else: self.bottomButtons.buttons[1].disable() self.bottomButtons.buttons[2].enable() self.bottomButtons.buttons[5].disable() if self.name: self.bottomButtons.buttons[4].enable() else: self.bottomButtons.buttons[4].disable() if self.structure and self.clouds: self.bottomButtons.buttons[3].enable() else: self.bottomButtons.buttons[3].disable() def update(self): textMatrix = [] objectList = self.names self.updateButtons() i = 0 for name in objectList: datum = [] datum.append(i + 1) datum.append(name) datum.append(self.rmsds[i]) textMatrix.append(datum) i += 1 if not objectList: textMatrix = [ [], ] self.scrolledMatrix.update(objectList=objectList, textMatrix=textMatrix) self.waiting = 0
class ConfirmSeqSpinSystemsPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.spinSystems = [] self.spectrum = None self.spectra = [] self.waiting = 0 self.shiftList = None self.spinSystem = None self.link = '-1' BasePopup.__init__(self, parent=parent, title="Confirm Sequential Spin System", **kw) def body(self, guiFrame): guiFrame.grid_columnconfigure(0, weight=1) row = 0 frame = Frame(guiFrame) frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(3, weight=1) label = Label(frame, text='Shift List:') label.grid(row=0, column=0, sticky='w') self.shiftListPulldown = PulldownMenu(frame, callback=self.setShiftList) self.shiftListPulldown.grid(row=0, column=1, sticky='w') label = Label(frame, text='Sequential Link Type:') label.grid(row=0, column=2, sticky='w') entries = ['-1', '-1,+1', '+1'] self.linkPulldown = PulldownMenu(frame, callback=self.setLink, entries=entries, do_initial_callback=False, selected_index=entries.index( self.link)) self.linkPulldown.grid(row=0, column=3, sticky='w') row += 1 frame = LabelFrame(guiFrame, text='Link Atoms:') frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) labels = ['C', 'CA', 'CB', 'CG', 'CD', 'H', 'HA', 'HB', 'HG', 'HD'] selected = ['CA', 'CB'] self.atomSelector = PartitionedSelector(frame, objects=labels, labels=labels, selected=selected, toggledBg='#808080', callback=self.changeAtoms, maxRowObjects=10) self.atomSelector.grid(row=0, column=0, sticky='ew') row += 1 guiFrame.grid_rowconfigure(row, weight=1) frame = LabelFrame(guiFrame, text='Predicted Residue Assignments') frame.grid(row=row, column=0, sticky='nsew') frame.grid_columnconfigure(0, weight=1) frame.grid_rowconfigure(0, weight=1) headingList = [ '#', 'Predicted\nResidue', 'Prob.', 'Links', 'CA', 'CA -1', 'CB', 'CB -1' ] self.spinSystemMatrix = ScrolledMatrix(frame, headingList=headingList, callback=self.selectSpinSystem, multiSelect=1) self.spinSystemMatrix.grid(row=0, column=0, sticky='nsew') row += 1 texts = ['Link Selected', 'Link All', 'Commit Assignment'] commands = [ self.linkSelectedSpinSystems, self.linkAllSpinSystems, self.commitAssignments ] buttonList = UtilityButtonList(guiFrame, texts=texts, commands=commands, helpUrl=self.help_url) buttonList.grid(row=row, column=0, sticky='ew') self.buttons = buttonList.buttons for func in ('__init__', 'delete'): for clazz in ('ccp.nmr.Nmr.ShiftList', ): self.registerNotify(self.updateShiftLists, clazz, func) for func in ('__init__', 'delete', 'setNmrChains', 'setResidue', 'setResonances', 'addResonance', 'removeResonance'): self.registerNotify(self.updateSpinSystemsAfter, 'ccp.nmr.Nmr.ResonanceGroup', func) self.updateShiftLists() def setLink(self, index, name): self.link = name self.updateSpinSystemsAfter() def updateButtons(self): if len(self.spinSystemMatrix.currentObjects) > 1: self.buttons[0].enable() else: self.buttons[0].disable() if self.spinSystemMatrix.objectList: self.buttons[1].enable() else: self.buttons[1].disable() if self.spinSystem: self.buttons[2].enable() else: self.buttons[2].disable() def changeAtoms(self, *opt): self.updateSpinSystemsAfter() def getShiftListNames(self, shiftLists): shiftListNames = [] for shiftList in shiftLists: if not hasattr(shiftList, 'name'): shiftList.name = "ShiftList " + str(shiftList.serial) elif not shiftList.name: shiftList.name = "ShiftList " + str(shiftList.serial) shiftListNames.append(shiftList.name) return shiftListNames def updateShiftLists(self, *opt): shiftLists = list( self.nmrProject.findAllMeasurementLists(className='ShiftList')) shiftListNames = self.getShiftListNames(shiftLists) shiftList = None index = -1 if shiftListNames: if self.shiftList in shiftLists: shiftList = self.shiftList else: shiftList = shiftLists[0] index = shiftLists.index(shiftList) self.shiftList = shiftList self.shiftListPulldown.setup(shiftListNames, index) def setShiftList(self, index, name=None): shiftLists = list( self.nmrProject.findAllMeasurementLists(className='ShiftList')) if shiftLists: self.shiftList = shiftLists[index] else: self.shiftList = None self.updateSpinSystemsAfter() def linkSelectedSpinSystems(self): spinSystems = self.spinSystemMatrix.currentObjects self.linkSpinSystems(spinSystems) def linkAllSpinSystems(self): spinSystems = self.spinSystemMatrix.objectList self.linkSpinSystems(spinSystems) def linkSpinSystems(self, spinSystems): data = [] for spinSystem in spinSystems: residue, p = self.getProbableResidue(spinSystem) key = '%s%s%4.4d' % (residue.chain.molSystem.code, residue.chain.code, residue.seqCode) data.append([key, residue.seqCode, residue, spinSystem]) data.sort() seqCodes = [x[1] for x in data] residues = [x[2] for x in data] spinSystems = [x[3] for x in data] N = len(data) for i in range(N): if i > 0: delta = seqCodes[i] - seqCodes[i - 1] if delta == 1 and (residues[i].chain is residues[i - 1].chain): ss = findConnectedSpinSystem(spinSystems[i], delta=-1) if ss: mergeSpinSystems( ss, spinSystems[i - 1]) # copy resonances across & delete makeSeqSpinSystemLink(spinSystems[i - 1], spinSystems[i], delta=1) if i < N - 1: delta = seqCodes[i + 1] - seqCodes[i] if delta == 1 and (residues[i].chain is residues[i + 1].chain): ss = findConnectedSpinSystem(spinSystems[i], delta=1) if ss: mergeSpinSystems( ss, spinSystems[i + 1]) # copy resonances across & delete makeSeqSpinSystemLink(spinSystems[i], spinSystems[i + 1], delta=1) self.updateSpinSystemsAfter() def commitAssignments(self): merge = showYesNo('Query', 'Merge with any existing spin systems?', self) for spinSystem in self.spinSystemMatrix.currentObjects: if not spinSystem.residue: residue, p = self.getProbableResidue(spinSystem) assignSpinSystemResidue(spinSystem, residue, warnMerge=merge) def getProbableResidue(self, spinSystem): residue = None probability = 0.0 if spinSystem.residue: return spinSystem.residue, 1.0 data = [] for residueProb in spinSystem.residueProbs: data.append((residueProb.weight, residueProb.possibility)) data.sort() if data: residue, probability = data[-1] return residue, probability def getTentativeSpinSystems(self): spinSystemsList = [] if self.project: for spinSystem in self.nmrProject.sortedResonanceGroups(): if spinSystem.residueProbs and not spinSystem.residue: #if spinSystem.residue: residue, p = self.getProbableResidue(spinSystem) key = '%s%s%4.4d' % (residue.chain.molSystem.code, residue.chain.code, residue.seqCode) spinSystemsList.append((key, spinSystem)) spinSystemsList.sort() return [x[1] for x in spinSystemsList] def updateSpinSystemsAfter(self, spinSystem=None): if self.waiting: return else: if spinSystem: if not spinSystem.residueProbs: return if spinSystem.residue: return self.waiting = True self.after_idle(self.updateSpinSystems) def getHeadings(self): headingList = ['#', 'Predicted\nResidue', 'Prob.', 'Links'] atoms = self.atomSelector.getSelected() for atom in atoms: headingList.append(atom) if self.link == '-1': headingList.append('%s -1' % atom) headingList.append('D %s -1' % atom) elif self.link == '+1': headingList.append('%s +1' % atom) headingList.append('D %s +1' % atom) else: headingList.append('%s -1' % atom) headingList.append('D %s -1' % atom) headingList.append('%s +1' % atom) headingList.append('D %s +1' % atom) return headingList def addShiftData(self, spinSystem, datum): prevSS, nextSS = self.getConnectedSpinSystems(spinSystem) atoms = self.atomSelector.getSelected() dict = {} residue, p = self.getProbableResidue(spinSystem) prevRes = residue.chain.findFirstResidue(seqCode=residue.seqCode - 1) nextRes = residue.chain.findFirstResidue(seqCode=residue.seqCode + 1) prevSS0 = None nextSS0 = None for ss in self.getTentativeSpinSystems(): if self.getProbableResidue(ss)[0] is prevRes: prevSS0 = ss if self.getProbableResidue(ss)[0] is nextRes: nextSS0 = ss if nextSS0 and prevSS0: break for atom in atoms: resonances = [] resonancesPrev = [] resonancesNext = [] resonancesPrev0 = [] resonancesNext0 = [] for resonance0 in spinSystem.sortedResonances(): for name in resonance0.assignNames: if name[:2] == atom: resonances.append(resonance0) break text = '' if resonances: text = self.getResonanceText(resonances) datum.append(text) if prevSS and ('-1' in self.link): for resonance0 in prevSS.sortedResonances(): for name in resonance0.assignNames: if name[:2] == atom: resonancesPrev.append(resonance0) break deltasPrev = [] if prevSS0 and resonancesPrev: for resonance1 in prevSS0.sortedResonances(): for name1 in resonance1.assignNames: if name1[:2] == atom: shift1 = resonance1.findFirstShift( parentList=self.shiftList) deltas = [] for resonance2 in resonancesPrev: shift2 = resonance2.findFirstShift( parentList=self.shiftList) if shift1 and shift2: deltas.append( abs(shift1.value - shift2.value)) if deltas: deltas.sort() deltasPrev.append('%.2f' % deltas[0]) break if nextSS and ('+1' in self.link): for resonance0 in nextSS.sortedResonances(): for name in resonance0.assignNames: if name[:2] == atom: resonancesNext.append(resonance0) break deltasNext = [] if nextSS0 and resonancesNext: for resonance1 in nextSS0.sortedResonances(): for name1 in resonance1.assignNames: if name1[:2] == atom: shift1 = resonance1.findFirstShift( parentList=self.shiftList) deltas = [] for resonance2 in resonancesNext: shift2 = resonance2.findFirstShift( parentList=self.shiftList) if shift1 and shift2: deltas.append( abs(shift1.value - shift2.value)) if deltas: deltas.sort() deltasNext.append('%.2f' % deltas[0]) break if self.link == '-1': ppms = '' diff = '' if resonancesPrev: ppms = self.getResonanceText(resonancesPrev) diff = ','.join(deltasPrev) datum.append(ppms) datum.append(diff) elif self.link == '+1': ppms = '' diff = '' if resonancesNext: ppms = self.getResonanceText(resonancesNext) diff = ','.join(deltasNext) datum.append(ppms) datum.append(diff) else: ppms = '' diff = '' if resonancesPrev: ppms = self.getResonanceText(resonancesPrev) diff = ','.join(deltasPrev) datum.append(ppms) datum.append(diff) ppms = '' diff = '' if resonancesNext: ppms = self.getResonanceText(resonancesNext) diff = ','.join(deltasNext) datum.append(ppms) datum.append(diff) def updateSpinSystems(self): textMatrix = [] objectList = [] colorMatrix = [] headingList = self.getHeadings() for spinSystem in self.getTentativeSpinSystems(): residueText = None residue, probability = self.getProbableResidue(spinSystem) if residue: residueText = '%d%s' % (residue.seqCode, getResidueCode(residue)) links = [] color = '#D04040' if findConnectedSpinSystem(spinSystem, delta=-1): links.append('-1') if findConnectedSpinSystem(spinSystem, delta=1): links.append('+1') if len(links) == 2: color = '#40B040' elif len(links) == 1: color = '#B0B040' datum = [] datum.append(spinSystem.serial) datum.append(residueText) datum.append(probability) datum.append(' '.join(links)) self.addShiftData(spinSystem, datum) colors = [None] * len(headingList) colors[3] = color objectList.append(spinSystem) textMatrix.append(datum) colorMatrix.append(colors) if self.spinSystem not in objectList: self.spinSystem = None self.spinSystemMatrix.update(headingList=headingList, objectList=objectList, textMatrix=textMatrix, colorMatrix=colorMatrix) self.updateButtons() self.waiting = False def getResonanceText(self, resonances): shifts = [] for resonance in resonances: shift = resonance.findFirstShift(parentList=self.shiftList) if shift: shifts.append('%.2f' % shift.value) return ','.join(shifts) def getConnectedSpinSystems(self, spinSystem): if self.link == '-1': prevSS = findConnectedSpinSystem(spinSystem, delta=-1) nextSS = None elif self.link == '+1': prevSS = None nextSS = findConnectedSpinSystem(spinSystem, delta=1) else: prevSS = findConnectedSpinSystem(spinSystem, delta=-1) nextSS = findConnectedSpinSystem(spinSystem, delta=1) return prevSS, nextSS def selectSpinSystem(self, object, row, col): self.spinSystem = object self.updateButtons() def destroy(self): for func in ('__init__', 'delete'): for clazz in ('ccp.nmr.Nmr.ShiftList', ): self.unregisterNotify(self.updateShiftLists, clazz, func) for func in ('__init__', 'delete', 'setNmrChains', 'setResidue', 'setResonances', 'addResonance', 'removeResonance'): self.unregisterNotify(self.updateSpinSystemsAfter, 'ccp.nmr.Nmr.ResonanceGroup', func) BasePopup.destroy(self)
class AutoAssignIOCyclePopup(BasePopup): help_url = joinPath(getHelpUrlDir(), 'AutoAssignIOCycle.html') def __init__(self, parent, project): self.project = project self.guiParent = parent self.autoAssignFormat = AutoAssignFormat(project, guiParent=parent) self.format = 'autoAssign' self.chainStampSep = '-' self.dateTimeFlag = time.strftime("%Y%m%d.%H:%M") self.getPreviousDateTimeStamps() self.getChainsAndChainStamps() self.importFileName = self.exportFileName = None BasePopup.__init__(self, parent=parent, title="Project '%s': " % project.name + 'AutoAssign export/import cycle.', modal=True, transient=True) def getPreviousDateTimeStamps(self): self.dateTimeStamps = [] appData = self.project.findAllApplicationData(application=self.format, keyword=dateTimeStamp_kw) for appDatum in appData: self.dateTimeStamps.append(appDatum.value) def getChainsAndChainStamps(self): self.chains = [] self.chainDateTimeStamps = [] self.chainDateTimeStampDict = {} for molSys in self.project.sortedMolSystems(): for chain in molSys.sortedChains(): self.chains.append(chain) appData = chain.findFirstApplicationData( application=self.format, keyword=dateTimeStamp_kw) if appData and appData.value in self.dateTimeStamps: (tlist, tdict) = createSelection([chain]) cdtsTag = "%s%s%s" % (tlist[0], self.chainStampSep, appData.value) self.chainDateTimeStamps.append(cdtsTag) self.chainDateTimeStampDict[cdtsTag] = chain def body(self, master): self.geometry('600x400') # # Quick check # if not self.chains: showError("No chains", "No chains available - cannot use export/import cycle.") self.destroy() # # Set it all up # columnspan = 2 row = 0 label = Label(master, text="AutoAssign export/import cycle.") label.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) row += 1 label = Label( master, fg='red', text= "Popup to export %s data from the CCPN data model,\nrun %s, then re-import the output." % (self.format, self.format)) label.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) # # Make a break... # row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) # # Set up export file info # row += 1 label = Label(master, text="Export menu (using date/time label '%s')" % self.dateTimeFlag) label.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) row += 1 (chainList, self.chainDict) = createSelection(self.chains) label = Label(master, text="Select chain to export:") label.grid(row=row, column=0, sticky=Tkinter.W) self.chainSelect = PulldownMenu(master, entries=chainList) self.chainSelect.grid(row=row, column=1, sticky=Tkinter.W) row += 1 label = Label(master, text="Export %s project file:" % self.format) label.grid(row=row, column=0, sticky=Tkinter.W) self.selectExportFileButton = Tkinter.Button( master, text='Select export file', command=(lambda: self.selectExportProjectFile())) self.selectExportFileButton.grid(row=row, column=1, sticky=Tkinter.W) row += 1 self.exportButton = Tkinter.Button(master, text='Export', command=(lambda: self.doExport())) self.exportButton.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) # # Make a break... # row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) # # Set up import file info # row += 1 label = Label(master, text="Re-import menu") label.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) row += 1 # # Select the right chain with the right date/time flag... # label = Label(master, text="Select chain with correct date/time flag:") label.grid(row=row, column=0, sticky=Tkinter.W) self.chainDateTimeSelect = PulldownMenu( master, entries=self.chainDateTimeStamps) self.chainDateTimeSelect.grid(row=row, column=1, sticky=Tkinter.W) # TODO UPDATE THIS WHEN EXPORT BUTTON PRESSED AND GETTING OK FROM EXPORT ITSELF! # Probably also need just a message if no importDateTimeStamp available... row += 1 label = Label(master, text="Import %s output file:" % self.format) label.grid(row=row, column=0, sticky=Tkinter.W) self.selectImportFileButton = Tkinter.Button( master, text='Select import file', command=(lambda: self.selectImportShiftFile())) self.selectImportFileButton.grid(row=row, column=1, sticky=Tkinter.W) row += 1 self.importButton = Tkinter.Button(master, text='Import', command=(lambda: self.doImport())) self.importButton.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) # # Make a break... # row += 1 separator = Separator(master, height=3) separator.setColor('black', bgColor='black') separator.grid(row=row, column=0, columnspan=columnspan, sticky=Tkinter.EW) row += 1 buttons = createDismissHelpButtonList(master, texts=[], commands=[], help_url=self.help_url) buttons.grid(row=row, columnspan=columnspan, column=0) def selectExportProjectFile(self): if self.exportFileName: fileName = self.exportFileName else: fileName = 'table.aat' popup = FormatFilePopup( self, file=fileName, component='project', format=self.format, title='Select name for %s project file to export.' % self.format) if popup.fileSelected: self.selectExportFileButton.config(text=popup.file) self.exportFileName = popup.file def selectImportShiftFile(self): if self.exportFileName: fileName = self.exportFileName else: fileName = 'autoAssign.out' popup = FormatFilePopup( self, file=fileName, component='shifts', format=self.format, title='Select name for %s output file to re-import.' % self.format) if popup.fileSelected: self.selectImportFileButton.config(text=popup.file) self.importFileName = popup.file def doExport(self): if self.exportFileName: chain = self.chainDict[self.chainSelect.getSelected()] returnValue = self.autoAssignFormat.writeProject( self.exportFileName, chain=chain, setTag=self.dateTimeFlag) if not returnValue: showError( "No export file written", "There were problems while exporting the %s project file." % self.format) else: showInfo("File written", "File written successfully") cdtsTag = "%s-%s" % (self.chainSelect.getSelected(), self.dateTimeFlag) if not cdtsTag in self.chainDateTimeSelect.entries: if "<None>" in self.chainDateTimeSelect.entries: self.chainDateTimeSelect.entries.pop( self.chainDateTimeSelect.entries.index("<None>")) self.chainDateTimeSelect.replace( [cdtsTag] + self.chainDateTimeSelect.entries) self.chainDateTimeStampDict[cdtsTag] = chain else: showError( "No export file defined", "Please define a name for the %s project file to export to." % self.format) def doImport(self): if self.importFileName: cdtsTag = self.chainDateTimeSelect.getSelected() if not self.chainDateTimeStampDict.has_key(cdtsTag): showError( "No import tag defined", "No chain with date/time stamp defined - cannot re-import." ) else: chain = self.chainDateTimeStampDict[cdtsTag] (chainText, curDateTimeStamp) = cdtsTag.split(self.chainStampSep) # # Get relevant info from data model (not immediately necessary but as example) # # Note that could in principle use the normal peakNum tag, but dangerous in case # multiple exports were done... this is more laborious though. # peakLists = [] rootPeakListTag = str((curDateTimeStamp, 'isRoot')) rootPeakNumToPeak = {} for nmrExp in self.project.currentNmrProject.sortedExperiments( ): for ds in nmrExp.sortedDataSources(): for peakList in ds.sortedPeakLists(): appData = peakList.findAllApplicationData( application=self.format, keyword=dateTimeStamp_kw) for appDatum in appData: if appDatum and appDatum.value == curDateTimeStamp: peakLists.append(peakList) if peakList.findFirstApplicationData( application=self.format, keyword=ioCycleTag_kw, value=rootPeakListTag): for peak in peakList.sortedPeaks(): appData = peak.findFirstApplicationData( application=self.format, keyword=ioCycleTag_kw) if appData: (curTag, peakNum) = eval(appData.value) if curTag == curDateTimeStamp: rootPeakNumToPeak[ peakNum] = peak # # Now get the actual chemical shift info from the AutoAssign output file # autoAssignChemShiftFile = AutoAssignChemShiftFile( self.importFileName) autoAssignChemShiftFile.read() # # Set the mapping between the chain residues and the seqCode in the chem shift file # residues = list(chain.sortedResidues()) seqCodeToResidue = {} for i in range(0, len(residues)): residue = residues[i] (seqCode, code1Letter) = autoAssignChemShiftFile.seqCodes[i] seqCode = returnInt(seqCode) seqCodeToResidue[seqCode] = residue for rawChemShift in autoAssignChemShiftFile.chemShifts: peak = None residue = None prevResidue = None seqCode = rawChemShift.seqCode atomName = rawChemShift.atomName #allValues = rawChemShift.allValues #rawChemShift.spinSystemId if seqCodeToResidue.has_key(seqCode): residue = seqCodeToResidue[seqCode] else: # THIS SHOULD NEVER HAPPEN! print " Error: no match for seqCode %d while re-importing project." % seqCode continue # # Set info on residue/atom level # atom = self.findMatchingAtom(residue, atomName) self.autoAssignFormat.setSeqAssignTag( atom, rawChemShift.value, AppDataClass=Implementation.AppDataFloat) # # Set info on peak level # if rawChemShift.peakId: (peakNum, rootName) = rawChemShift.peakId.split( '.') # TODO set this somewhere? peakNum = returnInt(peakNum) if rootPeakNumToPeak.has_key(peakNum): peak = rootPeakNumToPeak[peakNum] self.autoAssignFormat.setSeqAssignTag( peak, str((chain.code, residue.seqId))) else: showError( "No import file defined", "Please define a name for the %s shift output file to import." % self.format) def findMatchingAtom(self, residue, atomName): atom = residue.findFirstAtom(name=atomName) if not atom: # Rough search but should be OK for bb atoms namingSystem = residue.chemCompVar.chemComp.findFirstNamingSystem( name='XPLOR') chemAtomSysName = findChemAtomSysName(namingSystem, {'sysName': atomName}) atom = residue.findFirstAtom(name=chemAtomSysName.atomName) return atom def apply(self): if not 0: showError("No root spectrum", "Can't continue: need a root spectrum...") return False return True
class MidgePopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.project = parent.getProject() self.waiting = 0 self.specFreq = 800.13 self.maxIter = 15 self.mixTime = 60 self.corrTime = 11.5 self.leakRate = 2.0 self.ratioHD = 0.9 self.peakListDict = {} self.peakListDict3d = {} self.noesyPeakList = None self.noesy3dPeakList = None self.carbonLabel = 0 self.nitrogenLabel = 1 self.noesyPeakList1 = None self.noesyPeakList2 = None self.noesyPeakList3 = None self.noesyPeakList3d = None self.resonances = None self.noesyPeaks = None self.distanceConstraintList = None self.antiDistConstraintList = None self.adcAtomTypes = None self.structure = None BasePopup.__init__(self, parent, title="Relaxation Matrix Optimisation", **kw) def body(self, guiFrame): self.specFreqEntry = IntEntry(self, text=self.specFreq, width=8, returnCallback=self.setSpecFreq) self.maxIterEntry = IntEntry(self, text=self.maxIter, width=8, returnCallback=self.setMaxIter) self.mixTimeEntry = FloatEntry(self, text=self.mixTime, width=8, returnCallback=self.setMixTime) self.corrTimeEntry = FloatEntry(self, text=self.corrTime, width=8, returnCallback=self.setCorrTime) self.leakRateEntry = FloatEntry(self, text=self.leakRate, width=8, returnCallback=self.setLeakRate) guiFrame.grid_columnconfigure(0, weight=1) guiFrame.grid_rowconfigure(1, weight=1) row = 0 labelFrame0 = LabelFrame(guiFrame, text='Input data') labelFrame0.grid(row=row, column=0, sticky=Tkinter.NSEW) labelFrame0.grid_columnconfigure(3, weight=1) label = Label(labelFrame0, text='Assigned NOESY spectrum') label.grid(row=0, column=0, sticky=Tkinter.NW) self.noesyPulldown = PulldownMenu(labelFrame0, entries=self.getNoesys(), callback=self.setNoesy, selected_index=0, do_initial_callback=0) self.noesyPulldown.grid(row=0, column=1, sticky=Tkinter.NW) label = Label(labelFrame0, text='H/D ratio: ') label.grid(row=0, column=2, sticky=Tkinter.NW) self.ratioHDEntry = FloatEntry(labelFrame0, text=self.ratioHD, width=6) self.ratioHDEntry.grid(row=0, column=3, sticky=Tkinter.NW) label = Label(labelFrame0, text='NOESY spectrum 1:') label.grid(row=1, column=0, sticky=Tkinter.NW) self.tmix1Pulldown = PulldownMenu(labelFrame0, entries=self.getNoesys(), callback=self.setNoesy1, selected_index=-0, do_initial_callback=0) self.tmix1Pulldown.grid(row=1, column=1, sticky=Tkinter.NW) label = Label(labelFrame0, text='Tmix (ms): ') label.grid(row=1, column=2, sticky=Tkinter.NW) self.tmix1Entry = FloatEntry(labelFrame0, text=60, width=6) self.tmix1Entry.grid(row=1, column=3, sticky=Tkinter.NW) label = Label(labelFrame0, text='NOESY spectrum 2:') label.grid(row=2, column=0, sticky=Tkinter.NW) self.tmix2Pulldown = PulldownMenu(labelFrame0, entries=self.getNoesys(), callback=self.setNoesy2, selected_index=0, do_initial_callback=0) self.tmix2Pulldown.grid(row=2, column=1, sticky=Tkinter.NW) label = Label(labelFrame0, text='Tmix (ms): ') label.grid(row=2, column=2, sticky=Tkinter.NW) self.tmix2Entry = FloatEntry(labelFrame0, text=120, width=6) self.tmix2Entry.grid(row=2, column=3, sticky=Tkinter.NW) label = Label(labelFrame0, text='NOESY spectrum 3:') label.grid(row=3, column=0, sticky=Tkinter.NW) self.tmix3Pulldown = PulldownMenu(labelFrame0, entries=self.getNoesys(), callback=self.setNoesy3, selected_index=0, do_initial_callback=0) self.tmix3Pulldown.grid(row=3, column=1, sticky=Tkinter.NW) label = Label(labelFrame0, text='Tmix (ms): ') label.grid(row=3, column=2, sticky=Tkinter.NW) self.tmix3Entry = FloatEntry(labelFrame0, text=200, width=6) self.tmix3Entry.grid(row=3, column=3, sticky=Tkinter.NW) label = Label(labelFrame0, text='3D NOESY:') label.grid(row=4, column=0, sticky=Tkinter.NW) self.noesy3dPulldown = PulldownMenu(labelFrame0, entries=self.getNoesys3d(), callback=self.setNoesy3d, selected_index=0, do_initial_callback=0) self.noesy3dPulldown.grid(row=4, column=1, sticky=Tkinter.NW) label10 = Label(labelFrame0, text='Num peaks:') label10.grid(row=5, column=0, sticky=Tkinter.NW) self.numPeaksLabel = Label(labelFrame0, text='0') self.numPeaksLabel.grid(row=5, column=1, sticky=Tkinter.NW) label11 = Label(labelFrame0, text='Num resonances:') label11.grid(row=5, column=2, sticky=Tkinter.NW) self.numResonancesLabel = Label(labelFrame0, text='0') self.numResonancesLabel.grid(row=5, column=3, sticky=Tkinter.NW) row += 1 labelFrame1 = LabelFrame(guiFrame, text='Parameters') labelFrame1.grid(row=row, column=0, sticky=Tkinter.NSEW) labelFrame1.grid_columnconfigure(3, weight=1) label = Label(labelFrame1, text='15N labelled sample:') label.grid(row=0, column=0, sticky=Tkinter.NW) self.nitrogenSelect = CheckButton(labelFrame1, callback=self.setNitrogenLabel) self.nitrogenSelect.grid(row=0, column=1, sticky=Tkinter.W) self.nitrogenSelect.set(1) label = Label(labelFrame1, text='13C labelled sample:') label.grid(row=0, column=2, sticky=Tkinter.NW) self.carbonSelect = CheckButton(labelFrame1, callback=self.setCarbonLabel) self.carbonSelect.grid(row=0, column=3, sticky=Tkinter.W) self.carbonSelect.set(0) labelFrame1.grid_rowconfigure(1, weight=1) data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate ] colHeadings = [ 'Spectrometer\nfrequency', 'Max\niterations', 'Mixing\ntime (ms)', 'Correl.\ntime (ns)', 'Leak\nrate' ] editWidgets = [ self.specFreqEntry, self.maxIterEntry, self.mixTimeEntry, self.corrTimeEntry, self.leakRateEntry, ] editGetCallbacks = [ self.getSpecFreq, self.getMaxIter, self.getMixTime, self.getCorrTime, self.getLeakRate, ] editSetCallbacks = [ self.setSpecFreq, self.setMaxIter, self.setMixTime, self.setCorrTime, self.setLeakRate, ] self.midgeParamsMatrix = ScrolledMatrix( labelFrame1, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, maxRows=1, initialCols=5, headingList=colHeadings, callback=None, objectList=[ 'None', ], textMatrix=[ data, ]) self.midgeParamsMatrix.grid(row=1, column=0, columnspan=4, sticky=Tkinter.NSEW) label10 = Label(labelFrame1, text='Benchmark structure') label10.grid(row=2, column=0, sticky=Tkinter.NW) self.structurePulldown = PulldownMenu(labelFrame1, entries=self.getStructures(), callback=self.setStructure, selected_index=0, do_initial_callback=0) self.structurePulldown.grid(row=2, column=1, sticky=Tkinter.NW) label11 = Label(labelFrame1, text='ADC atom types:') label11.grid(row=2, column=2, sticky=Tkinter.NW) self.adcAtomsPulldown = PulldownMenu(labelFrame1, entries=self.getAdcAtomTypes(), callback=self.setAdcAtomTypes, selected_index=0, do_initial_callback=0) self.adcAtomsPulldown.grid(row=2, column=3, sticky=Tkinter.NW) row += 1 labelFrame2 = LabelFrame(guiFrame, text='Output') labelFrame2.grid(row=row, column=0, sticky=Tkinter.NSEW) labelFrame2.grid_columnconfigure(3, weight=1) label20 = Label(labelFrame2, text='Distance constraints:') label20.grid(row=0, column=0, sticky=Tkinter.NW) self.distConstrLabel = Label(labelFrame2, text='0') self.distConstrLabel.grid(row=0, column=1, sticky=Tkinter.NW) label21 = Label(labelFrame2, text='Anti-distance constraints:') label21.grid(row=0, column=2, sticky=Tkinter.NW) self.antiConstrLabel = Label(labelFrame2, text='0') self.antiConstrLabel.grid(row=0, column=3, sticky=Tkinter.NW) texts = [ 'Calculate distances', 'Show distance\nconstraints', 'Show anti-distance\nconstraints' ] commands = [ self.calculateDistances, self.showConstraints, self.showAntiConstraints ] self.midgeButtons = ButtonList(labelFrame2, expands=1, texts=texts, commands=commands) self.midgeButtons.grid(row=1, column=0, columnspan=4, sticky=Tkinter.NSEW) row += 1 self.bottomButtons = createDismissHelpButtonList(guiFrame, expands=0, help_url=None) self.bottomButtons.grid(row=row, column=0, columnspan=4, sticky=Tkinter.EW) self.getPeaks() self.getResonances() self.update() self.geometry('600x400') def setCarbonLabel(self, boolean): self.carbonLabel = boolean def setNitrogenLabel(self, boolean): self.nitrogenLabel = boolean def update(self): if self.resonances and ( (self.noesyPeaks and self.noesyPeakList1 and self.noesyPeakList2 and self.noesyPeakList3) or self.noesyPeakList3d): self.midgeButtons.buttons[0].enable() else: self.midgeButtons.buttons[0].disable() if self.distanceConstraintList: self.distConstrLabel.set( str(len(self.distanceConstraintList.constraints))) self.midgeButtons.buttons[1].enable() else: self.distConstrLabel.set('') self.midgeButtons.buttons[1].disable() if self.antiDistConstraintList: self.antiConstrLabel.set( str(len(self.antiDistConstraintList.constraints))) self.midgeButtons.buttons[2].enable() else: self.antiConstrLabel.set('') self.midgeButtons.buttons[2].disable() if self.resonances: self.numResonancesLabel.set(str(len(self.resonances))) else: self.numResonancesLabel.set('') if self.noesyPeaks: self.numPeaksLabel.set(str(len(self.noesyPeaks))) else: self.numPeaksLabel.set('') def getStructures(self): names = [ '<None>', ] for molSystem in self.project.sortedMolSystems(): for structure in molSystem.sortedStructureEnsembles(): names.append('%s:%d' % (molSystem.name, structure.ensembleId)) return names def setStructure(self, index, name=None): if index < 1: self.structure = None else: structures = [] for molSystem in self.project.molSystems: for structure in molSystem.structureEnsembles: structures.append(structure) self.structure = structures[index - 1] def getAdcAtomTypes(self): return ['<None>', 'HN', 'HN HA', 'HN HA HB'] def setAdcAtomTypes(self, index, name=None): if name is None: name = self.adcAtomsPulldown.getSelected() if name == '<None>': name = None self.adcAtomTypes = name def getResonances(self): resonanceDict = {} if self.noesyPeaks: for peak in self.noesyPeaks: for peakDim in peak.peakDims: for contrib in peakDim.peakDimContribs: resonanceDict[contrib.resonance] = 1 # TBD: Set resonance.name for typing self.resonances = resonanceDict.keys() def getPeaks(self): if self.noesyPeakList: self.noesyPeaks = self.noesyPeakList.sortedPeaks() def calculateDistances(self): resonances = list(self.resonances) resDict = {} for resonance in resonances: resDict[resonance.serial] = resonance ratioHD = self.ratioHDEntry.get() or self.ratioHD tmix1 = self.tmix1Entry.get() or 60 tmix2 = self.tmix2Entry.get() or 120 tmix3 = self.tmix3Entry.get() or 200 data = [(tmix1, self.noesyPeakList1), (tmix2, self.noesyPeakList2), (tmix3, self.noesyPeakList3)] data.sort() mixingTimes = [x[0] for x in data] peakLists = [x[1] for x in data] # get a clean, symmetric and normalised NOE matrix noeMatrix = getNoeMatrixFromPeaks(self.noesyPeaks, resonances, peakLists, mixingTimes, ratioHD=ratioHD, analysis=self.guiParent) # optimiseRelaxation will remove unconstrained resonances self.distanceConstraintList, resonances = optimiseRelaxation( resonances, noeMatrix, self.mixTime, self.specFreq, self.corrTime, self.leakRate, self.carbonLabel, self.nitrogenLabel, maxIter=self.maxIter) #constrainSpinSystems(self.distanceConstraintList) # for testing calculate distances from structure overrides any resonances: uses assigned ones #(self.distanceConstraintList, self.resonances) = self.cheatForTesting() #self.antiDistConstraintList = self.distanceConstraintList protonNumbs = {'CH3': 3, 'Haro': 2, 'HN': 1, 'H': 1} PI = 3.1415926535897931 GH = 2.6752e4 HB = 1.05459e-27 CONST = GH * GH * GH * GH * HB * HB tc = 1.0e-9 * self.corrTime wh = 2.0 * PI * self.specFreq * 1.0e6 j0 = CONST * tc j1 = CONST * tc / (1.0 + wh * wh * tc * tc) j2 = CONST * tc / (1.0 + 4.0 * wh * wh * tc * tc) #jself = 6.0*j2 + 3.0*j1 + j0 jcross = 6.0 * j2 - j0 if self.distanceConstraintList and self.noesyPeakList: constraintHead = self.distanceConstraintList.nmrConstraintStore if self.adcAtomTypes: adcDict = { 'HN': ['H'], 'HN HA': ['H', 'HA', 'HA1', 'HA2'], 'HN HA HB': ['H', 'HA', 'HA1', 'HA2', 'HB', 'HB2', 'HB3'] } allowedAtomTypes = adcDict[self.adcAtomTypes] print "Making ADCs" self.antiDistConstraintList = makeNoeAdcs( resonances[:], self.noesyPeakList.dataSource, constraintHead, allowedAtomTypes=allowedAtomTypes) print "Done ADCs" if self.structure: N = len(self.resonances) sigmas = [[] for i in range(N)] for i in range(N): sigmas[i] = [0.0 for j in range(N)] for constraint in self.distanceConstraintList.constraints: item = constraint.findFirstItem() resonances = list(item.resonances) ri = resDict[resonances[0].resonanceSerial] rj = resDict[resonances[1].resonanceSerial] i = self.resonances.index(ri) j = self.resonances.index(rj) atomSets1 = list(ri.resonanceSet.atomSets) atomSets2 = list(rj.resonanceSet.atomSets) if atomSets1 == atomSets2: ass = list(atomSets1) atomSets1 = [ ass[0], ] atomSets2 = [ ass[-1], ] distance = getAtomSetsDistance(atomSets1, atomSets2, self.structure) r = distance * 1e-8 nhs = protonNumbs[rj.name] sigma = 0.1 * jcross * nhs / (r**6) sigmas[i][j] = sigma constraint.setOrigData(distance) self.update() def showConstraints(self): if self.distanceConstraintList: self.guiParent.browseConstraints( constraintList=self.distanceConstraintList) def showAntiConstraints(self): if self.antiDistConstraintList: self.guiParent.browseConstraints( constraintList=self.antiDistConstraintList) def getNoesys3d(self): peakLists = getThroughSpacePeakLists(self.project) names = [ '<None>', ] for peakList in peakLists: spectrum = peakList.dataSource if spectrum.numDim != 3: continue name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict3d[name] = peakList if not self.noesyPeakList: self.noesyPeakList = peakList return names def getNoesys(self): peakLists = getThroughSpacePeakLists(self.project) names = [ '<None>', ] for peakList in peakLists: spectrum = peakList.dataSource name = '%s:%s:%s' % (spectrum.experiment.name, spectrum.name, peakList.serial) names.append(name) self.peakListDict[name] = peakList if not self.noesyPeakList: self.noesyPeakList = peakList return names def setNoesy(self, index, name=None): if not name: name = self.noesyPulldown.getSelected() if name == '<None>': self.noesyPeakList = None else: self.noesyPeakList = self.peakListDict[name] self.getPeaks() self.getResonances() self.update() def setNoesy1(self, index, name=None): if not name: name = self.tmix1Pulldown.getSelected() if name != '<None>': self.noesyPeakList1 = self.peakListDict[name] else: self.noesyPeakList1 = None self.update() def setNoesy2(self, index, name=None): if not name: name = self.tmix2Pulldown.getSelected() if name != '<None>': self.noesyPeakList2 = self.peakListDict[name] else: self.noesyPeakList2 = None self.update() def setNoesy3(self, index, name=None): if not name: name = self.tmix3Pulldown.getSelected() if name != '<None>': self.noesyPeakList3 = self.peakListDict[name] else: self.noesyPeakList3 = None self.update() def setNoesy3d(self, index, name=None): if not name: name = self.noesy3dPulldown.getSelected() if name != '<None>': self.noesyPeakList3d = self.peakListDict3d[name] self.noesyPeaks = self.noesyPeakList3d.sortedPeaks() else: self.noesyPeakList3d = None self.noesyPeaks = [] self.getResonances() self.update() def updateMidgeParams(self): data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate ] self.midgeParamsMatrix.update(textMatrix=[ data, ]) def getSpecFreq(self, obj): self.specFreqEntry.set(self.specFreq) def getMaxIter(self, obj): self.maxIterEntry.set(self.maxIter) def getMixTime(self, obj): self.mixTimeEntry.set(self.mixTime) def getCorrTime(self, obj): self.corrTimeEntry.set(self.corrTime) def getLeakRate(self, obj): self.leakRateEntry.set(self.leakRate) def setSpecFreq(self, event): value = self.specFreqEntry.get() if value is not None: self.specFreq = value self.updateMidgeParams() def setMaxIter(self, event): value = self.maxIterEntry.get() if value is not None: self.maxIter = value self.updateMidgeParams() def setMixTime(self, event): value = self.mixTimeEntry.get() if value is not None: self.mixTime = value self.updateMidgeParams() def setCorrTime(self, event): value = self.corrTimeEntry.get() if value is not None: self.corrTime = value self.updateMidgeParams() def setLeakRate(self, event): value = self.leakRateEntry.get() if value is not None: self.leakRate = value self.updateMidgeParams() def destroy(self): BasePopup.destroy(self)
class WriteBmrbChemShiftDepPopup(BasePopup): help_url = joinPath(getHelpUrlDir(), 'WriteBmrbChemShiftDep.html') def __init__(self, parent, project): self.project = project self.guiParent = parent self.selectedFormats = [] self.defaultText = 'Select file' self.chainDict = {} self.chainList = [] self.shiftListDict = {} self.shiftLists = [] for shiftList in self.project.currentNmrProject.findAllMeasurementLists( className='ShiftList'): if shiftList.measurements != (): label = str(shiftList.serial) + ':' + str(shiftList.name) self.shiftListDict[label] = shiftList self.shiftLists.append(label) if not self.shiftLists: showError('Error', 'No shift lists available!') return BasePopup.__init__(self, parent=parent, title="Project '%s': " % project.name + 'Write BMRB chemical shift deposition file', modal=False, transient=True) def body(self, master): row = 0 label = Label(master, text="BMRB chemical shift deposition file writer.") label.grid(row=row, column=0, columnspan=2, sticky=Tkinter.W) row += 1 label = Label(master, text="Shift lists:") label.grid(row=row, column=0, sticky=Tkinter.W) self.shiftListSelect = PulldownMenu(master, entries=self.shiftLists, callback=self.setChainList, do_initial_callback=False) self.shiftListSelect.grid(row=row, column=1, sticky=Tkinter.EW) row += 1 label = Label(master, text="Chains (only one per file):") label.grid(row=row, column=0, sticky=Tkinter.W) self.chainListSelect = PulldownMenu(master, entries=self.chainList) self.chainListSelect.grid(row=row, column=1, sticky=Tkinter.EW) self.setChainList(0, self.shiftLists[0]) row += 1 label = Label(master, text="Chemical shift deposition file:") label.grid(row=row, column=0, sticky=Tkinter.W) self.fileButton = Tkinter.Button(master, text=self.defaultText, command=self.selectFile) self.fileButton.grid(row=row, column=1, sticky=Tkinter.W) row += 1 texts = ['Write file'] commands = [ self.ok ] # This calls 'ok' in BasePopup, this then calls 'apply' in here buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, help_url=self.help_url) buttons.grid(row=row, columnspan=2, column=0) def setChainList(self, shiftListIndex, shiftListLabel): # # Has to be done... very slow this. # shiftList = self.shiftListDict[shiftListLabel] self.chainDict = {} self.chainList = [] for shift in shiftList.measurements: if shift.resonance: rs = shift.resonance.resonanceSet if rs: atom = rs.findFirstAtomSet().findFirstAtom() chain = atom.residue.chain if chain not in self.chainDict.values(): label = chain.molSystem.code + ":'" + chain.code + "'" self.chainDict[label] = chain self.chainList.append(label) self.chainListSelect.clearMenuItems() if self.chainList: self.chainListSelect.setup(self.chainList, 0) def selectFile(self): fileName = self.fileButton.__getitem__('text') if fileName == self.defaultText: fileName = 'bmrb.csdep' popup = FormatFilePopup(self, file=fileName, component='csdep', format='bmrb') if popup.fileSelected: self.fileButton.config(text=popup.file) popup.destroy() def apply(self): shiftListLabel = self.shiftListSelect.getSelected() shiftList = self.shiftListDict[shiftListLabel] try: chainLabel = self.chainListSelect.getSelected() chain = self.chainDict[chainLabel] except: showError( "No chains", "No chains were present or selected. Try running linkResonances first." ) return False fileName = self.fileButton.__getitem__('text') if fileName == self.defaultText: return False fileCreated = writeBmrbChemShiftDeposition(self.guiParent, chain, shiftList, fileName) if fileCreated: showInfo("Success", "Succesfully wrote chemical shift deposition file") else: showError("Not written", "Error writing file %s. File not written" % fileName) return False return True
class HcloudsMdPopup(BasePopup): def __init__(self, parent, *args, **kw): self.guiParent = parent self.project = parent.getProject() self.waiting = 0 self.constraintSet = None self.constrLists = [None] * 4 self.numClouds = 100 self.filePrefix = 't_intra_' self.cloudsFiles = [] self.adcAtomTypes = 'HN' # step num, initial temp, final temp, cooling steps, MD steps, MD tau, rep scale self.coolingScheme = [] self.coolingScheme.append([1, 1, 1, 3, 500, 0.001, 0]) self.coolingScheme.append([2, 80000, 4000, 19, 1000, 0.001, 0]) self.coolingScheme.append([3, 4000, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([4, 15000, 1, 3, 1000, 0.001, 0]) self.coolingScheme.append([5, 1, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([6, 8000, 1, 3, 1000, 0.001, 0]) self.coolingScheme.append([7, 1, 1, 5, 500, 0.001, 0]) self.coolingScheme.append([8, 3000, 25, 60, 2500, 0.001, 1]) self.coolingScheme.append([9, 25, 25, 1, 7500, 0.001, 1]) self.coolingScheme.append([10, 10, 10, 1, 7500, 0.001, 1]) self.coolingScheme.append([11, 0.01, 0.01, 1, 7500, 0.0005, 1]) self.coolingStep = None BasePopup.__init__(self, parent, title="Hydrogen Cloud Molecular Dynamics", **kw) def body(self, guiFrame): self.mdInitTempEntry = FloatEntry(self, text='', returnCallback=self.setMdInitTemp) self.mdFinTempEntry = FloatEntry(self, text='', returnCallback=self.setMdFinTemp) self.mdCoolStepsEntry = IntEntry(self, text='', returnCallback=self.setMdCoolSteps) self.mdSimStepsEntry = IntEntry(self, text='', returnCallback=self.setMdSimSteps) self.mdTauEntry = FloatEntry(self, text='', returnCallback=self.setMdTau) self.mdRepScaleEntry = FloatEntry(self, text='', returnCallback=self.setMdRepScale) guiFrame.grid_columnconfigure(0, weight=1) row = 0 guiFrame.grid_rowconfigure(row, weight=1) frame = LabelFrame(guiFrame, text='Input constraints') frame.grid(row=row, column=0, sticky=Tkinter.NSEW) frame.grid_columnconfigure(2, weight=1) srow = 0 label = Label(frame, text='Constraint set:') label.grid(row=srow, column=0, sticky=Tkinter.W) self.constraintSetPulldown = PulldownMenu( frame, callback=self.changeConstraintSet, selected_index=0, do_initial_callback=0) self.constraintSetPulldown.grid(row=srow, column=1, sticky=Tkinter.W) srow += 1 label = Label(frame, text='Dist constraint list 1:') label.grid(row=srow, column=0, sticky=Tkinter.W) self.distance1Pulldown = PulldownMenu( frame, callback=self.changeDistance1ConstraintList, selected_index=0, do_initial_callback=0) self.distance1Pulldown.grid(row=srow, column=1, sticky=Tkinter.W) self.numConstr1Label = Label(frame, text='Constraints: 0') self.numConstr1Label.grid(row=srow, column=2, sticky=Tkinter.W) srow += 1 label = Label(frame, text='Dist constraint list 2:') label.grid(row=srow, column=0, sticky=Tkinter.W) self.distance2Pulldown = PulldownMenu( frame, callback=self.changeDistance2ConstraintList, selected_index=0, do_initial_callback=0) self.distance2Pulldown.grid(row=srow, column=1, sticky=Tkinter.W) self.numConstr2Label = Label(frame, text='Constraints: 0') self.numConstr2Label.grid(row=srow, column=2, sticky=Tkinter.W) srow += 1 label = Label(frame, text='Dist constraint list 3:') label.grid(row=srow, column=0, sticky=Tkinter.W) self.distance3Pulldown = PulldownMenu( frame, callback=self.changeDistance3ConstraintList, selected_index=0, do_initial_callback=0) self.distance3Pulldown.grid(row=srow, column=1, sticky=Tkinter.W) self.numConstr3Label = Label(frame, text='Constraints: 0') self.numConstr3Label.grid(row=srow, column=2, sticky=Tkinter.W) srow += 1 label = Label(frame, text='Dist constraint list 4:') label.grid(row=srow, column=0, sticky=Tkinter.W) self.distance4Pulldown = PulldownMenu( frame, callback=self.changeDistance4ConstraintList, selected_index=0, do_initial_callback=0) self.distance4Pulldown.grid(row=srow, column=1, sticky=Tkinter.W) self.numConstr4Label = Label(frame, text='Constraints: 0') self.numConstr4Label.grid(row=srow, column=2, sticky=Tkinter.W) row += 1 frame0 = LabelFrame(guiFrame, text='Cooling scheme') frame0.grid(row=row, column=0, sticky=Tkinter.NSEW) frame0.grid_columnconfigure(1, weight=1) f0row = 0 frame0.grid_rowconfigure(f0row, weight=1) colHeadings = [ 'Step', 'Initial\nTemp.', 'Final\nTemp.', 'Cooling\nSteps', 'MD Steps', 'MD Tau', 'Rep.\nScale' ] editWidgets = [ None, self.mdInitTempEntry, self.mdFinTempEntry, self.mdCoolStepsEntry, self.mdSimStepsEntry, self.mdTauEntry, self.mdRepScaleEntry ] editGetCallbacks = [ None, self.getMdInitTemp, self.getMdFinTemp, self.getMdCoolSteps, self.getMdSimSteps, self.getMdTau, self.getMdRepScale ] editSetCallbacks = [ None, self.setMdInitTemp, self.setMdFinTemp, self.setMdCoolSteps, self.setMdSimSteps, self.setMdTau, self.setMdRepScale ] self.coolingSchemeMatrix = ScrolledMatrix( frame0, editSetCallbacks=editSetCallbacks, editGetCallbacks=editGetCallbacks, editWidgets=editWidgets, maxRows=9, initialRows=12, headingList=colHeadings, callback=self.selectCoolingStep, objectList=self.coolingScheme, textMatrix=self.coolingScheme) self.coolingSchemeMatrix.grid(row=f0row, column=0, columnspan=4, sticky=Tkinter.NSEW) f0row += 1 texts = ['Move earlier', 'Move later', 'Add step', 'Remove step'] commands = [ self.moveStepEarlier, self.moveStepLater, self.addCoolingStep, self.removeCoolingStep ] self.coolingSchemeButtons = ButtonList(frame0, expands=1, commands=commands, texts=texts) self.coolingSchemeButtons.grid(row=f0row, column=0, columnspan=4, sticky=Tkinter.EW) row += 1 guiFrame.grid_rowconfigure(row, weight=1) frame1 = LabelFrame(guiFrame, text='Dynamics control') frame1.grid(row=row, column=0, sticky=Tkinter.NSEW) frame1.grid_columnconfigure(1, weight=1) f1row = 0 label20 = Label(frame1, text='Number of clouds:') label20.grid(row=f1row, column=0, sticky=Tkinter.NW) self.numCloudsEntry = IntEntry(frame1, text=1, returnCallback=self.setNumClouds, width=10) self.numCloudsEntry.grid(row=f1row, column=1, sticky=Tkinter.NW) label21 = Label(frame1, text='Cloud file prefix:') label21.grid(row=f1row, column=2, sticky=Tkinter.NW) self.filePrefixEntry = Entry(frame1, text='t_intra_', returnCallback=self.setFilePrefix, width=10) self.filePrefixEntry.grid(row=f1row, column=3, sticky=Tkinter.NW) f1row += 1 texts = ['Start molecular dynamics', 'Show dynamics progress'] commands = [self.startMd, self.showMdProgress] self.mdButtons = ButtonList(frame1, expands=1, commands=commands, texts=texts) self.mdButtons.grid(row=f1row, column=0, columnspan=4, sticky=Tkinter.NSEW) row += 1 self.bottomButtons = createDismissHelpButtonList(guiFrame, expands=0, help_url=None) self.bottomButtons.grid(row=row, column=0, sticky=Tkinter.EW) self.update() for func in ('__init__', 'delete', 'setName'): for clazz in ('ccp.nmr.NmrConstraint.DistanceConstraintList', ): Implementation.registerNotify(self.updateConstraintLists, clazz, func) for func in ('__init__', 'delete'): Implementation.registerNotify( self.updateConstraintSets, 'ccp.nmr.NmrConstraint.NmrConstraintStore', func) def getContraintSetNames(self): names = [] constraintSets = self.project.currentNmrProject.nmrConstraintStores for set in constraintSets: names.append('%d' % set.serial) return names def changeConstraintSet(self, i, name): project = self.project if project.currentNmrProject.nmrConstraintStores: constraintSet = project.currentNmrProject.sortedNmrConstraintStores( )[i] else: constraintSet = None if constraintSet is not self.constraintSet: self.constraintSet = constraintSet self.updateConstraintLists() self.update() def updateConstraintLists(self, *opt): constrListData = self.getConstraintLists() constrListNames = [x[0] for x in constrListData] constraintLists = [x[1] for x in constrListData] # copes with self.constraintSet being None if constrListNames: i = 0 for constraintList in self.constrLists: if constraintList not in constraintLists: if i == 0: self.constrLists[i] = constraintLists[0] else: self.constrLists[i] = None i += 1 constraintLists.append(None) constrListNames.append('<None>') self.distance1Pulldown.setup( constrListNames, constraintLists.index(self.constrLists[0])) self.distance2Pulldown.setup( constrListNames, constraintLists.index(self.constrLists[1])) self.distance3Pulldown.setup( constrListNames, constraintLists.index(self.constrLists[2])) self.distance4Pulldown.setup( constrListNames, constraintLists.index(self.constrLists[3])) else: self.constrLists = [None] * 4 self.distance1Pulldown.setup([], -1) self.distance2Pulldown.setup([], -1) self.distance3Pulldown.setup([], -1) self.distance4Pulldown.setup([], -1) def updateConstraintSets(self, *opt): project = self.project constraintSets = list(project.currentNmrProject.nmrConstraintStores) if constraintSets: constraintSetNames = self.getContraintSetNames() # set defaults if self.constraintSet not in constraintSets: self.constraintSet = constraintSets[0] if self.constraintSet: j = 0 for constraintList in self.constrLists: if constraintList and (constraintList.nmrConstraintStore is not self.constraintSet): if self.constraintSet.constraintLists and j == 0: self.constrLists[ j] = self.constraintSet.constraintLists[0] else: self.constrLists[j] = None j += 1 else: self.constrLists = [None] * 4 i = constraintSets.index(self.constraintSet) self.constraintSetPulldown.setup(constraintSetNames, i) else: self.constraintSet = None self.constrLists = [None] * 4 self.constraintSetPulldown.setup([], -1) def getConstraintListName(self, constraintList): if constraintList.name: listName = ':%s' % (constraintList.name) else: listName = '' name = '%d:%d:%s%s' % (constraintList.nmrConstraintStore.serial, constraintList.serial, constraintList.className[:-14], listName) return name def getConstraintLists(self): constraintLists = [] if self.constraintSet: for constraintList in self.constraintSet.constraintLists: if constraintList.className == 'DistanceConstraintList': name = self.getConstraintListName(constraintList) constraintLists.append([name, constraintList]) return constraintLists def changeDistance1ConstraintList(self, i, name): self.changeDistanceConstraintList(i, name, 0) def changeDistance2ConstraintList(self, i, name): self.changeDistanceConstraintList(i, name, 1) def changeDistance3ConstraintList(self, i, name): self.changeDistanceConstraintList(i, name, 2) def changeDistance4ConstraintList(self, i, name): self.changeDistanceConstraintList(i, name, 3) def changeDistanceConstraintList(self, i, name, listNum): project = self.project constraintLists = self.getConstraintLists() if constraintLists and (i < 4): self.constrLists[listNum] = constraintLists[i][1] else: self.constrLists[listNum] = None self.update() def startMd(self): self.setNumClouds() self.setFilePrefix() if ((self.constrLists != [None] * 4) and (self.numClouds > 0) and self.filePrefix): resDict = {} for resonance in self.guiParent.project.currentNmrProject.resonances: resDict[resonance.serial] = resonance constraints = [] constraintStore = None for dcl in self.constrLists: if dcl: constraintStore = dcl.nmrConstraintStore constraints.extend(list(dcl.constraints)) resonances = [] for constraint in constraints: for item in constraint.items: for fixedResonance in item.resonances: if fixedResonance.resonanceSerial is None: resonance = newResonance( self.guiParent.project, isotopeCode=fixedResonance.isotopeCode) resonance.setName(fixedResonance.name) fixedResonance.setResonanceSerial(resonance.serial) resDict[resonance.serial] = resonance if fixedResonance.resonanceSet: atomSets = list( fixedResonance.resonanceSet.atomSets) assignAtomsToRes(atomSets, resonance) if resDict.get( fixedResonance.resonanceSerial) is not None: resonances.append( resDict[fixedResonance.resonanceSerial]) resDict[fixedResonance.resonanceSerial] = None resonances, intraConstraintList = self.makeIntraConstraints( resonances, constraintStore) constraints.extend(list(intraConstraintList.constraints)) resonances, interConstraintList = self.makeInterConstraints( resonances, constraintStore) constraints.extend(list(interConstraintList.constraints)) startMdProcess(self.numClouds, constraints, resonances, self.coolingScheme, self.filePrefix) #structGen = self.distanceConstraintList.structureGeneration serials = [] for resonance in resonances: serials.append(resonance.serial) clouds = [] for i in range(self.numClouds): clouds.append('%s%3.3d.pdb' % (self.filePrefix, i)) self.guiParent.application.setValues(constraintStore, 'clouds', values=clouds) self.guiParent.application.setValues(constraintStore, 'cloudsResonances', values=serials) # do better than this check for creation def makeInterConstraints(self, resonances, constraintSet): from ccpnmr.analysis.core.ConstraintBasic import getFixedResonance from ccpnmr.analysis.core.AssignmentBasic import findConnectedSpinSystem project = constraintSet.root constraintList = constraintSet.newDistanceConstraintList() constraintList.name = 'Seq connections' resDict = {} spinSystemDict = {} for resonance in resonances: resDict[resonance] = True spinSystem = resonance.resonanceGroup if spinSystem: spinSystemDict[spinSystem] = None spinSystems = spinSystemDict.keys() for spinSystem in spinSystems: nextSpinSystem = findConnectedSpinSystem(spinSystem, delta=1) if nextSpinSystem: ca = spinSystem.newAtoms.get('CA') c = spinSystem.newAtoms.get('C') n = nextSpinSystem.newAtoms.get('N') if ca and c and n: if resDict.get(ca) is None: resonances.append(ca) if resDict.get(c) is None: resonances.append(c) if resDict.get(n) is None: resonances.append(n) c_n = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.32, upperLimit=1.35, lowerLimit=1.29, error=0.06) # below based on angle constraints ca_n = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=2.415, upperLimit=2.513, lowerLimit=2.316, error=0.197) frCa = getFixedResonance(constraintSet, ca) frC = getFixedResonance(constraintSet, c) frN = getFixedResonance(constraintSet, n) item = ca_n.newDistanceConstraintItem( resonances=[frCa, frN]) item = c_n.newDistanceConstraintItem(resonances=[frC, frN]) return resonances, constraintList def makeIntraConstraints(self, resonances, constraintSet): from ccpnmr.analysis.core.ConstraintBasic import getFixedResonance project = constraintSet.root constraintList = constraintSet.newDistanceConstraintList() constraintList.name = 'Backbone intra' dict = {} for resonance in resonances: if resonance.resonanceGroup and resonance.assignNames: dict[resonance] = 1 resonance.resonanceGroup.newAtoms = {} for resonance in dict.keys(): ss = resonance.resonanceGroup if resonance.assignNames[0] == 'H': for resonance2 in ss.resonances: if dict.get(resonance2 ) and resonance2.assignNames[0][:2] == 'HA': ca = ss.newAtoms.get('CA') if ca is None: ca = project.newResonance(isotopeCode='13C', assignNames=[ 'CA', ]) resonances.append(ca) c = ss.newAtoms.get('C') if c is None: c = project.newResonance(isotopeCode='13C', assignNames=[ 'C', ]) resonances.append(c) n = ss.newAtoms.get('N') if n is None: n = project.newResonance(isotopeCode='15N', assignNames=[ 'N', ]) resonances.append(n) ss.newAtoms['C'] = c ss.newAtoms['CA'] = ca ss.newAtoms['N'] = n frCa = getFixedResonance(constraintSet, ca) frC = getFixedResonance(constraintSet, c) frN = getFixedResonance(constraintSet, n) frH = getFixedResonance(constraintSet, resonance) frha = getFixedResonance(constraintSet, resonance2) h_n = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.01, upperLimit=1.1, lowerLimit=0.9, error=0.2) n_ca = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.465, upperLimit=1.50, lowerLimit=1.43, error=0.07) ca_c = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.525, upperLimit=1.55, lowerLimit=1.50, error=0.05) # below based on angle constraints n_c = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=2.464, upperLimit=2.572, lowerLimit=2.356, error=0.216) item = h_n.newDistanceConstraintItem( resonances=[frH, frN]) item = n_ca.newDistanceConstraintItem( resonances=[frN, frCa]) item = ca_c.newDistanceConstraintItem( resonances=[frCa, frC]) item = n_c.newDistanceConstraintItem( resonances=[frN, frC]) if ss.newAtoms.get('CAHA') is None: ca_ha = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.09, upperLimit=1.19, lowerLimit=0.99, error=0.2) item = ca_ha.newDistanceConstraintItem( resonances=[frC, frha]) ss.newAtoms['CAHA'] = 1 if resonance.assignNames[0][:2] == 'HA': for resonance2 in ss.resonances: if dict.get(resonance2 ) and resonance2.assignNames[0][:2] == 'HB': ca = ss.newAtoms.get('CA') if ca is None: ca = project.newResonance(isotopeCode='13C', assignNames=[ 'CA', ]) resonances.append(ca) cb = ss.newAtoms.get('CB') if cb is None: cb = project.newResonance(isotopeCode='13C', assignNames=[ 'CB', ]) resonances.append(cb) ss.newAtoms['CA'] = cb ss.newAtoms['CB'] = ca ss.newAtoms['CAHA'] = 1 frCA = getFixedResonance(constraintSet, ca) frCB = getFixedResonance(constraintSet, cb) frHA = getFixedResonance(constraintSet, resonance) frHB = getFixedResonance(constraintSet, resonance2) c_b = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.09, upperLimit=1.19, lowerLimit=0.99, error=0.2) c_c = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.53, upperLimit=1.56, lowerLimit=1.51, error=0.05) item = c_b.newDistanceConstraintItem( resonances=[frCB, frHB]) item = c_c.newDistanceConstraintItem( resonances=[frCA, frCB]) if ss.newAtoms.get('CAHA') is None: c_a = constraintList.newDistanceConstraint( weight=1.0, origData=1.0, targetValue=1.09, upperLimit=1.19, lowerLimit=0.99, error=0.2) item = c_a.newDistanceConstraintItem( resonances=[frCA, frHA]) ss.newAtoms['CAHA'] = 1 return resonances, constraintList def showMdProgress(self): n = 0 m = self.numClouds for i in range(m): pdbFileName = '%s%3.3d.pdb' % (self.filePrefix, i) if os.path.exists(pdbFileName): n += 1 p = n * 100 / float(m) text = 'Done %d of %d clouds (%1.2f)%%' % (n, m, p) showInfo('MD Progress', text) def setFilePrefix(self, text=None): if not text: text = self.filePrefixEntry.get() if text: self.filePrefix = text def setNumClouds(self, n=None, *event): if not n: n = self.numCloudsEntry.get() if n: self.numClouds = int(n) def update(self): self.updateConstraintSets() self.updateConstraintLists() if (self.constrLists != [None] * 4) and self.coolingScheme: self.mdButtons.buttons[0].enable() self.mdButtons.buttons[1].enable() else: self.mdButtons.buttons[0].disable() self.mdButtons.buttons[1].disable() if self.constrLists[0]: self.numConstr1Label.set('Constraints: ' + str(len(self.constrLists[0].constraints))) else: self.numConstr1Label.set('Constraints: 0') if self.constrLists[1]: self.numConstr2Label.set('Constraints: ' + str(len(self.constrLists[1].constraints))) else: self.numConstr2Label.set('Constraints: 0') if self.constrLists[2]: self.numConstr3Label.set('Constraints: ' + str(len(self.constrLists[2].constraints))) else: self.numConstr3Label.set('Constraints: 0') if self.constrLists[3]: self.numConstr4Label.set('Constraints: ' + str(len(self.constrLists[3].constraints))) else: self.numConstr4Label.set('Constraints: 0') def getMdInitTemp(self, coolingStep): self.mdInitTempEntry.set(coolingStep[1]) def getMdFinTemp(self, coolingStep): self.mdFinTempEntry.set(coolingStep[2]) def getMdCoolSteps(self, coolingStep): self.mdCoolStepsEntry.set(coolingStep[3]) def getMdSimSteps(self, coolingStep): self.mdSimStepsEntry.set(coolingStep[4]) def getMdTau(self, coolingStep): self.mdTauEntry.set(coolingStep[5]) def getMdRepScale(self, coolingStep): self.mdRepScaleEntry.set(coolingStep[6]) def setMdInitTemp(self, event): value = self.mdInitTempEntry.get() if value is not None: self.coolingStep[1] = value self.updateCoolingScheme() def setMdFinTemp(self, event): value = self.mdFinTempEntry.get() if value is not None: self.coolingStep[2] = value self.updateCoolingScheme() def setMdCoolSteps(self, event): value = self.mdCoolStepsEntry.get() if value is not None: self.coolingStep[3] = value self.updateCoolingScheme() def setMdSimSteps(self, event): value = self.mdSimStepsEntry.get() if value is not None: self.coolingStep[4] = value self.updateCoolingScheme() def setMdTau(self, event): value = self.mdTauEntry.get() if value is not None: self.coolingStep[5] = value self.updateCoolingScheme() def setMdRepScale(self, event): value = self.mdRepScaleEntry.get() if value is not None: self.coolingStep[6] = value self.updateCoolingScheme() def selectCoolingStep(self, object, row, col): self.coolingStep = object def moveStepEarlier(self): if self.coolingStep: i = self.coolingStep[0] - 1 if i > 0: coolingStep = self.coolingScheme[i - 1] coolingStep[0] = i + 1 self.coolingStep[0] = i self.coolingScheme[i - 1] = self.coolingStep self.coolingScheme[i] = coolingStep self.updateCoolingScheme() self.coolingSchemeMatrix.hilightObject(self.coolingStep) def moveStepLater(self): if self.coolingStep: i = self.coolingStep[0] - 1 if i < len(self.coolingScheme) - 1: coolingStep = self.coolingScheme[i + 1] coolingStep[0] = i + 1 self.coolingStep[0] = i + 2 self.coolingScheme[i + 1] = self.coolingStep self.coolingScheme[i] = coolingStep self.updateCoolingScheme() self.coolingSchemeMatrix.hilightObject(self.coolingStep) def addCoolingStep(self): i = len(self.coolingScheme) + 1 datum = [i, 3000, 100, 10, 2500, 0.001, 1] self.coolingScheme.append(datum) self.updateCoolingScheme() def removeCoolingStep(self): if self.coolingStep: coolingScheme = [] i = 0 for coolingStep in self.coolingScheme: if coolingStep is not self.coolingStep: i += 1 coolingStep[0] = i coolingScheme.append(coolingStep) self.coolingScheme = coolingScheme self.updateCoolingScheme() def updateCoolingScheme(self): objectList = self.coolingScheme textMatrix = self.coolingScheme self.coolingSchemeMatrix.update(objectList=objectList, textMatrix=textMatrix) def updateMidgeParams(self): data = [ self.specFreq, self.maxIter, self.mixTime, self.corrTime, self.leakRate, self.maxIntens ] self.midgeParamsMatrix.update(textMatrix=[ data, ]) def destroy(self): for func in ('__init__', 'delete', 'setName'): for clazz in ('ccp.nmr.NmrConstraint.DistanceConstraintList', ): Implementation.unregisterNotify(self.updateConstraintLists, clazz, func) for func in ('__init__', 'delete'): Implementation.unregisterNotify( self.updateConstraintSets, 'ccp.nmr.NmrConstraint.NmrConstraintStore', func) BasePopup.destroy(self)