Boost logo

Boost :

From: Alan Gutierrez (alan-boost_at_[hidden])
Date: 2004-12-30 11:12:05


* Jody Hagins <jody-boost-011304_at_[hidden]> [2004-12-30 10:24]:
> On Thu, 30 Dec 2004 08:25:51 +0000
> Reece Dunn <msclrhd_at_[hidden]> wrote:
>
>
> > How do you intend on writing *UI objects* - frames, widgets, layout
> > managers, etc. - that can interact with each other, be moved and
> > process events correctly without sharing a common *ui::object* base?
>
>
> No one should confuse me with a GUI expert, so take what I say with a
> grain of salt w.r.t. GUI development. However, I want to respond to
> this question, as it really does not have anything to do with GUIs.
>
> I assume you are talking about having a common base class with virtual
> functions for common tasks. This is certainly one way of doing it, and
> not being a GUI person, I can not comment on the "correctness" of such a
> proposal - it may well be the best methodology.
>
> However, to answer your question, you can certainly accomplish the same
> thing (i.e., "write UI objects that can interact with each other")
> without a common inheritance hierarchy.
>
> What kinds of interaction between the objects requires inheriting
> from a common base class, as opposed to using Boost.Bind,
> Boost.Function, and Boost.Signal?

    This a good question. It needs be be asked. Following a nested
    shape model is classic, might well be correct, but should not go
    unquestioned. This is a new library that has at its disposal new
    techniques, like generics.

    This is the old schoool:

    If I have a raido button control I can use Composition to draw
    in on by nesting it it a tree of objects.

        ui::window
         \-> ui::frame
             \-> ui:splitter
                 \-> ui::border_layout
                     \-> ui::flow_layout
                         \-> ui::radio_button
                             \-> ui::glyph
                             \-> ui::label

    An inheritence heirarchy can be something like.

        ui::object
        \-> ui::widget
            \-> ui::button
                \-> ui::label

    New school:

    Divide the ui up into rendering strategies. Provide a
    well-defined transition between strategies.

    A flash animation on a web page requires far more in the way of
    hit/visibility testing, rendering, than the web page. Do I want
    a heavy weight ui::object to represent every object of vector
    graphics rendering? Are not a lot of those shapes really
    calculated shapes and not actual objects in memory?
    
    Does the nested ui::object make senese for all rendering? Does
    it scale? No.
    
    If the radio button is one of one million radio buttons for a
    database result set do I have a sparse matrix with a million
    radio buttons? Do I employ a flyweight pattern so that I can
    pretend that there are a million radio buttons on the drawing
    surface?
    
    Or do I want to have a model for rendering that more accurately
    depicts a grid?

    Yes. Once, I've left the nesting of the frame, and entered into
    the grid, I abandon the nested object model altogether, in favor
    of sparse data structures.
    

    I think the model is so.

        ui::renderer< ui::surface< ui::surface_traits > ,
                      ... ??? >

        ui::grid< ui::surface<ui::surface_traits>,
                  ??? ... >

        ui::form< ui::surface<ui::surface_traits>,
                  ??? ... >

        ui::document< ui::surface<ui::surface_traits>,
                      ??? ... >

        ui::canvas< ui::surface<ui::surface_traits>,
                    ??? ... >

    Each of the above renderes can have opmtimal strategies,
    different paradigms entirely, for event rounting, hit and
    visibility testing, and rendering. Events can bubble up through
    the blocks of a document, or then can go directly to a cell on a
    grid.
    
    For a ui::form, nesting an object heirarchy to a common root
    object, is fine. In fact, what is proposed can be one renderer
    implementation.

        ui::nested_component< ui::radio_button,
                              ui::bounding_traits,
                              ui::event_set,
                              ??? >

    For a grid I might have a different render participation
    strategy for the component.

        ui::etheral_component< ui::radio_button,
                               ui::bounding_traits,
                               ui::event_set,
                               ??? >

    A window frame is easily described as a set of nested objects,
    as is a typical form o' widgets. That happy conincidence binds
    most UI libraries to this ui::object rooted model.
    
    Care has to be through about how messages cross the boundries
    between rendering strategies, but imposing nested objects on all
    strategies makes grids and documents cumbersome.

--
Alan Gutierrez - alan_at_[hidden]

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk