""" Python script for a GUI-dialog. Description: Python script to provide an abstract GUI for other python scripts. That way we've all the GUI-related code within one single file and are able to easily modify GUI-stuff in a central place. Author: Sebastian Sauer Copyright: Published as-is without any warranties. """ def getHome(): """ Return the homedirectory. """ import os try: home = os.getenv("HOME") if not home: import pwd user = os.getenv("USER") or os.getenv("LOGNAME") if not user: pwent = pwd.getpwuid(os.getuid()) else: pwent = pwd.getpwnam(user) home = pwent[6] return home except (KeyError, ImportError): return os.curdir class TkDialog: """ This class is used to wrap Tkinter into a more abstract interface.""" def __init__(self, title): import tkinter self.root = tkinter.Tk() self.root.title(title) self.root.deiconify() mainframe = self.Frame(self, self.root) self.widget = mainframe.widget class Widget: def __init__(self, dialog, parent): self.dialog = dialog self.parent = parent #def setVisible(self, visibled): pass #def setEnabled(self, enabled): pass class Frame(Widget): def __init__(self, dialog, parent): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter self.widget = tkinter.Frame(parent) self.widget.pack() class Label(Widget): def __init__(self, dialog, parent, caption): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter self.widget = tkinter.Label(parent, text=caption) self.widget.pack(side=tkinter.TOP) class CheckBox(Widget): def __init__(self, dialog, parent, caption, checked = True): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter self.checkstate = tkinter.IntVar() self.checkstate.set(checked) self.widget = tkinter.Checkbutton(parent, text=caption, variable=self.checkstate) self.widget.pack(side=tkinter.TOP) def isChecked(self): return self.checkstate.get() class List(Widget): def __init__(self, dialog, parent, caption, items): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter listframe = tkinter.Frame(parent) listframe.pack() tkinter.Label(listframe, text=caption).pack(side=tkinter.LEFT) self.items = items self.variable = tkinter.StringVar() itemlist = tkinter.OptionMenu(*(listframe, self.variable) + tuple( items )) itemlist.pack(side=tkinter.LEFT) def get(self): return self.variable.get() def set(self, index): self.variable.set( self.items[index] ) class Button(Widget): def __init__(self, dialog, parent, caption, commandmethod): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter self.widget = tkinter.Button(parent, text=caption, command=self.doCommand) self.commandmethod = commandmethod self.widget.pack(side=tkinter.LEFT) def doCommand(self): try: self.commandmethod() except: #TODO why the heck we arn't able to redirect exceptions? import traceback import io fp = io.StringIO() traceback.print_exc(file=fp) import tkinter.messagebox tkinter.messagebox.showerror("Exception", fp.getvalue()) #self.dialog.root.destroy() class Edit(Widget): def __init__(self, dialog, parent, caption, text): #TkDialog.Widget.__init__(self, dialog, parent) import tkinter self.widget = tkinter.Frame(parent) self.widget.pack() label = tkinter.Label(self.widget, text=caption) label.pack(side=tkinter.LEFT) self.entrytext = tkinter.StringVar() self.entrytext.set(text) self.entry = tkinter.Entry(self.widget, width=36, textvariable=self.entrytext) self.entry.pack(side=tkinter.LEFT) def get(self): return self.entrytext.get() class FileChooser(Edit): def __init__(self, dialog, parent, caption, initialfile = None, filetypes = None): TkDialog.Edit.__init__(self, dialog, parent, caption, initialfile) import tkinter self.initialfile = initialfile self.entrytext.set(initialfile) btn = tkinter.Button(self.widget, text="...", command=self.browse) btn.pack(side=tkinter.LEFT) if filetypes: self.filetypes = filetypes else: self.filetypes = (('All files', '*'),) def browse(self): import os text = self.entrytext.get() d = os.path.dirname(text) or os.path.dirname(self.initialfile) f = os.path.basename(text) or os.path.basename(self.initialfile) import tkinter.filedialog file = tkinter.filedialog.asksaveasfilename( initialdir=d, initialfile=f, #defaultextension='.html', filetypes=self.filetypes ) if file: self.entrytext.set( file ) class MessageBox: def __init__(self, dialog, typename, caption, message): self.widget = dialog.widget self.typename = typename self.caption = str(caption) self.message = str(message) def show(self): import tkinter.messagebox if self.typename == "okcancel": return tkinter.messagebox.askokcancel(self.caption, self.message,icon=tkmessageBox.QESTION) else: tkinter.messagebox.showinfo(self.caption, self.message) return True def show(self): self.root.mainloop() def close(self): self.root.destroy() class TQtDialog: """ This class is used to wrap PyTQt/PyTDE into a more abstract interface.""" def __init__(self, title): from TQt import qt class Dialog(qt.TQDialog): def __init__(self, parent = None, name = None, modal = 0, fl = 0): qt.TQDialog.__init__(self, parent, name, modal, fl) qt.TQDialog.accept = self.accept self.layout = qt.TQVBoxLayout(self) self.layout.setSpacing(6) self.layout.setMargin(11) class Label(qt.TQLabel): def __init__(self, dialog, parent, caption): qt.TQLabel.__init__(self, parent) self.setText("%s" % caption.replace("\n","
")) class Frame(qt.TQHBox): def __init__(self, dialog, parent): qt.TQHBox.__init__(self, parent) self.widget = self self.setSpacing(6) class Edit(qt.TQHBox): def __init__(self, dialog, parent, caption, text): qt.TQHBox.__init__(self, parent) self.setSpacing(6) label = qt.TQLabel(caption, self) self.edit = qt.TQLineEdit(self) self.edit.setText( str(text) ) self.setStretchFactor(self.edit, 1) label.setBuddy(self.edit) def get(self): return self.edit.text() class Button(qt.TQPushButton): #def __init__(self, *args): def __init__(self, dialog, parent, caption, commandmethod): #apply(qt.TQPushButton.__init__, (self,) + args) qt.TQPushButton.__init__(self, parent) self.commandmethod = commandmethod self.setText(caption) qt.TQObject.connect(self, qt.SIGNAL("clicked()"), self.commandmethod) class CheckBox(qt.TQCheckBox): def __init__(self, dialog, parent, caption, checked = True): #TkDialog.Widget.__init__(self, dialog, parent) qt.TQCheckBox.__init__(self, parent) self.setText(caption) self.setChecked(checked) #def isChecked(self): # return self.isChecked() class List(qt.TQHBox): def __init__(self, dialog, parent, caption, items): qt.TQHBox.__init__(self, parent) self.setSpacing(6) label = qt.TQLabel(caption, self) self.combo = qt.TQComboBox(self) self.setStretchFactor(self.combo, 1) label.setBuddy(self.combo) for item in items: self.combo.insertItem( str(item) ) def get(self): return self.combo.currentText() def set(self, index): self.combo.setCurrentItem(index) class FileChooser(qt.TQHBox): def __init__(self, dialog, parent, caption, initialfile = None, filetypes = None): #apply(qt.TQHBox.__init__, (self,) + args) qt.TQHBox.__init__(self, parent) self.setMinimumWidth(400) self.initialfile = initialfile self.filetypes = filetypes self.setSpacing(6) label = qt.TQLabel(caption, self) self.edit = qt.TQLineEdit(self) self.edit.setText(self.initialfile) self.setStretchFactor(self.edit, 1) label.setBuddy(self.edit) browsebutton = Button(dialog, self, "...", self.browseButtonClicked) #qt.TQObject.connect(browsebutton, qt.SIGNAL("clicked()"), self.browseButtonClicked) def get(self): return self.edit.text() def browseButtonClicked(self): filtermask = "" import types if isinstance(self.filetypes, tuple): for ft in self.filetypes: if len(ft) == 1: filtermask += "%s\n" % (ft[0]) if len(ft) == 2: filtermask += "%s|%s (%s)\n" % (ft[1],ft[0],ft[1]) if filtermask == "": filtermask = "All files (*.*)" else: filtermask = filtermask[:-1] filename = None try: print("TQtDialog.FileChooser.browseButtonClicked() tdefile.KFileDialog") # try to use the tdefile module included in pytde import tdefile filename = tdefile.KFileDialog.getOpenFileName(self.initialfile, filtermask, self, "Save to file") except: print("TQtDialog.FileChooser.browseButtonClicked() qt.TQFileDialog") # fallback to TQt filedialog filename = qt.TQFileDialog.getOpenFileName(self.initialfile, filtermask, self, "Save to file") if filename != None and filename != "": self.edit.setText(filename) class MessageBox: def __init__(self, dialog, typename, caption, message): self.widget = dialog.widget self.typename = typename self.caption = str(caption) self.message = str(message) def show(self): result = 1 if self.typename == "okcancel": result = qt.TQMessageBox.question(self.widget, self.caption, self.message, "&Ok", "&Cancel", "", 1) else: qt.TQMessageBox.information(self.widget, self.caption, self.message, "&Ok") result = 0 if result == 0: return True return False self.app = qt.tqApp self.dialog = Dialog(self.app.mainWidget(), "Dialog", 1, qt.TQt.WDestructiveClose) self.dialog.setCaption(title) self.widget = qt.TQVBox(self.dialog) self.widget.setSpacing(6) self.dialog.layout.addWidget(self.widget) self.Frame = Frame self.Label = Label self.Edit = Edit self.Button = Button self.CheckBox = CheckBox self.List = List self.FileChooser = FileChooser self.MessageBox = MessageBox def show(self): from TQt import qt qt.TQApplication.setOverrideCursor(qt.TQt.arrowCursor) self.dialog.exec_loop() qt.TQApplication.restoreOverrideCursor() def close(self): print("TQtDialog.close()") self.dialog.close() #self.dialog.deleteLater() class Dialog: """ Central class that provides abstract GUI-access to the outer world. """ def __init__(self, title): self.dialog = None try: print("Trying to import PyTQt...") self.dialog = TQtDialog(title) print("PyTQt is our toolkit!") except: try: print("Failed to import PyTQt. Trying to import TkInter...") self.dialog = TkDialog(title) print("Falling back to TkInter as our toolkit!") except: raise Exception("Failed to import GUI-toolkit. Please install the PyTQt or the Tkinter python module.") self.widget = self.dialog.widget def show(self): self.dialog.show() def close(self): self.dialog.close() def addFrame(self, parentwidget): return self.dialog.Frame(self.dialog, parentwidget.widget) def addLabel(self, parentwidget, caption): return self.dialog.Label(self.dialog, parentwidget.widget, caption) def addCheckBox(self, parentwidget, caption, checked = True): return self.dialog.CheckBox(self.dialog, parentwidget.widget, caption, checked) def addButton(self, parentwidget, caption, commandmethod): return self.dialog.Button(self.dialog, parentwidget.widget, caption, commandmethod) def addEdit(self, parentwidget, caption, text): return self.dialog.Edit(self.dialog, parentwidget.widget, caption, text) def addFileChooser(self, parentwidget, caption, initialfile = None, filetypes = None): return self.dialog.FileChooser(self.dialog, parentwidget.widget, caption, initialfile, filetypes) def addList(self, parentwidget, caption, items): return self.dialog.List(self.dialog, parentwidget.widget, caption, items) def showMessageBox(self, typename, caption, message): return self.dialog.MessageBox(self.dialog, typename, caption, message)