================================ ``grail.widgets.gwidget`` module ================================ .. include:: ../../version.h .. include:: ref.h .. contents:: Table of Contents :backlinks: top ----------- Description ----------- All MineSightŪ Grail widgets will inherit from the :c:`GWidget` class. The :c:`GWidget` class it inherits from the :c:`Tkinter.Frame`, and provides the basics for creating new widgets. In addition, new, common convenience functions are added to the :c:`GWidget` class that can be used on all objects that inherit from this class. ------- GWidget ------- class :dc:`GWidget([parent, **keywords])` Provides the base class for all the MineSightŪ Grail system's widgets. This allows us to make global changes in this one class, and enforce behavior throughout all the MineSightŪ Grail widgets. Arguments: :a:`parent` : :c:`Tkinter.Frame` Parent widget, widget we insert into. :a:`keywords` Any keywords acceptable to a :c:`Tkinter.Frame`. Component: hull The hull refers the :c:`Tkinter.Frame` that this widget is drawn on. This would be rarely referenced. Methods to override: There a three methods that you must override (without exception), these are, :f:`updatevars` This method is called to synchronize any :c:`RTV` with the contents of the widget. If the contents are correct, and the synchronization worked, this should return 1; otherwise, this method should return 0 on error. :f:`enable` This method should put the widget into an state enabled for user input. :f:`disable` This method should put the widget into a stat disabled for user input. Optional methods to override/extend: :f:`destroy` This method should typically be extended, and provides a means of performing cleanup when the widget is being cleaned up from the system resources. :df:`appear()` Cause a :c:`GWidget` to appear. If a geometry has already been packed/gridded/placed calling this method causes the :c:`GWidget` to appear. This function is mainly used with :f:`disappear` to cause a widget to appear and disappear at will. Takes care of all the geometry information, and layout type, so all you have to do is call 'appear' and 'disappear'. :df:`cget(tag)` Returns the configuration for the appropriate tag. Works just like the standard Tkinter method, and obeys the semantics discussed in the :f:`configure` method. As an example consider the composite widget that simply defines an 'entry' and a 'button' sub-componets. You could exam the configuration information by simply doing the following, .. Python:: entrytext = composite.cget('entry_text') buttontext = composite.cget('button_text') Just like the Tkinter library, the [] has be overridden as well. So the above example could also be written as, .. Python:: entrytext = composite['entry_text'] buttontext = composite['button_text'] .. Note:: That the 'hull' request does *not* work correctly. :df:`component(name)` Provides access to the sub-components in a :c:`GWidget`. Allows access to the composite sub-components via the sub-component's name. For example, consider a :c:`GWidget` containing a textentry and a button, which have been named 'entry' and 'button' respectively, then as a user you can gain a handle to the entry and button via this :f:`component` call. .. Python:: w = mywidget() button = w.component('button') entry = w.component('entry') :df:`configure([**keywords])` Provides a configuration access point. Operates exactly like the Tkinter configuration calls. But you can configure sub-components directly by prefixing the sub-components name. For example, conside that you have a composite widget containing two components: an 'entry' and a 'button'. Normally the text on a plain button could be changed like this, .. Python:: button.configure(text="new text") But for the composite widget, the button is one component in a collection of components, so the configuration method changes slightly. To change the text in our composite example we would do the following, .. Python:: composite.configure(button_text="new text") Often a widget will not allow you to configure an option, an :e:`GWidgetError` will be raised in these cases. Also, notice that you can make multiple configuration calls in one :f:`configure` call. Considering our composite example, we could do something like, .. Python:: composite.configure(button_text="new text", entry_background="black", entry_text="new text for the entry") Finally, this method maps to the [] operator as well, so the above, earlier, example could also be written as, .. Python:: composite["button_text"] = "new text" Which style is better is just a matter of preference. :df:`destroy()` **Optional Override/Extend** Since the time when a widget is destroyed is actually different from the time that a widget is officially removed from the heap, Tkinter will make a :f:`destroy` call to all its children frames (from the main frame downwards). During each :f:`destroy` call that particular widget has the ability to release resources, or re-instate previous states. Now, since our :c:`GWidget` is just a powerful :c:`Tkinter.Frame`, it obeys the same Tkinter logic. This method is typically used to indicate that you may no longer be interested in listening to a particular object's (aka emitter) signals. Consider the case when you have indicated that you are interested in the signals from an :c:`RTV` object. Your widget exists peacefully, and listens and responds to the :c:`RTV` object's signals, but when the main window closes, a chain of destroy calls are made, which essentially eliminate any window semantics. Then later in the code, the :c:`RTV` is changed programmatically. At this point, technically your widget could still exist out there in the universe (it has not been deleted) but it doesn't have an existence (no methods, data, etc...). Consider that it is just in purgatory waiting to be removed from the heap when the python garbage collector runs by. Now the problem is that signal emitted by the :c:`RTV` after the widget has been destroyed will find that there is a listener (the destroyed widget) still interested. At this point we attempt to make the appropriate callback call, and all heck breaks loose because the handling of that signal no longer exists on your widget, remember the widget is a ghost bidding its time in purgatory. So, when this condition occurs you will want to override and forward the destroy() method like this, .. Python:: class MyWidget(GWidget): # ... other methods ... def destroy(): # free, ignore, or do anything else you would normally # do in the '__del__' method. then make the forwarding # call up to the gwidget. GWidget.destroy() .. Note:: That 90% of the time it appears that you really want to invoke this idiom only if you expressed an interest in an :c:`RTV` signal. :df:`disable()` **Override** Use this method to define how your widget behaves in an disabled state. Meaning, that the user is unable to interact with your visible widget. :df:`disappear()` Cause a :c:`GWidget` to disappear. If a widget has already been layed out via the place/pack/grid methods, then this method will save geometry information plus the layout type and call the appropriate :f:`xxx_forget` method. For example, if your widget was gridded, then :f:`grid_forget` would be called. Likewise a packed widget would use the :f:`pack_forget` call. To make the widget re-appear call the :f:`appear` method. If the widget is invisible, calling disappear will have no effect. :df:`enable()` **Override** Use this method to define how your widget behaves in an enabled state. Meaning, that the user is able to interact with your visable widget. :df:`geominfo()` Returns the type and configuration for a geometry layout. Indicates what type of geometry layout was used: place, grid or pack. In addition it returns the configuration information used to perform the type geometry layout done. An example would be, .. Python:: w = GButton(root, text="test button!") geomtype, geominfo = w.geominfo() Returns a tuple: (geometrytype, geometryinfo,). 'geometrytype' can be one of ('place', 'grid', 'pack'). :df:`updatevars()` **Override** Extract values and transfer to :c:`RTV` objects for sub-components. This method should be overridden by the defined widget, it must either return 0 or return 1. An example of a failed update would be the attempt to set an IntegerRTV to contain the string "abc". Returns 1 if all the internal updates worked, otherwise returns 0 if one or more updates fail. .. Note:: The return value idiom is used because this may be called within a complex event structure. During that event structure a thrown exception will appear out of sequence, and thus make it harder to control your applications behavior. ----------------------- Exceptions and Warnings ----------------------- The following are general warnings and errors generated by the MineSightŪ Grail widgets. exception :de:`GWidgetError` General MineSightŪ Grail Graphical User Interface error. class :dc:`GWidgetWarning` General MineSightŪ Grail Graphical User Interface warning.