summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDodji Seketeli <dodji@src.gnome.org>2003-04-20 21:04:14 +0000
committerDodji Seketeli <dodji@src.gnome.org>2003-04-20 21:04:14 +0000
commitc3728eba9873805b8e259b6f1a567c9d7697e566 (patch)
treedac256ab37ea976054f73a9c3c719a16164d141b
parent027b78631bd098f9ed1d2b074ab5cb344eaf7dac (diff)
downloadlibcroco-c3728eba9873805b8e259b6f1a567c9d7697e566.tar.gz
updated the test7 code to see the layout in action.
* tests/test7-main.c: updated the test7 code to see the layout in action. * src/layeng/cr-style.[ch]: just modified some rule names for convenience. * src/layeng/cr-lay-eng.[ch]: when forward in normal flow layout code. Have now very basic layout code. Still have to write a canvas code to render the layed out box. * src/layeng/cr-lay-eng.c (compute_text_box_inner_edge_size): started to work on the the inner edge size computation based on pango. * src/layeng/Makefile.am: updated to compile/link against libgnomeui. * configure.in: updated it to test the presence of libgnomeui if and only if the layout engine is enabled. Dodji.
-rw-r--r--ChangeLog14
-rw-r--r--configure.in2
-rw-r--r--src/layeng/cr-lay-eng.c704
-rw-r--r--src/layeng/cr-lay-eng.h16
-rw-r--r--src/layeng/cr-style.c24
-rw-r--r--src/layeng/cr-style.h8
-rw-r--r--tests/test7-main.c16
7 files changed, 530 insertions, 254 deletions
diff --git a/ChangeLog b/ChangeLog
index aa50079..2db14dc 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,14 @@
-2003-04-21 Dodji <dodji@seketeli.org>
- * src/layeng/cr-lay-eng.c (cr_lay_eng_layout_box_normal):
- when forward in normal flow layout code.
+2003-04-20 dodji <dodji@seketeli.org>
+
+ * tests/test7-main.c: updated the test7 code to see the layout in
+ action.
+
+ * src/layeng/cr-style.[ch]: just modified some rule
+ names for convenience.
+
+ * src/layeng/cr-lay-eng.[ch]:
+ when forward in normal flow layout code. Have now very basic layout code.
+ Still have to write a canvas code to render the layed out box.
* src/layeng/cr-lay-eng.c (compute_text_box_inner_edge_size): started to work on the
the inner edge size computation based on pango.
diff --git a/configure.in b/configure.in
index 2ef762d..40ac1db 100644
--- a/configure.in
+++ b/configure.in
@@ -32,7 +32,7 @@ dnl on.
dnl
GLIB2_VERSION=2.0
-LIBXML2_VERSION=2.5.1
+LIBXML2_VERSION=2.4.23
LIBGNOMEUI_VERSION=2.0.3
dnl Checks for programs.
diff --git a/src/layeng/cr-lay-eng.c b/src/layeng/cr-lay-eng.c
index 687c2b3..313350c 100644
--- a/src/layeng/cr-lay-eng.c
+++ b/src/layeng/cr-lay-eng.c
@@ -42,26 +42,42 @@
struct _CRLayEngPriv
{
+ gboolean update_parent_inner_edge_size ;
CRCascade *cascade ;
CRSelEng *sel_eng ;
} ;
-static CRBox *
-cr_lay_eng_create_box_tree_real (CRLayEng * a_this,
- xmlNode *a_root_node,
- CRBox *a_parent_box) ;
-static enum CRStatus
-cr_lay_eng_layout_box (CRBox *a_this) ;
+static gboolean gv_layeng_initialized = FALSE ;
+static CRBox *
+create_box_tree_real (CRLayEng * a_this,
+ xmlNode *a_root_node,
+ CRBox *a_parent_box) ;
static glong
-cr_lay_eng_get_box_bottommost_y (CRBox *a_this) ;
+get_box_bottommost_y (CRBox *a_this) ;
static glong
-cr_lay_eng_get_box_rightmost_x (CRBox *a_this) ;
+get_box_rightmost_x (CRBox *a_this) ;
+
+static enum CRStatus
+compute_box_size (CRLayEng *a_this,
+ CRBox *a_cur_box) ;
+
+static enum CRStatus
+layout_inline_box (CRLayEng *a_this,
+ CRBox *a_cur_box) ;
static enum CRStatus
-cr_lay_eng_layout_box_normal (CRBox *a_this) ;
+layout_block_box (CRLayEng *a_this,
+ CRBox *a_cur_box) ;
+
+static enum CRStatus
+layout_box_in_normal_flow (CRLayEng *a_this,
+ CRBox *a_cur_box) ;
+
+static enum CRStatus
+layout_box (CRLayEng *a_this, CRBox *a_cur_box) ;
static enum CRStatus
compute_text_box_inner_edge_size (CRBox *a_this) ;
@@ -88,10 +104,10 @@ init_anonymous_text_box (CRBox *a_box)
cr_num_set (&a_box->style->padding_bottom, 0, NUM_LENGTH_PX) ;
cr_num_set (&a_box->style->padding_left, 0, NUM_LENGTH_PX) ;
- cr_num_set (&a_box->style->border_top_width, 0, NUM_LENGTH_PX) ;
- cr_num_set (&a_box->style->border_right_width, 0, NUM_LENGTH_PX) ;
- cr_num_set (&a_box->style->border_bottom_width, 0, NUM_LENGTH_PX) ;
- cr_num_set (&a_box->style->border_left_width, 0, NUM_LENGTH_PX) ;
+ cr_num_set (&a_box->style->border_top, 0, NUM_LENGTH_PX) ;
+ cr_num_set (&a_box->style->border_right, 0, NUM_LENGTH_PX) ;
+ cr_num_set (&a_box->style->border_bottom, 0, NUM_LENGTH_PX) ;
+ cr_num_set (&a_box->style->border_left, 0, NUM_LENGTH_PX) ;
cr_num_set (&a_box->style->margin_top, 0, NUM_LENGTH_PX) ;
cr_num_set (&a_box->style->margin_right, 0, NUM_LENGTH_PX) ;
@@ -124,9 +140,9 @@ init_anonymous_text_box (CRBox *a_box)
*happens.
*/
static CRBox *
-cr_lay_eng_create_box_tree_real (CRLayEng * a_this,
- xmlNode *a_root_node,
- CRBox *a_parent_box)
+create_box_tree_real (CRLayEng * a_this,
+ xmlNode *a_root_node,
+ CRBox *a_parent_box)
{
enum CRStatus status = CR_OK ;
xmlNode *cur = NULL ;
@@ -289,7 +305,7 @@ cr_lay_eng_create_box_tree_real (CRLayEng * a_this,
/*walk through what remains from the tree*/
if (cur->children)
{
- cr_lay_eng_create_box_tree_real
+ create_box_tree_real
(a_this, cur->children, cur_box) ;
}
}
@@ -313,8 +329,11 @@ cr_lay_eng_create_box_tree_real (CRLayEng * a_this,
static glong
-cr_lay_eng_get_box_bottommost_y (CRBox *a_this)
+get_box_bottommost_y (CRBox *a_this)
{
+ if (!a_this)
+ return 0 ;
+
return (a_this->outer_edge.y
+
a_this->outer_edge.y_offset
@@ -330,7 +349,7 @@ cr_lay_eng_get_box_bottommost_y (CRBox *a_this)
*-1 otherwise.
*/
static glong
-cr_lay_eng_get_box_rightmost_x (CRBox *a_this)
+get_box_rightmost_x (CRBox *a_this)
{
if (!a_this)
return 0 ;
@@ -342,6 +361,18 @@ cr_lay_eng_get_box_rightmost_x (CRBox *a_this)
a_this->outer_edge.width) ;
}
+
+/**
+ *computes the inner edge size of a box which
+ *contents text only.
+ *This fonction uses pango to compute the size
+ *of the box.
+ *Note that this is highly experimental for the time being.
+ *It more a design sketch than a real working code.
+ *@param a_this in/out parameter the current box which inner edge is to
+ *be computed.
+ *@return TRUE if the inner edge has been computed, FALSE otherwise.
+ */
static enum CRStatus
compute_text_box_inner_edge_size (CRBox *a_this)
{
@@ -355,7 +386,7 @@ compute_text_box_inner_edge_size (CRBox *a_this)
&& a_this->content
&& a_this->content->type == TEXT_CONTENT_TYPE,
CR_BAD_PARAM_ERROR) ;
-
+
if (a_this->content->u.text == NULL
|| strlen (a_this->content->u.text) == 0)
{
@@ -376,7 +407,7 @@ compute_text_box_inner_edge_size (CRBox *a_this)
a_this->inner_edge.width = logical_rect.width ;
a_this->inner_edge.height = logical_rect.height ;
- cleanup:
+/* cleanup:*/
if (label)
{
@@ -394,273 +425,445 @@ compute_text_box_inner_edge_size (CRBox *a_this)
}
/**
- *Lay the box out according to "Normal flow"
- *as decribed in css2 spec chap 9.4.
- *In normal flow, a box belongs to a formating context
- *that may be block or inline. In block formating context,
- *boxes are laid out verticaly, one under an other.
- *In inline formatting context, boxes are laid out horizontally,
- *usually from the left to the right, unless we support bidi.
- *@param a_this the current box.
+ *Computes the size and positions of border edge, pading edge,
+ *and inner edge. Also compute the size of the outer edge (aka margin edge).
+ *All these calculations are done relatively to the position of the outer edge.
+ *Which means that the position (x,y) of the outer edge *must* be set prior
+ *to calling this function.
+ *Note that this function calls layout_box() to compute the size of
+ *the inner edge if it contains non terminal boxes.
+ *@param a_this the layout engine.
+ *@param a_cur_box the box.
+ *@return CR_OK upon successfull completion, an error code otherwise.
*/
static enum CRStatus
-cr_lay_eng_layout_box_normal (CRBox *a_this)
+compute_box_size (CRLayEng *a_this,
+ CRBox *a_cur_box)
{
enum CRStatus status = CR_OK ;
- g_return_val_if_fail (a_this && a_this->style,
+ g_return_val_if_fail (a_cur_box && a_cur_box->style,
CR_BAD_PARAM_ERROR) ;
+ /*******************************************
+ *Now, compute the inner edge of this box;
+ *which means
+ *1/set the left border and
+ *left padding edges.
+ *2/compute the left most x and topmost y of
+ *the inner box and.
+ *3/Compute the outer edge of the contained
+ *box; this is recursive.
+ *******************************************/
+
/*
- *Only boxes that have
- *the position rule set to 'static' or 'relative'
- *can be part of a normal formatting context.
+ *1/ => left side of outer edge is separated from
+ *left side of border edge by "margin-left"... same
+ *principle applies for padding edge and inner edge.
*/
- if (a_this->style->position != POSITION_STATIC
- && a_this->style->position != POSITION_RELATIVE)
- {
- return CR_UNEXPECTED_POSITION_SCHEME ;
- }
/*
- *TODO
- *compute the "computed values" of the style data structure.
+ *TODO: collapse this margin !!!.
+ *See css2 chap 8.3.1 to see what "collapsing" means.
*/
- switch (a_this->type)
- {
- case BOX_TYPE_BLOCK:
- case BOX_TYPE_ANONYMOUS_BLOCK:
- {
- CRBox *cont_box = a_this->parent ;
- /************************************
- *We are in a block formating context
- ************************************/
+ a_cur_box->border_edge.x =
+ a_cur_box->outer_edge.x
+ +
+ a_cur_box->style->margin_left.val ;
+ a_cur_box->border_edge.y =
+ a_cur_box->outer_edge.y
+ +
+ a_cur_box->style->margin_top.val ;
- /*
- *position the 'x' of the top
- *leftmost corner of this box
- *at the leftmost abscissa of it's
- *containing box.
- *Position the 'y' of
- *the top left corner of this
- *just under the previous box.
- */
- if (!cont_box)
- a_this->outer_edge.x = 0 ;
- else
- a_this->outer_edge.x =
- cont_box->inner_edge.x ;
-
- a_this->outer_edge.y =
- cr_lay_eng_get_box_bottommost_y (a_this->prev) ;
-
- a_this->outer_edge.x =
- cr_lay_eng_get_box_rightmost_x (a_this->prev) ;
-
- /*******************************************
- *Now, compute the inner edge of this box;
- *which means
- *1/set the left border and
- *left padding edges.
- *2/compute the left most x and topmost y of
- *the inner box and.
- *3/Compute the outer edge of the containing
- *box; this is recursive.
- *******************************************/
+ a_cur_box->padding_edge.x =
+ a_cur_box->border_edge.x
+ +
+ a_cur_box->style->border_left.val ;
+ a_cur_box->padding_edge.y =
+ a_cur_box->border_edge.y
+ +
+ a_cur_box->style->border_top.val ;
- /*
- *1/ => left side of outer edge is separated from
- *left side of border edge by "margin-left"... same
- *principle applies for padding edge and inner edge.
- */
+ /*
+ *Now 2/
+ */
+ a_cur_box->inner_edge.x =
+ a_cur_box->padding_edge.x
+ +
+ a_cur_box->style->padding_left.val ;
+ a_cur_box->inner_edge.y =
+ a_cur_box->padding_edge.y
+ +
+ a_cur_box->style->padding_left.val ;
- /*
- *TODO: collapse this margin !!!.
- *See css2 chap 8.3.1 to see what "collapsing" means.
- */
- a_this->border_edge.x =
- a_this->outer_edge.x
- -
- a_this->style->margin_left.val ;
- a_this->border_edge.y =
- a_this->outer_edge.y
- -
- a_this->style->margin_top.val ;
-
- a_this->padding_edge.x =
- a_this->border_edge.x
- -
- a_this->style->border_left_width.val ;
- a_this->padding_edge.y =
- a_this->border_edge.y
- -
- a_this->style->border_top_width.val ;
+ /*
+ *And now, 3/
+ */
+ if (a_cur_box->children)
+ {
+ /*layout the children boxes*/
+ status = layout_box (a_this, a_cur_box->children) ;
+ g_return_val_if_fail (status == CR_OK, status) ;
+ }
+ else
+ {
/*
- *Now 2/
+ *this box may have a content.
+ *TODO: compute it's width and height.
+ *then, when computed, update the
+ *children max width size in the parent box.
*/
- a_this->inner_edge.x =
- a_this->padding_edge.x
- -
- a_this->style->padding_left.val ;
- a_this->inner_edge.y =
- a_this->padding_edge.y
- -
- a_this->style->padding_left.val ;
+ if (a_cur_box->content)
+ {
+ switch (a_cur_box->content->type)
+ {
+ case TEXT_CONTENT_TYPE:
+ compute_text_box_inner_edge_size
+ (a_cur_box) ;
+ break ;
+
+ case IMAGE_CONTENT_TYPE:
+ cr_utils_trace_info
+ ("image content not "
+ "supported yet") ;
+ break ;
+ case NO_CONTENT_TYPE:
+ cr_utils_trace_info
+ ("incoherent box model. "
+ "We should have either "
+ "image or text here. "
+ "found NO_CONTENT_TYPE "
+ "intead") ;
+ break ;
+ default:
+ cr_utils_trace_info
+ ("Unknown content type") ;
+ break ;
+ }
+ }
+ }
- /*
- *And now, 3/
- */
- if (a_this->children)
+ /*******************************************
+ *Inner edge position (x,y) computing is
+ *finished. (we have it's width).
+ *So now, we can compute the widths of the
+ *remaining three other boxes
+ *(padding edge, border edge and outer edge)
+ ******************************************/
+ a_cur_box->padding_edge.width = a_cur_box->inner_edge.width +
+ a_cur_box->style->padding_right.val +
+ a_cur_box->style->padding_left.val ;
+ a_cur_box->padding_edge.height = a_cur_box->inner_edge.height +
+ a_cur_box->style->padding_top.val +
+ a_cur_box->style->padding_bottom.val ;
+
+ a_cur_box->border_edge.width = a_cur_box->padding_edge.width +
+ a_cur_box->style->border_right.val +
+ a_cur_box->style->border_left.val ;
+ a_cur_box->border_edge.height = a_cur_box->padding_edge.height +
+ a_cur_box->style->border_top.val +
+ a_cur_box->style->border_bottom.val ;
+
+ a_cur_box->outer_edge.width = a_cur_box->border_edge.width +
+ a_cur_box->style->margin_left.val +
+ a_cur_box->style->margin_right.val ;
+ a_cur_box->outer_edge.height = a_cur_box->border_edge.height +
+ a_cur_box->style->margin_top.val +
+ a_cur_box->style->margin_bottom.val ;
+
+ return CR_OK ;
+}
+
+/**
+ *Layout a box in block formating context.
+ *See css2 spec in chapters 9.2.
+ *@param a_this the current instance of CRLayEng.
+ *@param a_cur_box the current box to layout.
+ *@return CR_OK upon successfull completion, an error code otherwise.
+ */
+static enum CRStatus
+layout_block_box (CRLayEng *a_this,
+ CRBox *a_cur_box)
+{
+ enum CRStatus status = CR_OK ;
+
+ g_return_val_if_fail (a_cur_box && a_cur_box->style,
+ CR_BAD_PARAM_ERROR) ;
+
+ CRBox *cont_box = a_cur_box->parent ;
+
+ /************************************
+ *We are in a block formating context
+ ************************************/
+
+ /*
+ *position the 'x' of the top
+ *leftmost corner of this box
+ *at the leftmost abscissa of it's
+ *containing box.
+ *Position the 'y' of
+ *the top left corner of this
+ *just under the previous box.
+ */
+ if (!cont_box)
+ {
+ a_cur_box->outer_edge.x = 0 ;
+ a_cur_box->outer_edge.y = 0 ;
+ }
+ else
+ {
+ a_cur_box->outer_edge.x =
+ cont_box->inner_edge.x ;
+ if (a_cur_box->prev)
{
- cr_lay_eng_layout_box (a_this->children) ;
+ a_cur_box->outer_edge.y =
+ get_box_bottommost_y (a_cur_box->prev) ;
}
else
{
- /*
- *this box may have a content.
- *TODO: compute it's width and height.
- *then, when computed, update the
- *children max width size in the parent box.
- */
- if (a_this->content)
- {
- switch (a_this->content->type)
- {
- case TEXT_CONTENT_TYPE:
- compute_text_box_inner_edge_size
- (a_this) ;
- break ;
-
- case IMAGE_CONTENT_TYPE:
- cr_utils_trace_info
- ("image content not "
- "supported yet") ;
- break ;
- case NO_CONTENT_TYPE:
- cr_utils_trace_info
- ("incoherent box model. "
- "We should have either "
- "image or text here. "
- "found NO_CONTENT_TYPE "
- "intead") ;
- break ;
- default:
- cr_utils_trace_info
- ("Unknown content type") ;
- break ;
- }
- }
+ a_cur_box->outer_edge.y =
+ cont_box->inner_edge.y ;
}
-
- /*
- *now that we have the width/height of the inner box,
- *let's compute the width/height of the padding box,
- *border box and outer box.
- */
- a_this->padding_edge.width = a_this->inner_edge.width +
- a_this->style->padding_right.val +
- a_this->style->padding_left.val ;
-
- a_this->padding_edge.height = a_this->inner_edge.height +
- a_this->style->padding_top.val +
- a_this->style->padding_bottom.val ;
-
- /*TODO continue the calculus of the widths/height*/
-
- /*******************************************
- *Inner edge position (x,y) computing is
- *finished. (we have it's width).
- *So now, we can compute the widths of the
- *remaining three other boxes
- *(padding edge, border edge and outer edge)
- ******************************************/
- break ;
}
- case BOX_TYPE_COMPACT:
- case BOX_TYPE_RUN_IN:
- case BOX_TYPE_INLINE:
- case BOX_TYPE_ANONYMOUS_INLINE:
- {
- CRBox *cont_box = NULL, *prev_box = NULL ;
-
- cont_box = a_this->parent ;
- prev_box = a_this->prev ;
+ status = compute_box_size (a_this,
+ a_cur_box) ;
+
- /************************************
- *We are in an inline formating context
- ************************************/
+ return status ;
+}
+
+
+/**
+ *Layout a box in an inline formating context.
+ *See css2 spec in chapters 9.2.
+ *@param a_this the layout engine.
+ *@param a_cur_box the current box to layout.
+ *@return CR_OK upon successfull completion, an error code otherwise.
+ */
+static enum CRStatus
+layout_inline_box (CRLayEng *a_this,
+ CRBox *a_cur_box)
+{
+ CRBox *cont_box = NULL, *prev_box = NULL ;
+ enum CRStatus status = CR_OK ;
+
+ g_return_val_if_fail (a_cur_box && a_cur_box->style,
+ CR_BAD_PARAM_ERROR) ;
+
+ cont_box = a_cur_box->parent ;
+ prev_box = a_cur_box->prev ;
+
+ /************************************
+ *We are in an inline formating context
+ ************************************/
+
+ /********************************************
+ *position the 'x' of the top
+ *leftmost corner of this box
+ *one pixel right after the rightmost x
+ *of the preceding box.
+ *Position the 'y' of this box to
+ *the y of the previous box.
+ ********************************************/
+ if (!prev_box)
+ {
/*
- *position the 'x' of the top
- *leftmost corner of this box
- *one pixel right after the rightmost x
- *of the preceding box.
- *Position the 'y' of this box to
- *the y of the previous box.
+ *this box is the leftmost box contained in its containing
+ *box.
*/
- if (!prev_box)
+ if (cont_box)
{
- a_this->outer_edge.x = 0 ;
- a_this->outer_edge.y = 0 ;
+ a_cur_box->outer_edge.x = cont_box->inner_edge.x ;
+ a_cur_box->outer_edge.y = cont_box->inner_edge.y ;
}
else
{
- a_this->outer_edge.x =
- cr_lay_eng_get_box_rightmost_x
- (prev_box) + 1 ;
- a_this->outer_edge.y = prev_box->outer_edge.y ;
+ /*this box does not have any containing box*/
+ a_cur_box->outer_edge.x = 0 ;
+ a_cur_box->outer_edge.y = 0 ;
}
+ }
+ else
+ {
+ a_cur_box->outer_edge.x =
+ get_box_rightmost_x (prev_box) + 1 ;
+ a_cur_box->outer_edge.y = prev_box->outer_edge.y ;
+ }
+
+ /*******************************************
+ *Now, compute the inner edge of this box;
+ *which means
+ *1/set the left border and
+ *left padding edges.
+ *2/compute the left most x and topmost y of
+ *the inner box and.
+ *3/Compute the outer edge of the containing
+ *box; this is recursive.
+ *******************************************/
+
+ status = compute_box_size (a_this,
+ a_cur_box) ;
+
+ return status ;
+}
- /*TODO*/
- /*******************************************
- *Now, compute the inner edge of this box;
- *which means
- *1/set the left border and
- *left padding edges.
- *2/compute the left most x and topmost y of
- *the inner box and.
- *3/Compute the outer edge of the containing
- *box; this is recursive.
- *******************************************/
+/**
+ *Lay the box out according to "Normal flow"
+ *as decribed in css2 spec chap 9.4.
+ *In normal flow, a box belongs to a formating context
+ *that may be block or inline. In block formating context,
+ *boxes are laid out verticaly, one under an other.
+ *In inline formatting context, boxes are laid out horizontally,
+ *usually from the left to the right, unless we support bidi.
+ *@param a_this the layout engine.
+ *@param a_cur_box the current box.
+ *@return CR_OK upon successfull completion, an error code otherwise.
+ */
+static enum CRStatus
+layout_box_in_normal_flow (CRLayEng *a_this,
+ CRBox *a_cur_box)
+{
+ enum CRStatus status = CR_OK ;
+
+ g_return_val_if_fail (a_cur_box && a_cur_box->style,
+ CR_BAD_PARAM_ERROR) ;
+
+ /*
+ *Only boxes that have
+ *the position rule set to 'static' or 'relative'
+ *can be part of a normal formatting context.
+ */
+ if (a_cur_box->style->position != POSITION_STATIC
+ && a_cur_box->style->position != POSITION_RELATIVE)
+ {
+ return CR_UNEXPECTED_POSITION_SCHEME ;
}
+
+ /*
+ *TODO
+ *compute the "computed values" of the style data structure.
+ */
+ switch (a_cur_box->type)
+ {
+ case BOX_TYPE_BLOCK:
+ case BOX_TYPE_ANONYMOUS_BLOCK:
+ layout_block_box (a_this, a_cur_box) ;
+ break ;
+
+ case BOX_TYPE_COMPACT:
+ case BOX_TYPE_RUN_IN:
+ case BOX_TYPE_INLINE:
+ case BOX_TYPE_ANONYMOUS_INLINE:
+ layout_inline_box (a_this, a_cur_box) ;
break ;
default:
break ;
}
+
return status ;
}
+
+/**
+ *Layout a box.
+ *This function determine the flow scheme (e.g: normal flow etc ...)
+ *and call the right specialized function that knows how to perform
+ *the layout according to that flow scheme.
+ *Note that a flow scheme is local to a box. A child box can have a
+ *different flow scheme for example. So the lower level function called
+ *by layout_box() can also call layout_box() to perform the layout of their
+ *children boxes.
+ *@param a_this the layout engine.
+ *@param a_cur_box the current box.
+ */
static enum CRStatus
-cr_lay_eng_layout_box (CRBox *a_this)
+layout_box (CRLayEng *a_this,
+ CRBox *a_cur_box)
{
CRBox *cur_box = NULL ;
- g_return_val_if_fail (a_this && a_this->style,
+ g_return_val_if_fail (a_cur_box && a_cur_box->style,
CR_BAD_PARAM_ERROR) ;
- for (cur_box = a_this ; cur_box ;
+ PRIVATE (a_this)->update_parent_inner_edge_size = TRUE ;
+
+ for (cur_box = a_cur_box ; cur_box ;
cur_box = cur_box->next)
{
switch (cur_box->style->position)
{
case POSITION_STATIC:
case POSITION_RELATIVE:
- cr_lay_eng_layout_box_normal (cur_box) ;
+ layout_box_in_normal_flow
+ (a_this, cur_box) ;
break ;
case POSITION_ABSOLUTE:
case POSITION_FIXED:
- /*cr_box_layout_absolute (a_this) ;*/
+ /*cr_box_layout_absolute (a_cur_box) ;*/
break ;
case POSITION_INHERIT:
break ;
}
}
+
+ /*
+ *make sure the parent inner_edge.width is big enough to contain
+ *the current box.
+ */
+ if (PRIVATE (a_this)->update_parent_inner_edge_size == TRUE
+ && a_cur_box->parent)
+ {
+ gulong parent_inner_edge_right_bound =
+ a_cur_box->parent->inner_edge.x +
+ a_cur_box->parent->inner_edge.width ;
+ gulong outer_edge_right_bound =
+ a_cur_box->outer_edge.x +
+ a_cur_box->outer_edge.width ;
+
+ if (parent_inner_edge_right_bound
+ <
+ outer_edge_right_bound)
+ {
+ /*
+ *parent inner edge is too short to
+ *contain this box outer edge.
+ *So, we just enlarge it.
+ */
+ a_cur_box->parent->inner_edge.width =
+ outer_edge_right_bound -
+ a_cur_box->parent->inner_edge.x ;
+ }
+ }
+
+ /*
+ *Make sure the parent inner_edge.heigth is big enough
+ *to contain the current box.
+ */
+ if (a_cur_box->parent)
+ {
+ gulong parent_inner_edge_bottom_bound =
+ a_cur_box->parent->inner_edge.y +
+ a_cur_box->parent->inner_edge.height ;
+ gulong outer_edge_bottom_bound =
+ a_cur_box->outer_edge.y +
+ a_cur_box->outer_edge.height ;
+
+ if (parent_inner_edge_bottom_bound <
+ outer_edge_bottom_bound)
+ {
+ a_cur_box->parent->inner_edge.height =
+ outer_edge_bottom_bound -
+ a_cur_box->parent->inner_edge.y ;
+ }
+ }
+
return CR_OK ;
}
@@ -668,10 +871,41 @@ cr_lay_eng_layout_box (CRBox *a_this)
*Public methods.
**********************/
+/**
+ *The first function to call prior to any other
+ *method of the layout engine.
+ *@param a_argc the argc parameter passed to the standard C main entry point.
+ *@param a_argv the argv parameter passed to the standard C main entry point.
+ */
+void
+cr_lay_eng_init (glong a_argc, gchar ** a_argv)
+{
+
+ if (gv_layeng_initialized == FALSE)
+ {
+ gnome_init ("croco layout engine", "0.0" ,
+ a_argc, a_argv) ;
+ gv_layeng_initialized = TRUE ;
+ }
+}
+
+
+/**
+ *Instanciates a new Layout Engine.
+ *return the new instance of #CRLayEng or NULL if
+ *an error occured.
+ */
CRLayEng *
cr_lay_eng_new (void)
{
- CRLayEng *result = NULL;
+ CRLayEng *result = NULL ;
+
+ if (gv_layeng_initialized == FALSE)
+ {
+ cr_utils_trace_info ("Layout Engine must be initialized "
+ "by calling cr_lay_eng_init() first") ;
+ return NULL ;
+ }
result = g_try_malloc (sizeof (CRLayEng)) ;
if (!result)
@@ -704,7 +938,7 @@ cr_lay_eng_new (void)
*otherwise.
*/
enum CRStatus
-cr_lay_eng_build_box_tree (CRLayEng *a_this,
+cr_lay_eng_create_box_tree (CRLayEng *a_this,
xmlDoc *a_doc,
CRCascade *a_cascade,
CRBox **a_box_model)
@@ -721,8 +955,8 @@ cr_lay_eng_build_box_tree (CRLayEng *a_this,
PRIVATE (a_this)->cascade = a_cascade ;
*a_box_model =
- cr_lay_eng_create_box_tree_real (a_this, root_node,
- NULL) ;
+ create_box_tree_real (a_this, root_node,
+ NULL) ;
return CR_OK ;
}
@@ -816,6 +1050,28 @@ cr_lay_eng_get_matched_style (CRLayEng *a_this,
}
/**
+ *Recursively computes the sizes and positions of each
+ *box in the box tree.
+ *@param a_this
+ *@param a_box_tree
+ *@return
+ */
+enum CRStatus
+cr_lay_eng_layout_box_tree (CRLayEng *a_this,
+ CRBox *a_box_tree)
+{
+ enum CRStatus status = CR_OK ;
+
+ g_return_val_if_fail (a_this && a_box_tree,
+ CR_BAD_PARAM_ERROR) ;
+
+ status = layout_box (a_this, a_box_tree) ;
+
+ return status ;
+}
+
+
+/**
*Destuctor of #CRLayEng.
*@param a_this the current instance of #CRLayEng.
*/
diff --git a/src/layeng/cr-lay-eng.h b/src/layeng/cr-lay-eng.h
index db431b0..ae46e9c 100644
--- a/src/layeng/cr-lay-eng.h
+++ b/src/layeng/cr-lay-eng.h
@@ -48,6 +48,10 @@ typedef struct
} CRLayEng ;
+
+void
+cr_lay_eng_init (glong a_argc, gchar ** a_argv) ;
+
CRLayEng *
cr_lay_eng_new (void) ;
@@ -58,10 +62,14 @@ cr_lay_eng_get_matched_style (CRLayEng *a_this,
CRStyle *a_parent_style,
CRStyle **a_style) ;
enum CRStatus
-cr_lay_eng_build_box_tree (CRLayEng *a_this,
- xmlDoc *a_xml_doc,
- CRCascade *a_cascade,
- CRBox **a_box_tree) ;
+cr_lay_eng_create_box_tree (CRLayEng *a_this,
+ xmlDoc *a_xml_doc,
+ CRCascade *a_cascade,
+ CRBox **a_box_tree) ;
+enum CRStatus
+cr_lay_eng_layout_box_tree (CRLayEng *a_this,
+ CRBox *a_box_tree) ;
+
void
cr_lay_eng_destroy (CRLayEng *a_this) ;
diff --git a/src/layeng/cr-style.c b/src/layeng/cr-style.c
index a9404ba..0e569c9 100644
--- a/src/layeng/cr-style.c
+++ b/src/layeng/cr-style.c
@@ -230,13 +230,13 @@ cr_style_set_props_to_defaults (CRStyle *a_this)
cr_num_set (&a_this->padding_left,
0, NUM_LENGTH_PX) ;
- cr_num_set (&a_this->border_top_width,
+ cr_num_set (&a_this->border_top,
0, BORDER_MEDIUM) ;
- cr_num_set (&a_this->border_right_width,
+ cr_num_set (&a_this->border_right,
0, BORDER_MEDIUM) ;
- cr_num_set (&a_this->border_bottom_width,
+ cr_num_set (&a_this->border_bottom,
0, BORDER_MEDIUM) ;
- cr_num_set (&a_this->border_left_width,
+ cr_num_set (&a_this->border_left,
0, BORDER_MEDIUM) ;
/*default foreground color is black*/
@@ -400,30 +400,30 @@ set_prop_border_x_width_from_value (CRStyle *a_style,
switch (a_dir)
{
case DIR_TOP:
- num_val = &a_style->border_top_width ;
+ num_val = &a_style->border_top ;
parent_num_val =
- &a_style->parent_style->border_top_width ;
+ &a_style->parent_style->border_top ;
break ;
case DIR_RIGHT:
num_val =
- &a_style->border_right_width ;
+ &a_style->border_right ;
parent_num_val =
- &a_style->parent_style->border_right_width;
+ &a_style->parent_style->border_right;
break ;
case DIR_BOTTOM:
- num_val = &a_style->border_bottom_width ;
+ num_val = &a_style->border_bottom ;
parent_num_val =
- &a_style->parent_style->border_bottom_width;
+ &a_style->parent_style->border_bottom;
break ;
case DIR_LEFT:
- num_val = &a_style->border_left_width ;
+ num_val = &a_style->border_left ;
parent_num_val =
- &a_style->parent_style->border_left_width;
+ &a_style->parent_style->border_left;
break ;
default:
diff --git a/src/layeng/cr-style.h b/src/layeng/cr-style.h
index 004a232..7912a08 100644
--- a/src/layeng/cr-style.h
+++ b/src/layeng/cr-style.h
@@ -136,10 +136,10 @@ struct _CRStyle
CRNum padding_left ;
/**border properties*/
- CRNum border_top_width ;
- CRNum border_right_width ;
- CRNum border_bottom_width ;
- CRNum border_left_width ;
+ CRNum border_top ;
+ CRNum border_right ;
+ CRNum border_bottom ;
+ CRNum border_left ;
CRRgb color ;
CRRgb border_top_color ;
diff --git a/tests/test7-main.c b/tests/test7-main.c
index e1dadb6..5006db4 100644
--- a/tests/test7-main.c
+++ b/tests/test7-main.c
@@ -49,10 +49,10 @@ const guchar *gv_cssbuf =
;
static enum CRStatus
-test_cr_lay_eng_build_annotated_tree (void) ;
+test_layout_box (void) ;
static enum CRStatus
-test_cr_lay_eng_build_annotated_tree (void)
+test_layout_box (void)
{
enum CRStatus status = CR_OK ;
CRStyleSheet * sheet = NULL ;
@@ -102,9 +102,9 @@ test_cr_lay_eng_build_annotated_tree (void)
}
sheet = NULL ;
- status = cr_lay_eng_build_box_tree (layout_engine,
- xml_doc, cascade,
- &box_tree) ;
+ status = cr_lay_eng_create_box_tree (layout_engine,
+ xml_doc, cascade,
+ &box_tree) ;
if (status != CR_OK)
{
cr_utils_trace_info ("could not build the annotated doc") ;
@@ -113,6 +113,8 @@ test_cr_lay_eng_build_annotated_tree (void)
if (box_tree)
{
+ cr_lay_eng_layout_box_tree (layout_engine,
+ box_tree) ;
cr_box_dump_to_file (box_tree, 0, stdout) ;
cr_box_destroy (box_tree) ;
box_tree = NULL ;
@@ -154,7 +156,9 @@ main (int argc, char **argv)
{
enum CRStatus status = CR_OK ;
- status = test_cr_lay_eng_build_annotated_tree () ;
+ cr_lay_eng_init (argc, argv) ;
+
+ status = test_layout_box () ;
if (status != CR_OK)
{