class TasksFrame(Frame): def __init__(self, guiParent, basePopup): self.guiParent = guiParent self.basePopup = basePopup # selection hash. This needs to be stored so that we can # refresh with the same criteria self.select = None # should the screen autorefresh self.autoRefresh = False # add this to shortcuts to ease navigation self.basePopup.frameShortcuts['Tasks'] = self #self.registerNotify=basePopup.registerNotify #self.unregisterNotify=basePopup.unregisterNotify #self.frames = [] # FIXME JMCI # This frame is specific for a single repository so we need a # method for identifying one from the whole set (or could have # subtabs) Frame.__init__(self, guiParent) # set up the grid self.grid_columnconfigure(0, weight=0, minsize=20) self.grid_columnconfigure(1, weight=1, minsize=30) self.grid_columnconfigure(2, weight=0, minsize=40) self.grid_rowconfigure(0, weight=0, minsize=20) self.grid_rowconfigure(1, weight=0, minsize=10) self.grid_rowconfigure(2, weight=0, minsize=0) self.grid_rowconfigure(3, weight=0, minsize=0) self.grid_rowconfigure(4, weight=0, minsize=0) self.grid_rowconfigure(5, weight=1, minsize=0) self.grid_rowconfigure(6, weight=0, minsize=10) self.grid_rowconfigure(7, weight=0, minsize=10) initial_cols = ['ID','Task','User','Status'] self.task_matrix = ScrolledMatrix(self, headingList=initial_cols, initialRows=15, doubleCallback=self.goto_task_tab) # Filters for narrowing down tasks. should probably code this # specifically inside this package #self.filter = FilterFrame(self, self.basePopup, text='Filter') self.filter = TaskFilterFrame(self, self.basePopup, text='Filter') # Frame for controlling the main client side daemon # seems to be a problem. add a simple button for now opts = ['Client','Server'] self.daemonFrame = TabbedFrame(self, options=opts, toggleOff=False, selected=0) self.daemonSwitchLabel = Label(self, text= 'Task Daemon') self.daemonSwitch = RadioButtons(self, ['on', 'off'], select_callback=self.set_daemon, selected_index = 1) sel = 1 if self.autoRefresh: sel = 0 self.autoRefreshSwitchLabel = Label(self, text= 'Auto Refresh') self.autoRefreshSwitch = RadioButtons(self, ['on', 'off'], select_callback=self.set_refresh, selected_index = sel) self.label_rep = Label(self, text='', font='Helvetica16') # set up a loop self.refresh() def drawFrame(self): # build up the body. # This is a very simple mock up. In reality we need to be # able to select a number of different input files that # depend on the task type # we need to have the current repository in context self.repository = self.basePopup.repList.currentRepository if self.repository == None: self.label_rep.grid_remove() self.task_matrix.grid_remove() self.filter.grid_remove() self.daemonSwitchLabel.grid_remove() self.daemonSwitch.grid_remove() else: strg = self.repository.user + '@' + self.repository.name + ' (' + self.repository.connect + ')' self.label_rep.set('TaskManager: Repository ' + strg) self.label_rep.grid(row=1, column=1, columnspan=2, sticky='w') self.task_matrix.grid(row=2, column=1, rowspan=4, sticky='nsew') loc = SharedBeanServiceLocator() port = loc.getSharedBean() request1 = getList(); request1._arg0 = 'org.pimslims.applet.server.TaskBean'; request1._arg1 = 'getListWithFields'; if self.select==None: request1._arg2 = '' else: wsstr_in = WSString(self.select) request1._arg2 = wsstr_in.str response1 = port.getList(request1) wsstr1 = WSString(response1._return) ss1 = wsstr1.getStruct() matrix = []; objs = []; for el in ss1: new_row = (el['serial'], 'TestTask1', 'jionides', el['status']) matrix.append(new_row) objs.append(el) self.task_matrix.update(objectList=objs, textMatrix=matrix) self.filter.grid(row=2, column=2, sticky='n') # FIXME JMCI # The tabbed frame seems to cause the GUI to hang over expansion. # use a simple radio button for now # self.daemonFrame.grid(row=3, column=2, padx=10, sticky='nsew') self.daemonSwitchLabel.grid(row=3, column=2, padx=10, sticky='n') self.daemonSwitch.grid(row=4, column=2, padx=10, sticky='n') self.autoRefreshSwitchLabel.grid(row=6, column=1, padx=10, sticky='w') self.autoRefreshSwitch.grid(row=6, column=1, padx=10, sticky='e') def selectTask(self): row = self.task_matrix.currentCell print 'in select task ', row def set_daemon(self, text): print 'setting daemon ', text if text == 'on': self.basePopup.taskDaemon.active = True else: self.basePopup.taskDaemon.active = False def set_refresh(self, text): print 'setting refresh ', text if text == 'on': self.autoRefresh = True else: self.autoRefresh = False def refresh(self): if self.autoRefresh: print 'refreshing frame ', time.time() self.drawFrame() self.after(5000, self.refresh) def goto_task_tab(self, obj, row, col): print obj self.basePopup.currentTask = obj['serial'].__str__() # This is really awkward because we actually have to go to the # correct tab. We have some horrible hacks here. Need a dictionary # that can take us straight to the correct frame based on a # keyword self.basePopup.tabbedFrame.select(2) #for ff in self.basePopup.tabbedFrame.frames[2].children.values(): # ff.tabbedFrame.select(0) if self.basePopup.frameShortcuts.has_key('Task'): taskFrame = self.basePopup.frameShortcuts['Task'] # really need to check on the type of task if taskFrame.frameShortcuts.has_key('Test1'): taskFrame.frameShortcuts['Test1'].drawFrame() # also need to select the current tabbed frame self.basePopup.tabbedFrame.select(2) def administerNotifiers(self, notifyFunc): for func in ('__init__','delete','setName'): notifyFunc(self.updateAllAfter, 'ccp.nmr.Nmr.Experiment', func) notifyFunc(self.updateAllAfter, 'ccp.nmr.Nmr.DataSource', func) def updateAllAfter(self, obj): self.after_idle(self.updateAll) def updateAll(self, project=None): return def quit(self): self.guiParent.parent.destroy() def destroy(self): #self.administerNotifiers(self.basePopup.unregisterNotify) Frame.destroy(self)
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 CingGui(BasePopup): def __init__(self, parent, options, *args, **kw): # Fill in below variable once run generates some results self.haveResults = None # store the options self.options = options BasePopup.__init__(self, parent=parent, title='CING Setup', **kw) # self.setGeometry(850, 750, 50, 50) self.project = None # self.tk_strictMotif( True) self.updateGui() # end def __init__ def body(self, guiFrame): row = 0 col =0 # frame = Frame( guiFrame ) # frame.grid(row=row, column=col, sticky='news') self.menuBar = Menu( guiFrame) self.menuBar.grid( row=row, column=col, sticky='ew') #---------------------------------------------------------------------------------- # Project frame #---------------------------------------------------------------------------------- # guiFrame.grid_columnconfigure(row, weight=1) # frame = LabelFrame(guiFrame, text='Project', font=medFont) row = +1 col =0 frame = LabelFrame(guiFrame, text='Project', **labelFrameAttributes ) print '>', frame.keys() frame.grid(row=row, column=col, sticky='nsew' ) frame.grid_columnconfigure(2, weight=1) # frame.grid_rowconfigure(0, weight=1) srow = 0 self.projectOptions = ['old','new from PDB','new from CCPN','new from CYANA'] self.projOptionsSelect = RadioButtons(frame, selected_index=0, entries=self.projectOptions, direction='vertical', select_callback=self.updateGui ) self.projOptionsSelect.grid(row=srow,column=0,rowspan=len(self.projectOptions),columnspan=2, sticky='w') if self.options.name: text = self.options.name else: text='' # end if self.projEntry = Entry(frame, bd=1, text=text, returnCallback=self.updateGui) self.projEntry.grid(row=srow,column=2,columnspan=2,sticky='ew') # self.projEntry.bind('<Key>', self.updateGui) self.projEntry.bind('<Leave>', self.updateGui) projButton = Button(frame, bd=1,command=self.chooseOldProjectFile, text='browse') projButton.grid(row=srow,column=3,sticky='ew') srow += 1 self.pdbEntry = Entry(frame, bd=1, text='') self.pdbEntry.grid(row=srow,column=2,sticky='ew') self.pdbEntry.bind('<Leave>', self.updateGui) pdbButton = Button(frame, bd=1,command=self.choosePdbFile, text='browse') pdbButton.grid(row=srow,column=3,sticky='ew') srow += 1 self.ccpnEntry = Entry(frame, bd=1, text='') self.ccpnEntry.grid(row=srow,column=2,sticky='ew') self.ccpnEntry.bind('<Leave>', self.updateGui) ccpnButton = Button(frame, bd=1,command=self.chooseCcpnFile, text='browse') ccpnButton.grid(row=srow,column=3,sticky='ew') srow += 1 self.cyanaEntry = Entry(frame, bd=1, text='') self.cyanaEntry.grid(row=srow,column=2,sticky='ew') self.cyanaEntry.bind('<Leave>', self.updateGui) cyanaButton = Button(frame, bd=1,command=self.chooseCyanaFile, text='browse') cyanaButton.grid(row=srow,column=3,sticky='ew') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow,column=0,sticky='nw') srow += 1 label = Label(frame, text='Project name:') label.grid(row=srow,column=0,sticky='nw') self.nameEntry = Entry(frame, bd=1, text='') self.nameEntry.grid(row=srow,column=2,sticky='w') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow,column=0,sticky='nw') srow += 1 self.openProjectButton = Button(frame, command=self.openProject, text='Open Project', **actionButtonAttributes ) self.openProjectButton.grid(row=srow,column=0, columnspan=4, sticky='ew') #---------------------------------------------------------------------------------- # status #---------------------------------------------------------------------------------- # guiFrame.grid_columnconfigure(1, weight=0) srow = 0 frame = LabelFrame(guiFrame, text='Status', **labelFrameAttributes) frame.grid( row=srow, column=1, sticky='wnes') self.projectStatus = Text(frame, height=11, width=70, borderwidth=0, relief='flat') self.projectStatus.grid(row=0, column=0, sticky='wen') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow,column=0,sticky='nw') srow += 1 self.closeProjectButton = Button(frame, command=self.closeProject, text='Close Project', **actionButtonAttributes) self.closeProjectButton.grid(row=srow,column=0, columnspan=4, sticky='ew') #---------------------------------------------------------------------------------- # Validate frame #---------------------------------------------------------------------------------- row +=1 col=0 frame = LabelFrame(guiFrame, text='Validate', **labelFrameAttributes) # frame = LabelFrame(guiFrame, text='Validate', font=medFont) frame.grid(row=row, column=col, sticky='nsew') # frame.grid_columnconfigure(2, weight=1) frame.grid_rowconfigure(0, weight=1) srow = 0 # label = Label(frame, text='validation') # label.grid(row=srow,column=0,sticky='nw') # # self.selectDoValidation = CheckButton(frame) # self.selectDoValidation.grid(row=srow, column=1,sticky='nw' ) # self.selectDoValidation.set(True) # # srow += 1 # label = Label(frame, text='') # label.grid(row=srow,column=0,sticky='nw') # # srow += 1 label = Label(frame, text='checks') label.grid(row=srow,column=0,sticky='nw') self.selectCheckAssign = CheckButton(frame) self.selectCheckAssign.grid(row=srow, column=1,sticky='nw' ) self.selectCheckAssign.set(True) label = Label(frame, text='assignments and shifts') label.grid(row=srow,column=2,sticky='nw') # srow += 1 # self.selectCheckQueen = CheckButton(frame) # self.selectCheckQueen.grid(row=srow, column=4,sticky='nw' ) # self.selectCheckQueen.set(False) # label = Label(frame, text='QUEEN') # label.grid(row=srow,column=5,sticky='nw') # # queenButton = Button(frame, bd=1,command=None, text='setup') # queenButton.grid(row=srow,column=6,sticky='ew') srow += 1 self.selectCheckResraint = CheckButton(frame) self.selectCheckResraint.grid(row=srow, column=1,sticky='nw' ) self.selectCheckResraint.set(True) label = Label(frame, text='restraints') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectCheckStructure = CheckButton(frame) self.selectCheckStructure.grid(row=srow, column=1,sticky='nw' ) self.selectCheckStructure.set(True) label = Label(frame, text='structural') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectMakeHtml = CheckButton(frame) self.selectMakeHtml.grid(row=srow, column=1,sticky='nw' ) self.selectMakeHtml.set(True) label = Label(frame, text='generate HTML') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectCheckScript = CheckButton(frame) self.selectCheckScript.grid(row=srow, column=1,sticky='nw' ) self.selectCheckScript.set(False) label = Label(frame, text='user script') label.grid(row=srow,column=0,sticky='nw') self.validScriptEntry = Entry(frame, bd=1, text='') self.validScriptEntry.grid(row=srow,column=2,columnspan=3, sticky='ew') scriptButton = Button(frame, bd=1,command=self.chooseValidScript, text='browse') scriptButton.grid(row=srow,column=5,sticky='ew') srow += 1 label = Label(frame, text='ranges') label.grid(row=srow,column=0,sticky='nw') self.rangesEntry = Entry( frame, text='' ) self.rangesEntry.grid( row=srow, column=2, columnspan=3, sticky='ew') # self.validScriptEntry = Entry(frame, bd=1, text='') # self.validScriptEntry.grid(row=srow,column=3,sticky='ew') # # scriptButton = Button(frame, bd=1,command=self.chooseValidScript, text='browse') # scriptButton.grid(row=srow,column=4,sticky='ew') srow += 1 texts = ['Run Validation','View Results','Setup QUEEN'] commands = [self.runCing, None, None] buttonBar = ButtonList(frame, texts=texts, commands=commands,expands=True) buttonBar.grid(row=srow, column=0, columnspan=6, sticky='ew') for button in buttonBar.buttons: button.config(**actionButtonAttributes) # end for self.runButton = buttonBar.buttons[0] self.viewResultButton = buttonBar.buttons[1] self.queenButton = buttonBar.buttons[2] #---------------------------------------------------------------------------------- # Miscellaneous frame #---------------------------------------------------------------------------------- row +=0 col=1 # frame = LabelFrame(guiFrame, text='Miscellaneous', font=medFont) frame = LabelFrame(guiFrame, text='Miscellaneous', **labelFrameAttributes) frame.grid(row=row, column=col, sticky='news') frame.grid_columnconfigure(2, weight=1) frame.grid_columnconfigure(4, weight=1,minsize=30) frame.grid_rowconfigure(0, weight=1) # Exports srow = 0 label = Label(frame, text='export to') label.grid(row=srow,column=0,sticky='nw') self.selectExportXeasy = CheckButton(frame) self.selectExportXeasy.grid(row=srow, column=1,sticky='nw' ) self.selectExportXeasy.set(True) label = Label(frame, text='Xeasy, Sparky, TALOS, ...') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectExportCcpn = CheckButton(frame) self.selectExportCcpn.grid(row=srow, column=1,sticky='nw' ) self.selectExportCcpn.set(True) label = Label(frame, text='CCPN') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectExportQueen = CheckButton(frame) self.selectExportQueen.grid(row=srow, column=1,sticky='nw' ) self.selectExportQueen.set(True) label = Label(frame, text='QUEEN') label.grid(row=srow,column=2,sticky='nw') srow += 1 self.selectExportRefine = CheckButton(frame) self.selectExportRefine.grid(row=srow, column=1,sticky='nw' ) self.selectExportRefine.set(True) label = Label(frame, text='refine') label.grid(row=srow,column=2,sticky='nw') srow += 1 label = Label(frame, text='') label.grid(row=srow,column=0,sticky='nw') # User script srow += 1 label = Label(frame, text='user script') label.grid(row=srow,column=0,sticky='nw') self.selectMiscScript = CheckButton(frame) self.selectMiscScript.grid(row=srow, column=1,sticky='nw' ) self.selectMiscScript.set(False) self.miscScriptEntry = Entry(frame, bd=1, text='') self.miscScriptEntry.grid(row=srow,column=3,sticky='ew') script2Button = Button(frame, bd=1,command=self.chooseMiscScript, text='browse') script2Button.grid(row=srow,column=4,sticky='ew') srow += 1 texts = ['Export','Run Script'] commands = [None, None] buttonBar = ButtonList(frame, texts=texts, commands=commands,expands=True) buttonBar.grid(row=srow, column=0, columnspan=5, sticky='ew') for button in buttonBar.buttons: button.config(**actionButtonAttributes) # end for self.exportButton = buttonBar.buttons[0] self.scriptButton = buttonBar.buttons[1] #---------------------------------------------------------------------------------- # Textarea #---------------------------------------------------------------------------------- row +=1 guiFrame.grid_rowconfigure(row, weight=1) self.outputTextBox = ScrolledText(guiFrame) self.outputTextBox.grid(row=row, column=0, columnspan=2, sticky='nsew') self.redirectConsole() #---------------------------------------------------------------------------------- # Buttons #---------------------------------------------------------------------------------- row +=1 col=0 texts = ['Quit', 'Help'] commands = [self.close, None] self.buttonBar = ButtonList(guiFrame, texts=texts, commands=commands,expands=True) self.buttonBar.grid(row=row, column=col, columnspan=2, sticky='ew') # self.openProjectButton = self.buttonBar.buttons[0] # self.closeProjectButton = self.buttonBar.buttons[1] # self.runButton = self.buttonBar.buttons[0] # self.viewResultButton = self.buttonBar.buttons[1] for button in self.buttonBar.buttons: button.config(**actionButtonAttributes) # end for # end def body def getGuiOptions(self): projectName = self.projEntry.get() index = self.projOptionsSelect.getIndex() if index > 0: makeNewProject = True projectImport = None if index > 1: i = index-2 format = ['PDB','CCPN','CYANA'][i] file = [self.pdbEntry, self.ccpnEntry, self.cyanaEntry][i].get() if not file: showWarning('Failure','No %s file selected' % format) return # end if projectImport = (format, file) # end if else: # Chould also check that any old project file exists makeNewProject = False projectImport = None # end if doValidation = self.selectDoValidation.get() checks = [] if doValidation: if self.selectCheckAssign.get(): checks.append('assignments') # end if if self.selectCheckResraint.get(): checks.append('restraints') # end if if self.selectCheckStructure.get(): checks.append('structural') # end if if self.selectMakeHtml.get(): checks.append('HTML') # end if if self.selectCheckScript.get(): script = self.validScriptEntry.get() if script: checks.append( ('script',script) ) # end if # end if if self.selectCheckQueen.get(): checks.append('queen') # end if # end if exports = [] if self.selectExportXeasy.get(): exports.append('Xeasy') # end if if self.selectExportCcpn.get(): exports.append('CCPN') # end if if self.selectExportQueen.get(): exports.append('QUEEN') # end if if self.selectExportRefine.get(): exports.append('refine') # end if miscScript = None if self.selectMiscScript.get(): script = self.miscScriptEntry.get() if script: miscScript = script # end if # end if return projectName, makeNewProject, projectImport, doValidation, checks, exports, miscScript # end def getGuiOptions def runCing(self): options = self.getGuiOptions() if options: projectName, makeNewProject, projectImport, doValidation, checks, exports, miscScript = options print 'Project name:', projectName print 'Make new project?', makeNewProject print 'Import source:', projectImport print 'Do vailidation?', doValidation print 'Validation checks:', ','.join(checks) print 'Export to:', ','.join(exports) print 'User script:', miscScript # end if # end def runCing # else there was already an error message def chooseOldProjectFile(self): fileTypes = [ FileType('CING', ['project.xml']), FileType('All', ['*']) ] popup = FileSelectPopup(self, file_types = fileTypes, title = 'Select CING project file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() # dirName = popup.getDirectory() if len(fileName) > 0: # Put text into entry,name widgets dummy,name = cing.Project.rootPath(fileName) self.projEntry.configure(state='normal') self.projEntry.set(fileName) self.nameEntry.configure(state='normal') self.nameEntry.set(name) self.nameEntry.configure(state='disabled') # choose the correct radiobutton self.projOptionsSelect.setIndex(0) self.updateGui() # end if #nd if popup.destroy() # end def chooseOldProjectFile def choosePdbFile(self): fileTypes = [ FileType('PDB', ['*.pdb']), FileType('All', ['*'])] popup = FileSelectPopup(self, file_types = fileTypes, title = 'PDB file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() if len(fileName)>0: # Put text into entry widget self.pdbEntry.configure(state='normal') self.pdbEntry.set(fileName) # Put text into name widget _dir,name,dummy = nTpath( fileName ) self.nameEntry.configure(state='normal') self.nameEntry.set(name) # choose the correct radiobutton self.projOptionsSelect.setIndex(1) self.updateGui() #end if popup.destroy() # end def choosePdbFile def chooseCcpnFile(self): fileTypes = [ FileType('XML', ['*.xml']), FileType('All', ['*'])] popup = FileSelectPopup(self, file_types = fileTypes, title = 'CCPN project XML file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() if len(fileName)>0: self.pdbEntry.configure(state='normal') self.pdbEntry.set(fileName) self.projOptionsSelect.setIndex(1) _dir,name,dummy = nTpath( fileName ) self.nameEntry.set(name) #end if self.ccpnEntry.set(fileName) self.projOptionsSelect.setIndex(2) popup.destroy() # end def chooseCcpnFile def chooseCyanaFile(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types = fileTypes, title = 'CYANA fproject file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() self.cyanaEntry.set(fileName) self.projOptionsSelect.setIndex(3) popup.destroy() # end def chooseCyanaFile def chooseValidScript(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types = fileTypes, title = 'Script file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() self.validScriptEntry.set(fileName) popup.destroy() # end def chooseValidScript def chooseMiscScript(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types = fileTypes, title = 'Script file', dismiss_text = 'Cancel', selected_file_must_exist = True) fileName = popup.getFile() self.miscScriptEntry.set(fileName) popup.destroy() # end def chooseMiscScript def openProject(self ): projOption = self.projOptionsSelect.get() if projOption == self.projectOptions[0]: self.openOldProject() elif projOption == self.projectOptions[1]: self.initPdb() # end if if self.project: self.project.gui = self # end if self.updateGui() #end def def openOldProject(self ): fName = self.projEntry.get() if not os.path.exists( fName ): nTerror('Error: file "%s" does not exist\n', fName) #end if if self.project: self.closeProject() # end if self.project = cing.Project.open( name=fName, status='old', verbose=False ) #end def def initPdb(self ): fName = self.pdbEntry.get() if not os.path.exists( fName ): nTerror('Error: file "%s" does not exist\n', fName) #end if self.project = cing.Project.open( self.nameEntry.get(), status='new' ) self.project.initPDB( pdbFile=fName, convention = 'PDB' ) #end def def closeProject(self): if self.project: self.project.close() # end if self.project = None self.updateGui() #end def def updateGui(self, event=None): projOption = self.projOptionsSelect.get() buttons = self.buttonBar.buttons # Disable entries for e in [self.projEntry, self.pdbEntry, self.ccpnEntry, self.cyanaEntry, self.nameEntry]: e.configure(state='disabled') #end for if projOption == self.projectOptions[0]: # Enable entries self.projEntry.configure(state='normal') if (len(self.projEntry.get()) > 0): self.openProjectButton.enable() self.runButton.enable() else: self.openProjectButton.disable() self.runButton.disable() #end if elif projOption == self.projectOptions[1]: # Enable entries self.pdbEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.pdbEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if elif projOption == self.projectOptions[2]: # Enable entries self.ccpnEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.ccpnEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if elif projOption == self.projectOptions[3]: # Enable entries self.cyanaEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.cyanaEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if self.projectStatus.clear() if not self.project: self.projectStatus.setText('No open project') self.closeProjectButton.setText('Close Project') self.closeProjectButton.disable() else: self.projectStatus.setText(self.project.format()) self.closeProjectButton.enable() self.closeProjectButton.setText(sprintf('Close Project "%s"', self.project.name)) #end if #end def def redirectConsole(self): #pipe = TextPipe(self.inputTextBox.text_area) #sys.stdin = pipe pipe = TextPipe(self.outputTextBox.text_area) sys.stdout = pipe nTmessage.stream = pipe # end def redirectConsole # sys.stderr = pipe def resetConsole(self): #sys.stdin = stdin nTmessage.stream = stdout sys.stdout = stdout sys.stderr = stderr # end def resetConsole def open(self): self.redirectConsole() BasePopup.open(self) # end def open def close(self): geometry = self.getGeometry() self.resetConsole() BasePopup.close(self) print 'close:',geometry sys.exit(0) # remove later # end def close def destroy(self): geometry = self.getGeometry() self.resetConsole() BasePopup.destroy(self) print 'destroy:',geometry sys.exit(0) # remove later
class PeakSeparatorGui(BasePopup): """ **Separate Merged Peaks Using Peak Models** The Peak Separator code uses a Markov Chain Monte Carlo search which, using idealised peak shapes, attempts to deconvolve overlapped peak regions into their separate constituent peaks. This routine is also suitable for accurately fitting model shapes to single peaks in order to calculate precise intensities. **Options Peak Separator Parameters** *Min. Number of peaks* is by default set to one, it is not possible to set this to a value less than one. *Max. Number of peaks* is by default set to one, increasing this value allows the search routine to fit more models. The best fit may be found with fewer than the maximum number models. Higher numbers slow the routine, and setting this value to 0 allows the routine to (effectively) fit unlimited peaks. *Only pick positive peaks*. If you are not interested in negative peaks, removing the possibility of fitting negative peaks can reduce search time. *Peak Model* fits the spectra with either a Gaussian peak model or a Lorentzian peak model. **Options Region** *Peak List* choose which peak list newly picked peaks should be added to. Peaks picked using this method will have their details appended with 'PeakSepartor' so you know where they came from. *Region Table* shows which area of the current spectrum is about to be searched. *Add Region*. Once an area of spectra has been highlighted clicking this button will pass it's details on to the Peak Separator. *Reset All* will reset all search parameters. *Separate Peaks* will run the Peak Separator code with your current settings. This may take a few minutes to run, depending on the size of the spectral region being searched, the number of peaks being fitted and the speed of your machine. Please wait while this completes. After a successful Peak Separation run, the found peaks will be added to the selected peak list. These peaks intensties (volume) have been found using the peak model selected. **Advanced Settings Tab** *Rate* affects the speed of the Markov Chain Monte Carlo routine. A smaller value results in longer execution, but possibly higher quality results. The default setting is deemed sensible for the majority of runs. *Line Width* offers a finer degree of control over maximum and minimum peak widths for each dimension. The default values are *very* stupid and could do with re-checking for each experiment. *Re-Pick Entire Peak List* if you would like to use the Peak Separator to repick *every* peak in your peak list, try this option - but note that this may take a very long time! """ def __init__(self, parent, programName='Peak Separator', **kw): self.parent = parent self.programName = programName self.versionInfo = 'Version 0.2' self.help_url = 'http://www.ccpn.ac.uk/' self.window = None self.waiting = False self.rootWindow = None # just used for display - PeakSeparator will not see this self._minSigmaHz = None self._maxSigmaHz = None self.customSigma = False self.rePickPeakList = False self._sampleStartPpm = None self._sampleEndPpm = None try: self.project = parent.project except: pass self.params = PeakSeparatorParams() BasePopup.__init__(self, parent=parent, title=programName, location='+100+100', **kw) if not self.analysisProject: print '&&& init: No analysis project found ...' try: if parent.argumentServer: self.argServer = parent.argumentServer else: print '&&& init: No argument server found...' except: print '&&& init: Test' ########################################################################### def body(self, guiFrame): self.geometry('450x500') guiFrame.grid_rowconfigure(0, weight=1) guiFrame.grid_columnconfigure(0, weight=1) options = ['Peak Separator', 'Advanced Settings'] tabbedFrame = TabbedFrame(guiFrame, options=options) tabbedFrame.grid(row=0, column=0, sticky='nsew') buttons = UtilityButtonList(tabbedFrame.sideFrame, helpUrl=self.help_url) buttons.grid(row=0, column=0, sticky='e') self.tabbedFrame = tabbedFrame frameA, frameB = tabbedFrame.frames # # FrameA : Main Settings # frameA.grid_columnconfigure(1, weight=1) row = 0 # Label row row += 1 div = LabelDivider(frameA, text='Peak Separator Parameters') div.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 label = Label(frameA, text='Min. number of peaks:') label.grid(row=row, column=0, sticky='w') self.minPeaksEntry = IntEntry(frameA, returnCallback=self.applyChange, width=10, \ tipText='Minimum number of peaks to find (must be > 0)') self.minPeaksEntry.grid(row=row, column=1, sticky='n') self.minPeaksEntry.bind('<Leave>', self.applyChange, '+') row += 1 label = Label(frameA, text='Max. number of peaks:') label.grid(row=row, column=0, sticky='w') self.maxPeaksEntry = IntEntry(frameA, returnCallback=self.applyChange, width=10, \ tipText='Maximum number of peaks to find (0 is unlimited - not recommended)') self.maxPeaksEntry.grid(row=row, column=1, sticky='n') self.maxPeaksEntry.bind('<Leave>', self.applyChange, '+') row += 1 label = Label(frameA, text='Only pick positive peaks:') label.grid(row=row, column=0, sticky='w') entries = ['False', 'True'] self.posPeaksButtons = RadioButtons( frameA, entries=entries, select_callback=self.applyChange, direction='horizontal', tipTexts=[ 'Search for both positive and negative intensity peaks', 'Limit search to only positive peaks' ]) self.posPeaksButtons.grid(row=row, column=1, sticky='n') row += 1 label = Label(frameA, text='Peak Model:') label.grid(row=row, column=0, sticky='w') ### G/L Mixture works, but volume calculation involves Gamma function # entries = ['Gaussian', 'Lorentzian', 'G/L Mixture'] entries = ['Gaussian', 'Lorentzian'] self.shapeButtons = RadioButtons( frameA, entries=entries, select_callback=self.applyChange, direction='horizontal', tipTexts=[ 'Choose a Gaussian model peak shape to fit to peaks', 'Choose a Lorentzian model peak shape to fit to peaks' ]) self.shapeButtons.grid(row=row, column=1, sticky='n') row += 1 div = LabelDivider(frameA, text='Region', tipText='Region that search will limit itself to') div.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 label = Label(frameA, text='Peak List:') label.grid(row=row, column=0, sticky='nw') self.peakListPulldown = PulldownList( frameA, callback=self.setManuallyPickPeakList, tipText='Select which peak list new peaks are to be added to') self.peakListPulldown.grid(row=row, column=1, sticky='nw') # tricky scrolled matrix row += 1 self.regionTable = None frameA.grid_rowconfigure(row, weight=1) headings = ('dim.', 'start (ppm)', 'end (ppm)', 'actual size') self.editDimEntry = IntEntry(self, returnCallback=self.applyChange, width=5, tipText='Dimension number') self.editStartEntry = FloatEntry(self, returnCallback=self.applyChange, width=5, tipText='Search area lower bound') self.editEndEntry = FloatEntry(self, returnCallback=self.applyChange, width=5, tipText='Search area upper bound') editWidgets = [ self.editDimEntry, self.editStartEntry, self.editEndEntry, None ] editGetCallbacks = [None, None, None, None] editSetCallbacks = [None, None, None, None] self.regionTable = ScrolledMatrix(frameA, headingList=headings, multiSelect=False, editWidgets=editWidgets, editGetCallbacks=editGetCallbacks, editSetCallbacks=editSetCallbacks, initialRows=5) self.regionTable.grid(row=row, column=0, columnspan=2, sticky='nsew') # Run Button row += 1 texts = ['Add Region'] commands = [self.updateFromRegion] self.addResetButtons = ButtonList( frameA, texts=texts, commands=commands, tipTexts=['Add selected specrtral region']) self.addResetButtons.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 texts = ['Separate Peaks'] commands = [self.runPeakSeparator] self.runButton = ButtonList(frameA, texts=texts, commands=commands, expands=True, tipTexts=['Run peak search now']) self.runButton.grid(row=row, column=0, columnspan=2, sticky='nsew') # # FrameB : Further Settings # frameB.grid_columnconfigure(0, weight=1) row = 0 div = LabelDivider(frameB, text='Rate:') div.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 label = Label(frameB, text='Rate of MCMC step size change') label.grid(row=row, column=0, columnspan=1, sticky='w') self.rateEntry = FloatEntry(frameB, returnCallback=self.applyChange, width=10, \ tipText='Rate effects speed of run, smaller values take longer but may produce better results') self.rateEntry.grid(row=row, column=1, sticky='n') self.rateEntry.bind('<Leave>', self.applyChange, '+') self.rateEntry.set(self.params.rate) # tricky scrolled matrix for line width row += 2 div = LabelDivider(frameB, text='Line Width (Hz):') div.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 label = Label(frameB, text="Descr.") label.grid(row=row, rowspan=2, column=0, sticky='w') row += 1 self.lineWidthTable = None frameB.grid_rowconfigure(row, weight=1) lineWidthHeadings = ('dim.', 'min. σ (Hz)', 'max. σ (Hz)') self.editMinSigmaEntry = FloatEntry(self, returnCallback=self.applyChange, width=5, tipText='Minimum line width (Hz)') self.editMaxSigmaEntry = FloatEntry(self, returnCallback=self.applyChange, width=5, tipText='Maximum line width (Hz)') # self.editDimEntry is also from regionTable initialWidthRows = 4 editLineWidthWidgets = [ None, self.editMinSigmaEntry, self.editMaxSigmaEntry ] editLineWidthGetCallbacks = [None, self.getSigmaMin, self.getSigmaMax] editLineWidthSetCallbacks = [None, self.setSigmaMin, self.setSigmaMax] self.lineWidthTable = ScrolledMatrix( frameB, headingList=lineWidthHeadings, multiSelect=False, editWidgets=editLineWidthWidgets, editGetCallbacks=editLineWidthGetCallbacks, editSetCallbacks=editLineWidthSetCallbacks, initialRows=initialWidthRows) self.lineWidthTable.grid(row=row, column=0, columnspan=2, sticky='nsew') # option to 'repick' exisiting peak list row += initialWidthRows div = LabelDivider(frameB, text='(optional - repick entire peak list)') div.grid(row=row, column=0, columnspan=2, sticky='ew') row += 1 self.repickListPulldown = PulldownList( frameB, callback=self.setRePickPeakList, tipText= 'Select which peak list to repick (new peaks will be put into a new peak list)' ) self.repickListPulldown.grid(row=row, column=0, sticky='nw') texts = ['Repick Peak List'] commands = [self.runRepickPeaks] self.runButton = ButtonList( frameB, texts=texts, commands=commands, expands=True, tipTexts=['Repick selected peak list into a new peak list.']) self.runButton.grid(row=row, column=1, columnspan=1, sticky='nsew') row += 1 div = LabelDivider(frameB) row += 1 texts = ['Separate Peaks'] commands = [self.runPeakSeparator] self.runButton = ButtonList(frameB, texts=texts, commands=commands, expands=True, tipTexts=['Run peak search now']) self.runButton.grid(row=row, column=0, columnspan=2, sticky='nsew') self.setWidgetEntries() self.administerNotifiers(self.registerNotify) def administerNotifiers(self, notifyFunc): for func in ('__init__', 'delete'): notifyFunc(self.updateAfter, 'ccp.nmr.Nmr.PeakList', func) notifyFunc(self.updateAfter, 'ccp.nmr.Nmr.Experiment', 'setName') notifyFunc(self.updateAfter, 'ccp.nmr.Nmr.DataSource', 'setName') def destroy(self): self.administerNotifiers(self.unregisterNotify) BasePopup.destroy(self) ########################################################################### # update parameters from PS Region def updateFromRegion(self): if not self.params.peakList: print '&&& update from region: Need a peak list' return if (self.argServer.parent.currentRegion) == None: showError('No Region', 'Please select a peak region to be separated') return self.rePickPeakList = False getRegionParams(self.params, argServer=self.argServer) if not self.customSigma: self.initSigmaParams() self.setWidgetEntries() ########################################################################### # update parameters from PS PeakList def updateFromPeakList(self): if not self.params.peakList: print '&&& update from peakList: Need a peak list' return getPeakListParams(self.params) if not self.customSigma: self.initSigmaParams() self.setWidgetEntries() ########################################################################### # Run the C library! def runPeakSeparator(self): """ run the peak separator """ # hack for Macs - focus isn't always lost on mouse move # so bind event not always called. Shouldn't affect other OS. self.applyChange() if not self.params.peakList: print '&&& Peak list not yet set' else: # SeparatePeakRoutine(self.params, self.params.peakList, routine='pymc' ) SeparatePeakRoutine(self.params, self.params.peakList, routine='bayesys') def runRepickPeaks(self): """ Run the Peak Separator on entire chosen peak list """ # hack for Macs - focus isn't always lost on mouse move # so bind event not always called. Shouldn't affect other OS. self.applyChange() if not self.params.peakList: print '&&& Peak list not yet set' else: SeparatePeaksInPeakList(self.params) ########################################################################### def setWidgetEntries(self): ### Page One widgets self.minPeaksEntry.set(self.params.minAtoms) self.maxPeaksEntry.set(self.params.maxAtoms) if self.params.positivePeaks == 1: self.posPeaksButtons.set('True') # only pick pos peaks else: self.posPeaksButtons.set('False') # do something fancy if different shapes for each dim! n = self.params.peakShape - 3 # shape is only 3, 4, (5) self.shapeButtons.setIndex(n) if self.project is not None: self.updatePeakListList() self.updateSpectrumWindow() if self.params.sampleStart and self.params.peakList: if not self.rePickPeakList: objectList = [] textMatrix = [] if len(self.params.samplePpmStart) != self.params.Ndim: return for i in range(self.params.Ndim): dim_entry = [] dim_entry.append('%2d' % (i + 1)) dim_entry.append('%7.3f' % self.params.samplePpmStart[i]) dim_entry.append('%7.3f' % self.params.samplePpmEnd[i]) dim_entry.append('%3d' % self.params.sampleSize[i]) textMatrix.append(dim_entry) self.regionTable.update(textMatrix=textMatrix, objectList=objectList) ### Page Two widgets self.rateEntry.set(self.params.rate) if self.params.peakList and self.params.Ndim: textMatrix = [] objectList = [] for i in range(self.params.Ndim): if self.params.isFreqDim[i]: dim_entry = [] objectList.append(i) dim_entry.append('%2d' % (i + 1)) dim_entry.append('%7.3f' % self._minSigmaHz[i]) dim_entry.append('%7.3f' % self._maxSigmaHz[i]) textMatrix.append(dim_entry) self.lineWidthTable.update(textMatrix=textMatrix, objectList=objectList) def applyChange(self, *event): """ Upon change, add settings to params """ # Page One apply changes self.params.minAtoms = self.minPeaksEntry.get() self.params.maxAtoms = self.maxPeaksEntry.get() if self.posPeaksButtons.get() == 'True': # asked only pick pos peaks self.params.positivePeaks = 1 else: self.params.positivePeaks = 0 # do something fancy if different shapes for each dim! n = self.shapeButtons.getIndex() # shape is only 3, 4, (5) self.params.peakShape = n + 3 # Page Two apply changes self.params.rate = float(self.rateEntry.get()) self.updateSigmaParams() ########################################################################### # Peak list functions provide PeakSeparator some inherited params def getPeakListList(self): """ given a spectrum, get list of peak lists """ project = self.project peakLists = [] for experiment in self.nmrProject.experiments: for spectrum in experiment.dataSources: for peakList in spectrum.peakLists: peakLists.append([ '%s:%s:%d' % (experiment.name, spectrum.name, peakList.serial), peakList ]) peakLists.sort() return peakLists def updatePeakListList(self): """ set the peaklist list in the pulldown menu """ peakListData = self.getPeakListList() index = -1 names = [] peakList = self.params.peakList if peakListData: names = [x[0] for x in peakListData] peakLists = [x[1] for x in peakListData] if peakList not in peakLists: peakList = peakLists[0] index = peakLists.index(peakList) else: peakList = None peakLists = [] if peakList is not self.params.peakList: self.params.peakList = peakList self.peakListPulldown.setup(names, peakLists, index) self.repickListPulldown.setup(names, peakLists, index) def setRePickPeakList(self, peakList): """ Set the peak list to be repicked (and hit a Flag) """ self.rePickPeakList = True self.setPeakList(peakList) def setManuallyPickPeakList(self, peakList): """ Set the peak list to add new peaks to (and hit a Flag) """ self.rePickPeakList = False self.setPeakList(peakList) def setPeakList(self, peakList): """ Sets the Peak List """ if peakList is not self.params.peakList: self.params.peakList = peakList # # interrogate the peak list and get all the usefull parameters out self.updateFromPeakList() self.updateSpectrumWindow() self.setWidgetEntries() ########################################################################### # TBD I suspect this is for matching region with peak list, but may be obsolete now def getSpectrumWindowList(self): """ get list of windows which spectrum could be in """ windows = {} if self.params.peakList: views = getSpectrumViews(self.params.peakList.dataSource) for view in views: windows[view.spectrumWindowPane.spectrumWindow] = None return [[w.name, w] for w in windows.keys()] def updateSpectrumWindow(self): """ update the spectrum window """ windowData = self.getSpectrumWindowList() index = -1 names = [] window = self.rootWindow if windowData: names = [x[0] for x in windowData] windows = [x[1] for x in windowData] if window not in windows: window = windows[0] index = windows.index(window) else: window = None windows = [] if window is not self.rootWindow: self.rootWindow = window ########################################################################### # get and set sigma stuff def setSigmaMin(self, dim): value = self.editMinSigmaEntry.get() self._minSigmaHz[dim] = value # dont go and re-write users settings self.customSigma = True # make sure changes are in params object self.updateSigmaParams(dim) self.setWidgetEntries() def getSigmaMin(self, dim): if dim is not None: self.editMinSigmaEntry.set(self._minSigmaHz[dim]) def setSigmaMax(self, dim): value = self.editMaxSigmaEntry.get() self._maxSigmaHz[dim] = value # dont go and re-write users settings self.customSigma = True # make sure changes are in params object self.updateSigmaParams(dim) self.setWidgetEntries() def getSigmaMax(self, dim): if dim is not None: self.editMaxSigmaEntry.set(self._maxSigmaHz[dim]) def updateSigmaParams(self, dim=None): """ updateSigmaParams Just updates the parameters (params obj) for sigma values. If dim is None, do this for each dim """ dataDimRefs = self.params.dataDimRefs if not dataDimRefs: return if not self.params.minSigma or len( self.params.minSigma) != self.params.Ndim: self.params.minSigma = [0.] * self.params.Ndim if not self.params.maxSigma or len( self.params.maxSigma) != self.params.Ndim: self.params.maxSigma = [0.] * self.params.Ndim def updateSigmaParam(dim, dataDimRefs): """ Convert and update sigma for dim """ if self.params.isFreqDim[dim]: # note factor of two! self.params.minSigma[dim] = self.rHz2pnt( self._minSigmaHz[dim], dataDimRefs[dim]) / 2. self.params.maxSigma[dim] = self.rHz2pnt( self._maxSigmaHz[dim], dataDimRefs[dim]) / 2. else: self.params.minSigma[dim] = 1.0 self.params.maxSigma[dim] = 1.0 if dim: updateSigmaParam(dim, dataDimRefs) else: for dim in range(self.params.Ndim): updateSigmaParam(dim, dataDimRefs) # utility functions for sigma values def pnt2rHz(self, point, dataDimRef): """ Point to relative Hz frequency relative to frequency at Zeroeth point Necessary when (for example) looking for width of peak in Hz """ assert point, dataDimRef sigmaBase = pnt2hz(0, dataDimRef) sigmaHz = pnt2hz(point, dataDimRef) return abs(sigmaHz - sigmaBase) def rHz2pnt(self, freq, dataDimRef): """ Relative Hz to point frequency relative to frequency at Zeroeth point Necessary when (for example) looking for width of peak in Hz """ assert freq, dataDimRef sigmaBase = hz2pnt(0, dataDimRef) sigmaPoint = hz2pnt(freq, dataDimRef) return abs(sigmaPoint - sigmaBase) def initSigmaParams(self): """ Set some initial default values for sigma """ self._minSigmaHz = [] self._maxSigmaHz = [] if self.params.Ndim: for dim in range(self.params.Ndim): self._minSigmaHz.append(6.) self._maxSigmaHz.append(28.) ########################################################################### def updateAll(self): self.updateSpectrumWindow() self.updatePeakListList() self.waiting = False def updateAfter(self, obj=None): if self.waiting: return else: self.waiting = True self.after_idle(self.updateAll)
class RepositoryFrame(Frame): def __init__(self, guiParent, basePopup): # Base popup required to handle notification of data model changes # e.g. new peak lists, so that the GUI can update to the latest # state self.basePopup = basePopup self.guiParent = guiParent # should the screen autorefresh self.autoRefresh = False # add this to shortcuts to ease navigation self.basePopup.frameShortcuts['Repository'] = self # get a port proxy instance # this should probably belong to the repository directly # or else should belong in a dictionary in the main gui # layer when it can be picked up easily # FIXME JMCI # need to work out how to get a number of these! loc = SharedBeanServiceLocator() self.port = loc.getSharedBean() self.registerNotify = basePopup.registerNotify self.unregisterNotify = basePopup.unregisterNotify Frame.__init__(self, guiParent) # set up the grid self.grid_columnconfigure(0, weight=0, minsize=20) self.grid_columnconfigure(1, weight=1, minsize=10) self.grid_columnconfigure(2, weight=0, minsize=20) self.grid_rowconfigure(0, weight=0, minsize=5) self.grid_rowconfigure(1, weight=0, minsize=0) self.grid_rowconfigure(2, weight=0, minsize=10) self.grid_rowconfigure(3, weight=0, minsize=10) self.grid_rowconfigure(4, weight=0, minsize=10) self.grid_rowconfigure(5, weight=1, minsize=10) self.grid_rowconfigure(6, weight=0, minsize=10) self.grid_rowconfigure(7, weight=0, minsize=10) # widgets for view when no data self.noDataWidgets = [] self.noRepLabel = Label(self, text='No repository currently selected.') self.noDataWidgets.append(self.noRepLabel) # widgets for view when current repository set self.dataWidgets = [] self.repTitle = Label(self, text='Repository:', font='Helvetica16') self.dataWidgets.append(self.repTitle) #self.repLabel = Label(self,text='All Projects in Repository') #self.dataWidgets.append(self.repLabel) self.repTree = Tree(self, doubleCallback=self.goto_project_tab) self.dataWidgets.append(self.repTree) sel = 1 if self.autoRefresh: sel = 0 self.autoRefreshSwitchLabel = Label(self, text='Auto Refresh') self.autoRefreshSwitch = RadioButtons(self, ['on', 'off'], select_callback=self.set_refresh, selected_index=sel) # need to decide whether this is static or not r_button_texts = [ 'Add to Basket', ' Import ', ' Export ', ' Refresh ', 'Properties' ] r_button_cmds = [ self.tmpCall, self.import_project, self.export_project, self.drawFrame, self.goto_project_tab ] self.rep_button_list = ButtonList(self, r_button_texts, r_button_cmds) self.dataWidgets.append(self.rep_button_list) self.filterFrame = FilterFrame(self, self.basePopup, text='Filter') self.dataWidgets.append(self.filterFrame) baskets = ('basket1', 'basket2', 'basket3') self.basketSelect = PulldownList(self, self.tmpCall, baskets) self.dataWidgets.append(self.basketSelect) basketElements = ('1ay3', '1ay7') self.basketList = ScrolledListbox(self, basketElements, 25, 18) self.dataWidgets.append(self.basketList) b_button_texts = ['Remove from Basket', 'New Basket'] b_button_cmds = [self.tmpCall, self.tmpCall] self.b_button_list = ButtonList(self, b_button_texts, b_button_cmds) self.dataWidgets.append(self.b_button_list) # draw if not automatically refreshing if sel == 1: self.drawFrame() # set up a loop self.refresh() def drawFrame(self): if self.basePopup.repList.currentRepository == None: for widget in self.dataWidgets: widget.grid_remove() self.noRepLabel.grid(row=1, column=1, sticky='n') else: self.repository = self.basePopup.repList.currentRepository for widget in self.noDataWidgets: widget.grid_remove() # Column headers # want to have a general admin panel; current repository, button to change, info # about login and so on self.repTitle.set('Repository: ' + self.repository.user + '@' + self.repository.name + ' ( ' + self.repository.connect + ' )') self.repTitle.grid(row=1, column=1, sticky='w') # self.repLabel.grid(row=2, column=1, sticky='w') # Repository block #grid and update self.repTree.grid(row=3, column=1, rowspan=3, sticky='nsew') self.updateRepTree() self.autoRefreshSwitchLabel.grid(row=6, column=1, padx=10, sticky='w') self.autoRefreshSwitch.grid(row=6, column=1, padx=10, sticky='e') # the buttons for functionality in repository area self.rep_button_list.grid(row=7, column=1, padx=3, sticky='ew') # filter frame self.filterFrame.grid(row=3, column=2, stick='nsew') # list of baskest. Will callback to change current basket self.basketSelect.grid(row=4, column=2, padx=10, stick='w') # lists projects per basket self.basketList.grid(row=5, rowspan=2, column=2, padx=10, stick='nsew') self.b_button_list.grid(row=7, column=2, padx=5, stick='ew') def openLink(self, node): tree = node.tree par = node.object # this should be associated with the repository object request = getList() # FIXME JMCI # 1. Potentially need to traverse up the node tree # 2. Currently there is bug in expansion/contraction # 3. Search needs to work off proxy method (not off # generated stubs # pass the parent name for now. may need other criteria later h1 = {'name': par.__str__()} h2 = {'project': h1} wsstr_in = WSString(h2) request._arg0 = 'org.pimslims.applet.server.ProjectVersionBean' request._arg1 = 'getListWithFields' request._arg2 = wsstr_in.str # get the response response = self.port.getList(request) # currently we just get a list of numbers. May want to send # all the fields for every object too to cut down on db calls wsstr_out = WSString(response._return) ss = wsstr_out.getStruct() for hm in ss: print 'handling ', hm, ', ', hm['status'].__str__() #if hm['status'].__str__() == 'AVAILABLE': icon = 'text-x-generic' #else: # icon='emblem-readonly' pv = par.__str__() + '::' + hm['versionTag'].__str__() obj = pv text = hm['versionTag'].__str__() callback = None tree.add(node, obj, text, icon, callback) def set_refresh(self, text): print 'setting refresh ', text if text == 'on': self.autoRefresh = True else: self.autoRefresh = False def refresh(self): if self.autoRefresh: print 'refreshing frame ', time.time() self.drawFrame() self.after(5000, self.refresh) # FIME JMCI # it would probably be a good idea to have a method that allowed # a user to unlock a given project version. Would need to check # permissions very carefully, though def unlock_project_version(self): pass def goto_project_tab(self, node=None): if node is None: # get the selected node selected_nodes = self.repTree.getSelectedNodes() # restrict the choice to one node = selected_nodes[0] # we really need to traverse the tree a lot more carefully pv = node.object.__str__() print 'GOTO PROJECT ', pv, ', ', node, ', ', node.object pat = re.compile('::') matcher = pat.search(pv, 0) name = pv[0:matcher.start()] versionTag = pv[matcher.end():] print 'GOTO PROJECT ', name, ', ', versionTag #versionTag = node.object.__str__() #name = node.parent.object.__str__() #print node.__dict__ #print node.parent.__dict__ self.basePopup.repList.currentRepository.currentProjectName = name self.basePopup.repList.currentRepository.currentVersionTag = versionTag # this is going to have to be keyed on a natural key that then # gets set into the criteria of a ws query # hack for now. build in later. Essentially, we have to handle two # cases; that of a specific projectVersion request and that of a # request on a project alone. Probably the best behaviour would be # for the project-only request to default to the latest trunk # version of the project and the most elegent way of triggering # this would probably be to have this as a property of the project # returned in the main hash from Project.getFields(). self.basePopup.tabbedFrame.select(1) if self.basePopup.frameShortcuts.has_key('Project'): self.basePopup.frameShortcuts['Project'].drawFrame() def import_project(self): # FIXME JMCI # need to preserve the current status. Take default from the # Wms layer rootDir = self.basePopup.repList.current_import_dir fileSelectPopup = FileSelectPopup(self, None, rootDir) new_project_dir = fileSelectPopup.getDirectory() self.basePopup.repList.current_import_dir = new_project_dir print 'in import project with directory', new_project_dir idx = new_project_dir.rfind('/') new_project_name = new_project_dir[idx + 1:] print 'in import project with project', new_project_name # FIXME # need to set the project version number somewhere. For now set to none # and this gets picked up and set to a default 1.1 later self.repository.import_project(new_project_name, None, new_project_dir) self.drawFrame() def export_project(self): # get the selected node selected_nodes = self.repTree.getSelectedNodes() # restrict the choice to one node = selected_nodes[0] # we really need to traverse the tree a lot more carefully name = node.parent.object.__str__() versionTag = node.object.__str__()[len(name) + 2:] # need to preserve the current status. Take a default from the # Wms layer rootDir = self.basePopup.repList.current_export_dir # This should be obtained from a query box. Hard code for now fileSelectPopup = FileSelectPopup(self, None, rootDir) exp_project_dir = fileSelectPopup.getDirectory() self.basePopup.repList.current_export_dir = exp_project_dir self.repository.export_project(name, versionTag, exp_project_dir) def disconnectRepository(self): # do we need to formally break a connection and destroy the session? # yes we probably should. # need an "are you sure" dialog box # need to protect self.repository.repList.repositories.remove(self.repository) self.grid_remove() for ff in self.guiParent.guiParent.parent.frames[0].children.values(): ff.drawFrame() def tmpCall(self): return # This will need a separate call to the WS with an additional # criterion (picking up the checkout version) def updateRepTree(self): texts = [] icons = [] parents = [] callbacks = [] objects = [] # OK, this would be a good point to access the list # this should be associated with the repository object loc = SharedBeanServiceLocator() port = loc.getSharedBean() request = getList() # these are actually static request._arg0 = 'org.pimslims.applet.server.ProjectBean' request._arg1 = 'getList' request._arg2 = '' # get the response response = port.getList(request) # this is a hack at present. It needs to be written properly wsstr = WSString(response._return) ss = wsstr.getStruct() for strg in ss: texts.append(strg) icons.append('folder') parents.append(None) objects.append(strg) callbacks.append(self.openLink) print 'UPDATE ', ss print 'UPDATE ', len(ss) if len(ss) > 0: print 'UPDATE: updating ' self.repTree.update(parents, objects, texts, icons, callbacks) def administerNotifiers(self, notifyFunc): for func in ('__init__', 'delete', 'setName'): notifyFunc(self.updateAllAfter, 'ccp.nmr.Nmr.Experiment', func) notifyFunc(self.updateAllAfter, 'ccp.nmr.Nmr.DataSource', func) def updateAllAfter(self, obj): self.after_idle(self.updateAll) def updateAll(self, project=None): return def quit(self): self.guiParent.parent.destroy() def destroy(self): self.administerNotifiers(self.basePopup.unregisterNotify) Frame.destroy(self)
class CingGui(BasePopup): def __init__(self, parent, options, *args, **kw): # Fill in below variable once run generates some results self.haveResults = None # store the options self.options = options BasePopup.__init__(self, parent=parent, title='CING Setup', **kw) # self.setGeometry(850, 750, 50, 50) self.project = None # self.tk_strictMotif( True) self.updateGui() # end def __init__ def body(self, guiFrame): row = 0 col = 0 # frame = Frame( guiFrame ) # frame.grid(row=row, column=col, sticky='news') self.menuBar = Menu(guiFrame) self.menuBar.grid(row=row, column=col, sticky='ew') #---------------------------------------------------------------------------------- # Project frame #---------------------------------------------------------------------------------- # guiFrame.grid_columnconfigure(row, weight=1) # frame = LabelFrame(guiFrame, text='Project', font=medFont) row = +1 col = 0 frame = LabelFrame(guiFrame, text='Project', **labelFrameAttributes) print '>', frame.keys() frame.grid(row=row, column=col, sticky='nsew') frame.grid_columnconfigure(2, weight=1) # frame.grid_rowconfigure(0, weight=1) srow = 0 self.projectOptions = [ 'old', 'new from PDB', 'new from CCPN', 'new from CYANA' ] self.projOptionsSelect = RadioButtons(frame, selected_index=0, entries=self.projectOptions, direction='vertical', select_callback=self.updateGui) self.projOptionsSelect.grid(row=srow, column=0, rowspan=len(self.projectOptions), columnspan=2, sticky='w') if self.options.name: text = self.options.name else: text = '' # end if self.projEntry = Entry(frame, bd=1, text=text, returnCallback=self.updateGui) self.projEntry.grid(row=srow, column=2, columnspan=2, sticky='ew') # self.projEntry.bind('<Key>', self.updateGui) self.projEntry.bind('<Leave>', self.updateGui) projButton = Button(frame, bd=1, command=self.chooseOldProjectFile, text='browse') projButton.grid(row=srow, column=3, sticky='ew') srow += 1 self.pdbEntry = Entry(frame, bd=1, text='') self.pdbEntry.grid(row=srow, column=2, sticky='ew') self.pdbEntry.bind('<Leave>', self.updateGui) pdbButton = Button(frame, bd=1, command=self.choosePdbFile, text='browse') pdbButton.grid(row=srow, column=3, sticky='ew') srow += 1 self.ccpnEntry = Entry(frame, bd=1, text='') self.ccpnEntry.grid(row=srow, column=2, sticky='ew') self.ccpnEntry.bind('<Leave>', self.updateGui) ccpnButton = Button(frame, bd=1, command=self.chooseCcpnFile, text='browse') ccpnButton.grid(row=srow, column=3, sticky='ew') srow += 1 self.cyanaEntry = Entry(frame, bd=1, text='') self.cyanaEntry.grid(row=srow, column=2, sticky='ew') self.cyanaEntry.bind('<Leave>', self.updateGui) cyanaButton = Button(frame, bd=1, command=self.chooseCyanaFile, text='browse') cyanaButton.grid(row=srow, column=3, sticky='ew') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow, column=0, sticky='nw') srow += 1 label = Label(frame, text='Project name:') label.grid(row=srow, column=0, sticky='nw') self.nameEntry = Entry(frame, bd=1, text='') self.nameEntry.grid(row=srow, column=2, sticky='w') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow, column=0, sticky='nw') srow += 1 self.openProjectButton = Button(frame, command=self.openProject, text='Open Project', **actionButtonAttributes) self.openProjectButton.grid(row=srow, column=0, columnspan=4, sticky='ew') #---------------------------------------------------------------------------------- # status #---------------------------------------------------------------------------------- # guiFrame.grid_columnconfigure(1, weight=0) srow = 0 frame = LabelFrame(guiFrame, text='Status', **labelFrameAttributes) frame.grid(row=srow, column=1, sticky='wnes') self.projectStatus = Text(frame, height=11, width=70, borderwidth=0, relief='flat') self.projectStatus.grid(row=0, column=0, sticky='wen') #Empty row srow += 1 label = Label(frame, text='') label.grid(row=srow, column=0, sticky='nw') srow += 1 self.closeProjectButton = Button(frame, command=self.closeProject, text='Close Project', **actionButtonAttributes) self.closeProjectButton.grid(row=srow, column=0, columnspan=4, sticky='ew') #---------------------------------------------------------------------------------- # Validate frame #---------------------------------------------------------------------------------- row += 1 col = 0 frame = LabelFrame(guiFrame, text='Validate', **labelFrameAttributes) # frame = LabelFrame(guiFrame, text='Validate', font=medFont) frame.grid(row=row, column=col, sticky='nsew') # frame.grid_columnconfigure(2, weight=1) frame.grid_rowconfigure(0, weight=1) srow = 0 # label = Label(frame, text='validation') # label.grid(row=srow,column=0,sticky='nw') # # self.selectDoValidation = CheckButton(frame) # self.selectDoValidation.grid(row=srow, column=1,sticky='nw' ) # self.selectDoValidation.set(True) # # srow += 1 # label = Label(frame, text='') # label.grid(row=srow,column=0,sticky='nw') # # srow += 1 label = Label(frame, text='checks') label.grid(row=srow, column=0, sticky='nw') self.selectCheckAssign = CheckButton(frame) self.selectCheckAssign.grid(row=srow, column=1, sticky='nw') self.selectCheckAssign.set(True) label = Label(frame, text='assignments and shifts') label.grid(row=srow, column=2, sticky='nw') # srow += 1 # self.selectCheckQueen = CheckButton(frame) # self.selectCheckQueen.grid(row=srow, column=4,sticky='nw' ) # self.selectCheckQueen.set(False) # label = Label(frame, text='QUEEN') # label.grid(row=srow,column=5,sticky='nw') # # queenButton = Button(frame, bd=1,command=None, text='setup') # queenButton.grid(row=srow,column=6,sticky='ew') srow += 1 self.selectCheckResraint = CheckButton(frame) self.selectCheckResraint.grid(row=srow, column=1, sticky='nw') self.selectCheckResraint.set(True) label = Label(frame, text='restraints') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectCheckStructure = CheckButton(frame) self.selectCheckStructure.grid(row=srow, column=1, sticky='nw') self.selectCheckStructure.set(True) label = Label(frame, text='structural') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectMakeHtml = CheckButton(frame) self.selectMakeHtml.grid(row=srow, column=1, sticky='nw') self.selectMakeHtml.set(True) label = Label(frame, text='generate HTML') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectCheckScript = CheckButton(frame) self.selectCheckScript.grid(row=srow, column=1, sticky='nw') self.selectCheckScript.set(False) label = Label(frame, text='user script') label.grid(row=srow, column=0, sticky='nw') self.validScriptEntry = Entry(frame, bd=1, text='') self.validScriptEntry.grid(row=srow, column=2, columnspan=3, sticky='ew') scriptButton = Button(frame, bd=1, command=self.chooseValidScript, text='browse') scriptButton.grid(row=srow, column=5, sticky='ew') srow += 1 label = Label(frame, text='ranges') label.grid(row=srow, column=0, sticky='nw') self.rangesEntry = Entry(frame, text='') self.rangesEntry.grid(row=srow, column=2, columnspan=3, sticky='ew') # self.validScriptEntry = Entry(frame, bd=1, text='') # self.validScriptEntry.grid(row=srow,column=3,sticky='ew') # # scriptButton = Button(frame, bd=1,command=self.chooseValidScript, text='browse') # scriptButton.grid(row=srow,column=4,sticky='ew') srow += 1 texts = ['Run Validation', 'View Results', 'Setup QUEEN'] commands = [self.runCing, None, None] buttonBar = ButtonList(frame, texts=texts, commands=commands, expands=True) buttonBar.grid(row=srow, column=0, columnspan=6, sticky='ew') for button in buttonBar.buttons: button.config(**actionButtonAttributes) # end for self.runButton = buttonBar.buttons[0] self.viewResultButton = buttonBar.buttons[1] self.queenButton = buttonBar.buttons[2] #---------------------------------------------------------------------------------- # Miscellaneous frame #---------------------------------------------------------------------------------- row += 0 col = 1 # frame = LabelFrame(guiFrame, text='Miscellaneous', font=medFont) frame = LabelFrame(guiFrame, text='Miscellaneous', **labelFrameAttributes) frame.grid(row=row, column=col, sticky='news') frame.grid_columnconfigure(2, weight=1) frame.grid_columnconfigure(4, weight=1, minsize=30) frame.grid_rowconfigure(0, weight=1) # Exports srow = 0 label = Label(frame, text='export to') label.grid(row=srow, column=0, sticky='nw') self.selectExportXeasy = CheckButton(frame) self.selectExportXeasy.grid(row=srow, column=1, sticky='nw') self.selectExportXeasy.set(True) label = Label(frame, text='Xeasy, Sparky, TALOS, ...') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectExportCcpn = CheckButton(frame) self.selectExportCcpn.grid(row=srow, column=1, sticky='nw') self.selectExportCcpn.set(True) label = Label(frame, text='CCPN') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectExportQueen = CheckButton(frame) self.selectExportQueen.grid(row=srow, column=1, sticky='nw') self.selectExportQueen.set(True) label = Label(frame, text='QUEEN') label.grid(row=srow, column=2, sticky='nw') srow += 1 self.selectExportRefine = CheckButton(frame) self.selectExportRefine.grid(row=srow, column=1, sticky='nw') self.selectExportRefine.set(True) label = Label(frame, text='refine') label.grid(row=srow, column=2, sticky='nw') srow += 1 label = Label(frame, text='') label.grid(row=srow, column=0, sticky='nw') # User script srow += 1 label = Label(frame, text='user script') label.grid(row=srow, column=0, sticky='nw') self.selectMiscScript = CheckButton(frame) self.selectMiscScript.grid(row=srow, column=1, sticky='nw') self.selectMiscScript.set(False) self.miscScriptEntry = Entry(frame, bd=1, text='') self.miscScriptEntry.grid(row=srow, column=3, sticky='ew') script2Button = Button(frame, bd=1, command=self.chooseMiscScript, text='browse') script2Button.grid(row=srow, column=4, sticky='ew') srow += 1 texts = ['Export', 'Run Script'] commands = [None, None] buttonBar = ButtonList(frame, texts=texts, commands=commands, expands=True) buttonBar.grid(row=srow, column=0, columnspan=5, sticky='ew') for button in buttonBar.buttons: button.config(**actionButtonAttributes) # end for self.exportButton = buttonBar.buttons[0] self.scriptButton = buttonBar.buttons[1] #---------------------------------------------------------------------------------- # Textarea #---------------------------------------------------------------------------------- row += 1 guiFrame.grid_rowconfigure(row, weight=1) self.outputTextBox = ScrolledText(guiFrame) self.outputTextBox.grid(row=row, column=0, columnspan=2, sticky='nsew') self.redirectConsole() #---------------------------------------------------------------------------------- # Buttons #---------------------------------------------------------------------------------- row += 1 col = 0 texts = ['Quit', 'Help'] commands = [self.close, None] self.buttonBar = ButtonList(guiFrame, texts=texts, commands=commands, expands=True) self.buttonBar.grid(row=row, column=col, columnspan=2, sticky='ew') # self.openProjectButton = self.buttonBar.buttons[0] # self.closeProjectButton = self.buttonBar.buttons[1] # self.runButton = self.buttonBar.buttons[0] # self.viewResultButton = self.buttonBar.buttons[1] for button in self.buttonBar.buttons: button.config(**actionButtonAttributes) # end for # end def body def getGuiOptions(self): projectName = self.projEntry.get() index = self.projOptionsSelect.getIndex() if index > 0: makeNewProject = True projectImport = None if index > 1: i = index - 2 format = ['PDB', 'CCPN', 'CYANA'][i] file = [self.pdbEntry, self.ccpnEntry, self.cyanaEntry][i].get() if not file: showWarning('Failure', 'No %s file selected' % format) return # end if projectImport = (format, file) # end if else: # Chould also check that any old project file exists makeNewProject = False projectImport = None # end if doValidation = self.selectDoValidation.get() checks = [] if doValidation: if self.selectCheckAssign.get(): checks.append('assignments') # end if if self.selectCheckResraint.get(): checks.append('restraints') # end if if self.selectCheckStructure.get(): checks.append('structural') # end if if self.selectMakeHtml.get(): checks.append('HTML') # end if if self.selectCheckScript.get(): script = self.validScriptEntry.get() if script: checks.append(('script', script)) # end if # end if if self.selectCheckQueen.get(): checks.append('queen') # end if # end if exports = [] if self.selectExportXeasy.get(): exports.append('Xeasy') # end if if self.selectExportCcpn.get(): exports.append('CCPN') # end if if self.selectExportQueen.get(): exports.append('QUEEN') # end if if self.selectExportRefine.get(): exports.append('refine') # end if miscScript = None if self.selectMiscScript.get(): script = self.miscScriptEntry.get() if script: miscScript = script # end if # end if return projectName, makeNewProject, projectImport, doValidation, checks, exports, miscScript # end def getGuiOptions def runCing(self): options = self.getGuiOptions() if options: projectName, makeNewProject, projectImport, doValidation, checks, exports, miscScript = options print 'Project name:', projectName print 'Make new project?', makeNewProject print 'Import source:', projectImport print 'Do vailidation?', doValidation print 'Validation checks:', ','.join(checks) print 'Export to:', ','.join(exports) print 'User script:', miscScript # end if # end def runCing # else there was already an error message def chooseOldProjectFile(self): fileTypes = [FileType('CING', ['project.xml']), FileType('All', ['*'])] popup = FileSelectPopup(self, file_types=fileTypes, title='Select CING project file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() # dirName = popup.getDirectory() if len(fileName) > 0: # Put text into entry,name widgets dummy, name = cing.Project.rootPath(fileName) self.projEntry.configure(state='normal') self.projEntry.set(fileName) self.nameEntry.configure(state='normal') self.nameEntry.set(name) self.nameEntry.configure(state='disabled') # choose the correct radiobutton self.projOptionsSelect.setIndex(0) self.updateGui() # end if #nd if popup.destroy() # end def chooseOldProjectFile def choosePdbFile(self): fileTypes = [FileType('PDB', ['*.pdb']), FileType('All', ['*'])] popup = FileSelectPopup(self, file_types=fileTypes, title='PDB file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() if len(fileName) > 0: # Put text into entry widget self.pdbEntry.configure(state='normal') self.pdbEntry.set(fileName) # Put text into name widget _dir, name, dummy = nTpath(fileName) self.nameEntry.configure(state='normal') self.nameEntry.set(name) # choose the correct radiobutton self.projOptionsSelect.setIndex(1) self.updateGui() #end if popup.destroy() # end def choosePdbFile def chooseCcpnFile(self): fileTypes = [FileType('XML', ['*.xml']), FileType('All', ['*'])] popup = FileSelectPopup(self, file_types=fileTypes, title='CCPN project XML file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() if len(fileName) > 0: self.pdbEntry.configure(state='normal') self.pdbEntry.set(fileName) self.projOptionsSelect.setIndex(1) _dir, name, dummy = nTpath(fileName) self.nameEntry.set(name) #end if self.ccpnEntry.set(fileName) self.projOptionsSelect.setIndex(2) popup.destroy() # end def chooseCcpnFile def chooseCyanaFile(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types=fileTypes, title='CYANA fproject file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() self.cyanaEntry.set(fileName) self.projOptionsSelect.setIndex(3) popup.destroy() # end def chooseCyanaFile def chooseValidScript(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types=fileTypes, title='Script file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() self.validScriptEntry.set(fileName) popup.destroy() # end def chooseValidScript def chooseMiscScript(self): # Prepend default Cyana file extension below fileTypes = [ FileType('All', ['*']), ] popup = FileSelectPopup(self, file_types=fileTypes, title='Script file', dismiss_text='Cancel', selected_file_must_exist=True) fileName = popup.getFile() self.miscScriptEntry.set(fileName) popup.destroy() # end def chooseMiscScript def openProject(self): projOption = self.projOptionsSelect.get() if projOption == self.projectOptions[0]: self.openOldProject() elif projOption == self.projectOptions[1]: self.initPdb() # end if if self.project: self.project.gui = self # end if self.updateGui() #end def def openOldProject(self): fName = self.projEntry.get() if not os.path.exists(fName): nTerror('Error: file "%s" does not exist\n', fName) #end if if self.project: self.closeProject() # end if self.project = cing.Project.open(name=fName, status='old', verbose=False) #end def def initPdb(self): fName = self.pdbEntry.get() if not os.path.exists(fName): nTerror('Error: file "%s" does not exist\n', fName) #end if self.project = cing.Project.open(self.nameEntry.get(), status='new') self.project.initPDB(pdbFile=fName, convention='PDB') #end def def closeProject(self): if self.project: self.project.close() # end if self.project = None self.updateGui() #end def def updateGui(self, event=None): projOption = self.projOptionsSelect.get() buttons = self.buttonBar.buttons # Disable entries for e in [ self.projEntry, self.pdbEntry, self.ccpnEntry, self.cyanaEntry, self.nameEntry ]: e.configure(state='disabled') #end for if projOption == self.projectOptions[0]: # Enable entries self.projEntry.configure(state='normal') if (len(self.projEntry.get()) > 0): self.openProjectButton.enable() self.runButton.enable() else: self.openProjectButton.disable() self.runButton.disable() #end if elif projOption == self.projectOptions[1]: # Enable entries self.pdbEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.pdbEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if elif projOption == self.projectOptions[2]: # Enable entries self.ccpnEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.ccpnEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if elif projOption == self.projectOptions[3]: # Enable entries self.cyanaEntry.configure(state='normal') self.nameEntry.configure(state='normal') if (len(self.cyanaEntry.get()) > 0 and len(self.nameEntry.get()) > 0): buttons[0].enable() buttons[1].enable() else: buttons[0].disable() buttons[1].disable() #end if #end if self.projectStatus.clear() if not self.project: self.projectStatus.setText('No open project') self.closeProjectButton.setText('Close Project') self.closeProjectButton.disable() else: self.projectStatus.setText(self.project.format()) self.closeProjectButton.enable() self.closeProjectButton.setText( sprintf('Close Project "%s"', self.project.name)) #end if #end def def redirectConsole(self): #pipe = TextPipe(self.inputTextBox.text_area) #sys.stdin = pipe pipe = TextPipe(self.outputTextBox.text_area) sys.stdout = pipe nTmessage.stream = pipe # end def redirectConsole # sys.stderr = pipe def resetConsole(self): #sys.stdin = stdin nTmessage.stream = stdout sys.stdout = stdout sys.stderr = stderr # end def resetConsole def open(self): self.redirectConsole() BasePopup.open(self) # end def open def close(self): geometry = self.getGeometry() self.resetConsole() BasePopup.close(self) print 'close:', geometry sys.exit(0) # remove later # end def close def destroy(self): geometry = self.getGeometry() self.resetConsole() BasePopup.destroy(self) print 'destroy:', geometry sys.exit(0) # remove later
class WidgetCountPopup(BasePopup): on_off_entries = ['on', 'off'] def __init__(self, parent, help_msg='', help_url='', *args, **kw): self.help_msg = help_msg self.help_url = help_url BasePopup.__init__(self, parent=parent, title='Widget Count', *args, **kw) def body(self, master): self.alarm_id = None self.root_widget = getRoot(self) row = 0 label = Label(master, text='Widget count:') label.grid(row=row, column=0, sticky=Tkinter.W) self.count_label = Label(master, text='', tipText='Number of Tkinter widget objects') self.count_label.grid(row=row, column=1, sticky=Tkinter.W) row = row + 1 ind = 1 label = Label(master, text='Auto count:') label.grid(row=row, column=0, sticky=Tkinter.W) self.on_off_buttons = RadioButtons(master, entries=self.on_off_entries, select_callback=self.applyAuto, selected_index=ind) self.on_off_buttons.grid(row=row, column=1, sticky=Tkinter.EW) row = row + 1 label = Label(master, text='Auto frequency:') label.grid(row=row, column=0, sticky=Tkinter.W) self.freq_entry = IntEntry(master, text=60, returnCallback=self.applyAuto) self.freq_entry.grid(row=row, column=1, sticky=Tkinter.EW) label = Label(master, text='seconds') label.grid(row=row, column=2, sticky=Tkinter.W) row = row + 1 texts = ['Do Immediate Count'] commands = [self.applyManual] buttons = createDismissHelpButtonList(master, texts=texts, commands=commands, help_msg=self.help_msg, help_url=self.help_url) buttons.grid(row=row, column=0, columnspan=3, sticky=Tkinter.EW) self.doCount() def applyAuto(self, *event): on_off = self.on_off_buttons.get() if on_off == 'on': self.setCountOn() else: self.setCountOff() def applyManual(self): self.doCount() def setCountOn(self): self.setCountOff() freq = self.freq_entry.get() if freq is not None and freq > 0: freq *= 1000 # convert from sec to msec self.alarm_id = self.after(freq, self.doCountAuto) def setCountOff(self): if self.alarm_id: self.after_cancel(self.alarm_id) self.alarm_id = None def doCountAuto(self): if self.on_off_buttons.get() == 'on': self.doCount() freq = self.freq_entry.get() if freq is not None and freq > 0: freq *= 1000 # convert from sec to msec self.alarm_id = self.after(freq, self.doCountAuto) def doCount(self): count = getWidgetCount(self.root_widget) self.count_label.set('%d' % count)