zmapWindow/items - extensions to the Foo Canvas for zmap


Canvas Groups, Items and Utils

This directory contains functions and headers to support our own custom foocanvas items derived from FooCanvasItem and FooCanvasGroup.

There are three "public" level headers that "application" code (i.e. code outside of this directory) should use:

These give access to the public interfaces for our canvas, container and feature extensions respectively. (N.B. code within this directory should not include these headers but instead _only_ include the headers from within this directory that are actually needed.)

Each component has a public and a private header, private headers should always immediately include their public header to prevent type clashes, circularities etc. Only derived "classes" should include the private headers of their parents otherwise public headers should be used.

There are various types of "container" and various types of "feature" which are used to form the hierachy in the Foocanvas that represents our feature context, their relationship is like this:

                    | ZMapWindowContainerContext
                    |             |
                    |             |
                    | ZMapWindowContainerAlignment
                    |             |
                    |             |
ZMapContainerGroup--| ZMapWindowContainerBlock
                    |             |
                    |             |
                    | ZMapWindowContainerStrand
                    |             |
                    |             |
                    | ZMapWindowContainerFeatureSet
                                  |
                                  |
    ZMapCanvasItem--| the various types of zmapWindowXXXXFeature
(Note that going down each level is a one->many parent/child mapping.)

As can be seen from the above diagram ZMapContainerGroup and ZMapCanvasItem are "base" classes that provide generalised interfaces common to all groups or features.

The use of GObject as the basis for the groups/items means that each container member including the member itself has a G_TYPE. This means code that does ZMAP_IS_CONTAINER_GROUP(pointer) is simpler and hopefully more readable.

The ZMapWindowContainerGroup are sub classes of FooCanvasGroup and implement the FooCanvasItem interface (draw, update, bounds, etc...). The update code takes care of cropping the Container "owned" items, such as the background and any overlays/underlays that might be being drawn. It also includes hooks to provide similar functionality to the ContainerExecute callbacks. These are attached/owned by each specific container so only get called by the container they relate to. This again leads to simplier code, without the switch on the container level.

Each canvas item, as well as having its basic shape also has a background, under- and overlay. Crucial to this is the ordering of these items as we rely on the foocanvas routines to do all drawing and they just plough through the list of items in each foocanvas group. To implement backgrounds etc. we must maintain the order of these items.

The background item is used both as a visible background for the items but also more importantly to catch events _anywhere_ in the space (e.g. column) where the items might be drawn. This arrangement also means that code that has to process all items can do so simply by processing all members of the item list of the sub_group as they are guaranteed to all be feature items and it is trivial to perform such operations as taking the size of all items in a group.