Source code for tkinterquickhelper.funcwin.main_window

# -*- coding: utf-8 -*-
"""
building windows to use a function and specify its parameter based on a python function


:githublink:`%|py|7`
"""
import os
import warnings
import tkinter
import tkinter.tix as ttix  # pylint: disable=W0402
from tkinter import TclError
from .tk_window import create_tixtk
from .frame_function import FrameFunction
from .storing_functions import get_icon


[docs]class MainFrame(tkinter.Frame): """ Creates a Frame window to select within a list of functions, :class:`FrameFunction <tkinterquickhelper.funcwin.frame_function.FrameFunction>`. The class requires to run ``tix.Tk()`` and not ``tkinter.Tk()``. Otherwise, you will see the following error: :: _tkinter.TclError: invalid command name "tixComboBox" It is required by the use of ``ComboBox``. :func:`main_loop_functions <tkinterquickhelper.funcwin.main_window.main_loop_functions>` to see what the window will look like. :githublink:`%|py|31` """
[docs] def __init__(self, parent, functions, first=None, restore=True, width=100, raise_exception=False, overwrite=None, hide=False): """ :param parent: window parent :param functions: dictionary with a list of functions { name: function } :param first: first function to select :param restore: if True, check if existing saved parameters are present :param width: number of characters in every Entry field :param raise_exception: raise an exception instead of catching it :param overwrite: parameters to overwrite :param hide: if True, hide the window after clicking on OK :githublink:`%|py|44` """ if overwrite is None: overwrite = {} tkinter.Frame.__init__(self, parent) self.kparent = parent self.fsel = tkinter.Frame(self) self.ffun = tkinter.Frame(self) hline = tkinter.Frame(self, height=10, width=800, bg="blue") self.fsel.pack() hline.pack() self.ffun.pack() self.parent = parent self.varcombo = ttix.StringVar() self.combo = ttix.ComboBox(self.fsel, editable=1, dropdown=1, variable=self.varcombo, command=self.change_selection, options="listbox.height %d label.width %d entry.width %d" % (25, 30, 50)) # put the text zone in read only mode self.combo.entry.config(state='readonly') for i, k in enumerate(sorted(functions)): self.combo.insert(i, k) self.combo.pack() self.functionsDict = functions if first is None: keys = sorted(functions.keys()) first = keys[0] firstFunction = functions[first] self.params = {"restore": restore, "width": width, "raise_exception": raise_exception, "overwrite": overwrite, "hide": hide} self.varcombo.set(first) self.change_frame_function(firstFunction)
[docs] def run_cancel(self, *args): """ cancel :githublink:`%|py|83` """ try: self.kparent.destroy() except Exception as e: if "application has been destroyed" in str(e): return else: raise e if "selected" in self.__dict__ and "server" in self.selected.__name__: # trick: the server does not close itself # forcing to close # sys.exit() can only be used from the main thread os._exit(0)
[docs] def get_title(self): """ Returns the default title. :return: string :githublink:`%|py|102` """ return self.frameWindow.get_title()
[docs] def change_frame_function(self, function): """ Updates the frame :class:`FrameFunction <tkinterquickhelper.funcwin.frame_function.FrameFunction>` to select a new function. :param function: a function (a pointer) :githublink:`%|py|110` """ if "selected" not in self.__dict__ or function != self.selected: self.selected = function if hasattr(self, "frameWindow"): self.frameWindow.pack_forget() self.frameWindow = FrameFunction(self.ffun, function, restore=self.params["restore"], width=self.params["width"], raise_exception=self.params[ "raise_exception"], overwrite=self.params["overwrite"], hide=self.params["hide"], command_leave=self.run_cancel) self.frameWindow.pack() self.frameWindow.focus_set()
[docs] def change_selection(self, event): """ Functions called when the selection changes. :githublink:`%|py|131` """ st = self.varcombo.get() if "functionsDict" in self.__dict__: self.change_frame_function(self.functionsDict[st])
[docs]def main_loop_functions(functions, first=None, restore=True, width=100, raise_exception=False, overwrite=None, hide=False, title=None, ico=None, init_pos=None, mainloop=True): """ Uses :class:`MainFrame <tkinterquickhelper.funcwin.main_window.MainFrame>` as the main window. :param functions: dictionary with a list of functions { name: function } :param first: first function to select :param restore: if True, check if existing saved parameters are present :param width: number of characters in every Entry field :param raise_exception: raise an exception instead of catching it :param overwrite: parameters to overwrite :param hide: if True, hide the window after clicking on OK :param title: if not None, overwrite the default title :param ico: (str) an icon or None :param init_pos: location of the window *(x,y)* or None :param mainloop: run the mainloop :return: main window .. exref:: :title: Open a window to run a function from a predefined list of functions :: functions = {"test_regular_expression":test_regular_expression, "test_edit_distance":file_grep, "file_head":file_head } main_loop_functions(functions, title="title: TestMakeWindow2") .. image:: ../../images/open_functionl.png :align: center :githublink:`%|py|167` """ if overwrite is None: overwrite = {} ico = get_icon() if ico is None else ico root = create_tixtk() try: root.iconbitmap(ico) except TclError: warnings.warn("Unable to load icon '{0}'".format(ico)) fr = MainFrame(parent=root, functions=functions, first=first, restore=restore, width=width, raise_exception=raise_exception, overwrite=overwrite, hide=hide) fr.pack() root.title(fr.get_title() if title is None else title) if init_pos is not None: root.geometry('+%d+%d' % init_pos) if mainloop: fr.mainloop() return fr