
Hi All, In the "thoughts on a GUI component library" thread there have been various discussions about the layout of a rectangle and come relating to CSS. Note that point and size are stable. The CSS3 Values and Units module (http://www.w3.org/TR/2001/WD-css3-values-20010713/) defines various units (e.g. inches, picas and em). This is a good basis for a GUI library metric type. The type should store the values as a floating point to allow things like 2.71cm and also to support platforms that store coordinates as floating points (e.g. Cocoa). The CSS3 relative values (em and ex) are dependant on the inherited font-size property, so it is difficult to use these units as there is no associated font-size property. Another issue relating to this is how to resolve metric values between units that are not directly convertable. I have suggested using a device::resolve method that takes metric, point, size and rect types, but it may not always be possible to get access to a device. A further complication is the location of the origin. If we treat the origin as being in the top left corner (which is true for Windows, HTML/CSS and other document models such as text editors) this will simplify the design and for platforms that have a different model (e.g. Mac) then the implementation on that platform will need to map between the different representations. I personally like the CSS box model (http://www.w3.org/TR/css3-box/) which can be defined as: struct css::box_model { rect margin; rect border; rect padding; size dimensions; // width and height // T content; }; The problem with supporting it by default is that we would need: class component: public css::box_model; class graphics::object: public css::box_model; This clearly violates the don't pay for what you don't need rule of C++, so for a css_block_layout, it needs to contain the box model properties and a pointer to the component/graphical object. Obviously some level of support for the CSS box model should be provided, allowing an implementation of it to be written. There has been some discussion and disagreement as to what representation a rectangle takes. It is a good idea to hide the representation of a rectangle and provide accessors to the various values. This is because different people will want different things from it. However, for efficiency, it is a good idea to expose the members of point and size. In supporting the CSS box model and adoption of top-left as (0, 0) the representation becomes: class rect { point tl; point br; }; with: top() = tl.y; left() = tl.x; bottom() = br.y; right() = br.x; width() = br.x - tl.x; width( w ): br.x = tl.x + w; size() = ::size( width(), height()) center() = tl + ( size() / 2 ) An issue with this is: do we keep the width of the rectangle when setting left/right? In order to keep things simple, the answer has to be no. Construction of a rect should have the following variants: rect() = rect( 0, 0, 0, 0 ) rect( n ) = rect( n, n, n, n ) // This models the CSS "margin: 2px;" behaviour. rect( t, r, b, l ): tl( t, l ), br( b, r ) // This models "margin: 1pt 2pt 3pt 4pt;" rect( point p, size s ) = rect( p.x, p.y, p.x + s.dx, p.y + s.dy ) // This allows for support for traditional GUI representations Note that this model will change the nature of a program that uses the current model. We also have inflate/deflate operations that should take size *and* rect variants. This will allow easier box-model calculations: rect disp( point( 0, 0 ), size( 500, 700 )); rect margin( 1, 2, 3, 4 ); rect box = disp; box.deflate( margin ); // apply margin adjustments // ... Regards, Reece