General Toolkit
---------------
Overview
--------
- Everything is an widget.
- An widget is a visual or layout element that can be shown, hidden,
drawn, receive events and participate in geometry negotiation.
- If an widget cannot handle an event it receives it should pass
that event on to its parent. (Button and key events, etc.)
- An widget need not produce visual output. For instance, an hbox
simple arranges its children.
- Widgets have no children.
- Every widget has a container for a parent. (No exceptions).
- A container is a type of widget. A container contains 1 or more
children and manages their size and position. It also defines
a few more functions that allow widgets to ask their parents (the
container) to be resized.
- All widget and container functions are expected to be valid. A
NULL function is an error. (If the function should do nothing
then create a simple function that just returns). This includes
specifying a valid "event" function for widgets which do not receive
events (such as some containers). Children of the container may pass
events up the widget tree so it is necessary (and even desired)
to define an event function for such containers.
Widgets
-------
Variables
---------
"visible" - This flag is set if the widget is visible. This
simply means that the widget should participate in geometry
negotiation. That is, the widget may not necessarily be mapped on the
screen yet.
"mapped" - This flag is set if the widget is mapped on the
screen. Which means that it is ready for drawing.
"parent" - The parent container of the widget.
"requisition" - The child's requested size.
"allocation" - The child's allocated size.
"private" - Private storage which depends on the particular type
of widget. Currently this is used to store the GdkWindow for each
widget.
"user_data" - A hook onto which users can place data.
Functions
---------
"destroy" - This function should destroy the widget and free all
associated memory.
"show" - Make the widget visible. (Not the same as mapping).
"hide" - Make the widget invisible.
"map" - Map the widget.
"unmap" - Unmap the widget.
"draw" - Draw the widget (and any children).
"expose" - Draw only the widget. (Do not draw children).
"clear" - Clear the widgets background area. (This is useful when a
parent changes its background color and it needs to tell its
children to redraw their background.)
"event" - Handle an event. If the widget cannot handle the event
then it should pass it along to its parent. (Only widgets
which create their own GdkWindow's will receive events).
"size_request" - Fill in the size requisition structure.
"size_allocate" - Accept the size allocated. This means resizing
the widget and sending size allocations to children (if the widget is
a container).
Containers
----------
Variables
---------
"widget" - The first member of the container structure is the
widget structure. This allows containers to be freely cast into
widgets. It also means containers need to fill in the widget structure
when they are created.
"border_width" - The width of the border that surrounds the
widget. All containers should recognize and act upon the setting of
this variable.
"spacing" - The spacing between children. Containers which
manage multiple children should recognize this variable if at
all possible.
Functions
---------
"add" - Add the specified widget to the container. Give an error
if the widget cannot be added.
"remove" - Remove the specified widget from the container. Give
an error if the widget cannot be removed.
"need_resize" - This is called be children which are in need of
a resize. Most of the time the correct response is to call the
"need_resize" function of the containers parent with itself
as the widget in need of resize.
Data and Observers
------------------
Data
----
In order to handle communication between widgets and between widgets
and the user program, the concept of a piece of data is needed. For
the most part, widgets provide a visual interface to a piece of
data. In the case of a button, the data is the buttons state. In the
case of a slider, the data is the sliders position (value), lowera and
upper bounds and the step and page increments.
We'd like to be able to "observe" the data and get notifications when
it changes. Two new data structures are added to facilitate this. The
"GtkData" type specifies the basic operations for data. Data can have
a unique type. Data can be "attached" to and "detached" from. And data
can notify all attached observers that it has been modified. Lastly,
data can notify all attached observers that is is being destroyed.
Observer
--------
The "GtkObserver" type specifies the basic operations for an
observer. An observer can attach itself to a piece of data and then
receive notification of changes to that data. It will also receive
notification of the data's destruction (if that occurs).
Other UI elements
-----------------
Widgets and containers provide a basic mechanism for creating the rest
of the user interface. Widgets include such items as labels, pixmaps,
images, scales, etc. Containers include such items as horizontal and
vertical boxes as well as some more unusual containers. Such as
frames, alignments and even buttons.
Labels, images and pixmaps
--------------------------
Labels, images and pixmaps are simply what they sound like. They
display a label, image or pixmap. They inherit their parents
background color so that they may be used in buttons. Labels are
somewhat special in that they don't create their own window, but
instead use their parents window for drawing.
Buttons
-------
Buttons are containers which have a single child. The button
handles tracking of button presses and releases. The children of a
button should not handle button presses or releases and should pass
those events to their parents (like any well behaved widget
should).
HBoxes and VBoxes
-----------------
Horizontal and vertical boxes arrange their children as their
name implies...horizontally and vertically.
Menubars and Menus
------------------
Menubars are containers which hold menu items. The menu items are
arranged horizontally and packed to the left side of the menubar. Menu
items themselves receive button and key press events, but simply pass
them to their parent. (Which is either a menu or menubar).
Menus are containers which also hold menu items. The menu items are
arranged vertically and packed to the top of the menu.
Menu items are also containers. They can hold only 1 child, a menu.
Unlike normal containers, menu items do not determine the size and
positioning of their child. This is done by their parent. This allows
the menu (or menubar) to correctly position the submenu.
Menu items display a label. They can have optional accelerators which are
displayed to the right of the label and/or a radio or check button displayed
to the left of the label. Menu items contain a state variable which can
be set by their parent. The setting of this variable determines how the menu
item is drawn (normal, selected) and whether the submenu (if one exists)
is displayed.