summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohn Mark Bell <jmb@netsurf-browser.org>2009-08-21 17:05:22 +0000
committerJohn Mark Bell <jmb@netsurf-browser.org>2009-08-21 17:05:22 +0000
commitb0f127aa2c6b166572999c3eda46e74c845aec19 (patch)
tree5eb18a3e241b0cd66d85a490a8b9dd23ee11240c
parente57eaed1ad1dd589a2dc1dfd3c9c0c96db008135 (diff)
downloadnetsurf-b0f127aa2c6b166572999c3eda46e74c845aec19.tar.gz
netsurf-b0f127aa2c6b166572999c3eda46e74c845aec19.tar.bz2
Support HTML alignment hints.
svn path=/trunk/netsurf/; revision=9381
-rw-r--r--!NetSurf/Resources/CSS,f7936
-rw-r--r--css/dump.c22
-rw-r--r--css/select.c297
-rw-r--r--render/layout.c159
4 files changed, 421 insertions, 93 deletions
diff --git a/!NetSurf/Resources/CSS,f79 b/!NetSurf/Resources/CSS,f79
index bcf41812e..31adb3828 100644
--- a/!NetSurf/Resources/CSS,f79
+++ b/!NetSurf/Resources/CSS,f79
@@ -69,11 +69,8 @@ dir { display: block; padding-left: 1.5em; margin: 1.12em 0; }
menu { display: block; padding-left: 1.5em; margin: 1.12em 0; }
table { display: table; border-spacing: 2px; }
-table[align=left] { float: left; }
-table[align=center] { margin-left: auto; margin-right: auto; text-align: left; }
-table[align=right] { float: right; text-align: left; }
-caption { display: table-caption; text-align: center; }
+caption { display: table-caption; }
thead { display: table-header-group; vertical-align: middle; }
tfoot { display: table-footer-group; vertical-align: middle; }
@@ -82,34 +79,19 @@ tbody { display: table-row-group; vertical-align: middle; }
colgroup { display: table-column-group; }
col { display: table-column; }
-tr { display: table-row; vertical-align: middle; }
+table > tr { vertical-align: middle; }
+
+tr { display: table-row; vertical-align: inherit; }
td, th { display: table-cell; vertical-align: inherit; padding: 1px; }
-td { text-align: left; }
th { font-weight: bold; text-align: center; }
td[nowrap], th[nowrap] { white-space: nowrap; }
-tr[align=left] > td, tr[align=left] > th { text-align: left; }
-tr[align=center] > td, tr[align=center] > th { text-align: center; }
-tr[align=right] > td, tr[align=right] > th { text-align: right; }
-
-col[valign=top], colgroup[valign=top], tbody[valign=top], td[valign=top], tfoot[valign=top], th[valign=top], thead[valign=top], tr[valign=top] { vertical-align: top; }
-col[valign=middle], colgroup[valign=middle], tbody[valign=middle], td[valign=middle], tfoot[valign=middle], th[valign=middle], thead[valign=middle], tr[valign=middle] { vertical-align: middle; }
-col[valign=bottom], colgroup[valign=bottom], tbody[valign=bottom], td[valign=bottom], tfoot[valign=bottom], th[valign=bottom], thead[valign=bottom], tr[valign=bottom] { vertical-align: bottom; }
-
a:link { color: #00f; text-decoration: underline; }
img { color: #888; }
-img[align=left] { float: left; }
-img[align=right] { float: right; }
-object[align=left] { float: left; }
-object[align=right] { float: right; }
-
-applet[align=left] { float: left; }
-applet[align=right] { float: right; }
-
-center { display: block; text-align: center; }
+center { display: block; }
tt { font-family: monospace; }
i { font-style: italic; }
@@ -136,15 +118,11 @@ font[size="+4"] { font-size: xx-large }
hr { display: block; background-color: #000; height: 1px;
margin: 4px auto; border: 1px #d9d9d9 inset; }
-hr[align=left] { margin-left: 0; }
-hr[align=right] { margin-right: 0; }
hr[noshade] { background-color: #888; height: 2px; border: none; }
noframes { display: none; }
iframe { width: 19em; height: 10em; }
-iframe[align=left] { float: left; }
-iframe[align=right] { float: right; }
form { display: block; }
@@ -175,8 +153,4 @@ textarea { background-color: #fff; color: #000; text-align: left;
fieldset { display: block; border: thin solid #888; margin: 1.12em 0; }
-[align=left] { text-align: left; }
-[align=center] { text-align: center; }
-[align=right] { text-align: right; }
-
noembed, script, style, title { display: none; }
diff --git a/css/dump.c b/css/dump.c
index 430471382..9b1080233 100644
--- a/css/dump.c
+++ b/css/dump.c
@@ -1688,6 +1688,28 @@ void nscss_dump_computed_style(FILE *stream, const css_computed_style *style)
break;
}
+ /* -libcss-align */
+ val = css_computed_libcss_align(style);
+ switch (val) {
+ case CSS_LIBCSS_ALIGN_LEFT:
+ fprintf(stream, "-libcss-align: left ");
+ break;
+ case CSS_LIBCSS_ALIGN_RIGHT:
+ fprintf(stream, "-libcss-align: right ");
+ break;
+ case CSS_LIBCSS_ALIGN_CENTER:
+ fprintf(stream, "-libcss-align: center ");
+ break;
+ case CSS_LIBCSS_ALIGN_JUSTIFY:
+ fprintf(stream, "-libcss-align: justify ");
+ break;
+ case CSS_LIBCSS_ALIGN_DEFAULT:
+ fprintf(stream, "-libcss-align: default ");
+ break;
+ default:
+ break;
+ }
+
fprintf(stream, "}");
}
diff --git a/css/select.c b/css/select.c
index 3f3f297f9..12e25d536 100644
--- a/css/select.c
+++ b/css/select.c
@@ -1307,6 +1307,25 @@ css_error node_presentational_hint(void *pw, void *node,
xmlFree(bgcol);
return CSS_OK;
+ } else if (property == CSS_PROP_CAPTION_SIDE) {
+ xmlChar *align = NULL;
+
+ if (strcmp((const char *) n->name, "caption") == 0)
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "bottom") == 0) {
+ hint->status = CSS_CAPTION_SIDE_BOTTOM;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
} else if (property == CSS_PROP_COLOR) {
xmlChar *col;
css_error error;
@@ -1354,6 +1373,33 @@ css_error node_presentational_hint(void *pw, void *node,
xmlFree(col);
return CSS_OK;
+ } else if (property == CSS_PROP_FLOAT) {
+ xmlChar *align = NULL;
+
+ /** \todo input[type=image][align=*] - $11.3.3 */
+ if (strcmp((const char *) n->name, "table") == 0 ||
+ strcmp((const char *) n->name, "applet") == 0 ||
+ strcmp((const char *) n->name, "embed") == 0 ||
+ strcmp((const char *) n->name, "iframe") == 0 ||
+ strcmp((const char *) n->name, "img") == 0 ||
+ strcmp((const char *) n->name, "object") == 0)
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "left") == 0) {
+ hint->status = CSS_FLOAT_LEFT;
+ } else if (strcmp((const char *) align, "right") == 0) {
+ hint->status = CSS_FLOAT_RIGHT;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
} else if (property == CSS_PROP_HEIGHT) {
xmlChar *height;
@@ -1592,29 +1638,84 @@ css_error node_presentational_hint(void *pw, void *node,
return CSS_OK;
} else if (property == CSS_PROP_MARGIN_RIGHT ||
property == CSS_PROP_MARGIN_LEFT) {
- xmlChar *hspace;
+ xmlChar *hspace = NULL;
+ xmlChar *align = NULL;
if (strcmp((const char *) n->name, "img") == 0 ||
- strcmp((const char *) n->name, "applet") == 0)
+ strcmp((const char *) n->name, "applet") == 0) {
hspace = xmlGetProp(n, (const xmlChar *) "hspace");
- else
- hspace = NULL;
- if (hspace == NULL)
- return CSS_PROPERTY_NOT_SET;
+ if (hspace == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (parse_dimension((const char *) hspace, false,
+ &hint->data.length.value,
+ &hint->data.length.unit)) {
+ hint->status = CSS_MARGIN_SET;
+ } else {
+ xmlFree(hspace);
+ return CSS_PROPERTY_NOT_SET;
+ }
- if (parse_dimension((const char *) hspace, false,
- &hint->data.length.value,
- &hint->data.length.unit)) {
- hint->status = CSS_MARGIN_SET;
- } else {
xmlFree(hspace);
- return CSS_PROPERTY_NOT_SET;
- }
- xmlFree(hspace);
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "table") == 0) {
+ align = xmlGetProp(n, (const xmlChar *) "align");
- return CSS_OK;
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "center") == 0 ||
+ strcmp((const char *) align,
+ "abscenter") == 0 ||
+ strcmp((const char *) align,
+ "middle") == 0 ||
+ strcmp((const char *) align,
+ "absmiddle") == 0) {
+ hint->status = CSS_MARGIN_AUTO;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "hr") == 0) {
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "left") == 0) {
+ if (property == CSS_PROP_MARGIN_LEFT) {
+ hint->data.length.value = 0;
+ hint->data.length.unit = CSS_UNIT_PX;
+ hint->status = CSS_MARGIN_SET;
+ } else {
+ hint->status = CSS_MARGIN_AUTO;
+ }
+ } else if (strcmp((const char *) align,
+ "center") == 0) {
+ hint->status = CSS_MARGIN_AUTO;
+ } else if (strcmp((const char *) align, "right") == 0) {
+ if (property == CSS_PROP_MARGIN_RIGHT) {
+ hint->data.length.value = 0;
+ hint->data.length.unit = CSS_UNIT_PX;
+ hint->status = CSS_MARGIN_SET;
+ } else {
+ hint->status = CSS_MARGIN_AUTO;
+ }
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
+ }
} else if (property == CSS_PROP_PADDING_TOP ||
property == CSS_PROP_PADDING_RIGHT ||
property == CSS_PROP_PADDING_BOTTOM ||
@@ -1652,6 +1753,172 @@ css_error node_presentational_hint(void *pw, void *node,
xmlFree(cellpadding);
return CSS_OK;
+ } else if (property == CSS_PROP_TEXT_ALIGN) {
+ xmlChar *align = NULL;
+
+ if (strcmp((const char *) n->name, "p") == 0 ||
+ strcmp((const char *) n->name, "h1") == 0 ||
+ strcmp((const char *) n->name, "h2") == 0 ||
+ strcmp((const char *) n->name, "h3") == 0 ||
+ strcmp((const char *) n->name, "h4") == 0 ||
+ strcmp((const char *) n->name, "h5") == 0 ||
+ strcmp((const char *) n->name, "h6") == 0)
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "left") == 0) {
+ hint->status = CSS_TEXT_ALIGN_LEFT;
+ } else if (strcmp((const char *) align, "center") == 0) {
+ hint->status = CSS_TEXT_ALIGN_CENTER;
+ } else if (strcmp((const char *) align, "right") == 0) {
+ hint->status = CSS_TEXT_ALIGN_RIGHT;
+ } else if (strcmp((const char *) align, "justify") == 0) {
+ hint->status = CSS_TEXT_ALIGN_JUSTIFY;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
+ } else if (property == CSS_PROP_VERTICAL_ALIGN) {
+ xmlChar *valign = NULL;
+
+ if (strcmp((const char *) n->name, "col") == 0 ||
+ strcmp((const char *) n->name, "thead") == 0 ||
+ strcmp((const char *) n->name, "tbody") == 0 ||
+ strcmp((const char *) n->name, "tfoot") == 0 ||
+ strcmp((const char *) n->name, "tr") == 0 ||
+ strcmp((const char *) n->name, "td") == 0 ||
+ strcmp((const char *) n->name, "th") == 0) {
+ valign = xmlGetProp(n, (const xmlChar *) "valign");
+
+ if (valign == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) valign, "top") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_TOP;
+ } else if (strcmp((const char *) valign,
+ "middle") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_MIDDLE;
+ } else if (strcmp((const char *) valign,
+ "bottom") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_BOTTOM;
+ } else if (strcmp((const char *) valign,
+ "baseline") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_BASELINE;
+ } else {
+ xmlFree(valign);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(valign);
+
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "applet") == 0 ||
+ strcmp((const char *) n->name, "embed") == 0 ||
+ strcmp((const char *) n->name, "iframe") == 0 ||
+ strcmp((const char *) n->name, "img") == 0 ||
+ strcmp((const char *) n->name, "object") == 0) {
+ /** \todo input[type=image][align=*] - $11.3.3 */
+ valign = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (valign == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) valign, "top") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_TOP;
+ } else if (strcmp((const char *) valign,
+ "bottom") == 0 ||
+ strcmp((const char *) valign,
+ "baseline") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_BASELINE;
+ } else if (strcmp((const char *) valign,
+ "texttop") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_TEXT_TOP;
+ } else if (strcmp((const char *) valign,
+ "absmiddle") == 0 ||
+ strcmp((const char *) valign,
+ "abscenter") == 0) {
+ hint->status = CSS_VERTICAL_ALIGN_MIDDLE;
+ } else {
+ xmlFree(valign);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(valign);
+
+ return CSS_OK;
+ }
+ } else if (property == CSS_PROP_LIBCSS_ALIGN) {
+ xmlChar *align = NULL;
+
+ if (strcmp((const char *) n->name, "center") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_CENTER;
+
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "caption") == 0) {
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL || strcmp((const char *) align,
+ "center") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_CENTER;
+ } else if (strcmp((const char *) align, "left") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_LEFT;
+ } else if (strcmp((const char *) align, "right") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_RIGHT;
+ } else if (strcmp((const char *) align,
+ "justify") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_JUSTIFY;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ if (align != NULL)
+ xmlFree(align);
+
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "div") == 0 ||
+ strcmp((const char *) n->name, "thead") == 0 ||
+ strcmp((const char *) n->name, "tbody") == 0 ||
+ strcmp((const char *) n->name, "tfoot") == 0 ||
+ strcmp((const char *) n->name, "tr") == 0 ||
+ strcmp((const char *) n->name, "td") == 0 ||
+ strcmp((const char *) n->name, "th") == 0) {
+ align = xmlGetProp(n, (const xmlChar *) "align");
+
+ if (align == NULL)
+ return CSS_PROPERTY_NOT_SET;
+
+ if (strcmp((const char *) align, "center") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_CENTER;
+ } else if (strcmp((const char *) align, "left") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_LEFT;
+ } else if (strcmp((const char *) align, "right") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_RIGHT;
+ } else if (strcmp((const char *) align,
+ "justify") == 0) {
+ hint->status = CSS_LIBCSS_ALIGN_JUSTIFY;
+ } else {
+ xmlFree(align);
+ return CSS_PROPERTY_NOT_SET;
+ }
+
+ xmlFree(align);
+
+ return CSS_OK;
+ } else if (strcmp((const char *) n->name, "table") == 0) {
+ /* Tables reset HTML alignment */
+ hint->status = CSS_LIBCSS_ALIGN_DEFAULT;
+
+ return CSS_OK;
+ } else {
+ return CSS_PROPERTY_NOT_SET;
+ }
}
return CSS_PROPERTY_NOT_SET;
diff --git a/render/layout.c b/render/layout.c
index f2c0c158e..0bae98afe 100644
--- a/render/layout.c
+++ b/render/layout.c
@@ -70,9 +70,8 @@ static void layout_block_find_dimensions(int available_width,
struct box *box);
static bool layout_apply_minmax_height(struct box *box, struct box *container);
static void layout_block_add_scrollbar(struct box *box, int which);
-static int layout_solve_width(int available_width, int width, int lm, int rm,
- int max_width, int min_width,
- int margin[4], int padding[4], struct box_border border[4]);
+static int layout_solve_width(struct box *box, int available_width, int width,
+ int lm, int rm, int max_width, int min_width);
static void layout_float_find_dimensions(int available_width,
const css_computed_style *style, struct box *box);
static void layout_find_dimensions(int available_width, int viewport_height,
@@ -420,9 +419,8 @@ bool layout_block_context(struct box *block, int viewport_height,
if (!layout_table(box, box->parent->width - lm - rm,
content))
return false;
- layout_solve_width(box->parent->width, box->width,
- lm, rm, -1, -1, box->margin,
- box->padding, box->border);
+ layout_solve_width(box, box->parent->width, box->width,
+ lm, rm, -1, -1);
}
/* Position box: horizontal. */
@@ -856,8 +854,8 @@ void layout_block_find_dimensions(int available_width, int viewport_height,
}
}
- box->width = layout_solve_width(available_width, width, lm, rm,
- max_width, min_width, margin, padding, border);
+ box->width = layout_solve_width(box, available_width, width, lm, rm,
+ max_width, min_width);
box->height = height;
if (margin[TOP] == AUTO)
@@ -1012,6 +1010,7 @@ void layout_block_add_scrollbar(struct box *box, int which)
/**
* Solve the width constraint as given in CSS 2.1 section 10.3.3.
*
+ * \param box Box to solve constraint for
* \param available_width Max width available in pixels
* \param width Current box width
* \param lm Min left margin required to avoid floats in px.
@@ -1020,74 +1019,111 @@ void layout_block_add_scrollbar(struct box *box, int which)
* zero if not applicable
* \param max_width Box max-width ( -ve means no max-width to apply)
* \param min_width Box min-width ( <=0 means no min-width to apply)
- * \param margin[4] Current box margins. Updated with new box
- * left / right margins
- * \param padding[4] Current box paddings.
- * \param border[4] Current box border widths.
* \return New box width
+ *
+ * \post \a box's left/right margins will be updated.
*/
-int layout_solve_width(int available_width, int width, int lm, int rm,
- int max_width, int min_width,
- int margin[4], int padding[4], struct box_border border[4])
+int layout_solve_width(struct box *box, int available_width, int width,
+ int lm, int rm, int max_width, int min_width)
{
bool auto_width = false;
/* Increase specified left/right margins */
- if (margin[LEFT] != AUTO && margin[LEFT] < lm && margin[LEFT] >= 0)
- margin[LEFT] = lm;
- if (margin[RIGHT] != AUTO && margin[RIGHT] < rm && margin[RIGHT] >= 0)
- margin[RIGHT] = rm;
+ if (box->margin[LEFT] != AUTO && box->margin[LEFT] < lm &&
+ box->margin[LEFT] >= 0)
+ box->margin[LEFT] = lm;
+ if (box->margin[RIGHT] != AUTO && box->margin[RIGHT] < rm &&
+ box->margin[RIGHT] >= 0)
+ box->margin[RIGHT] = rm;
/* Find width */
if (width == AUTO) {
/* any other 'auto' become 0 or the minimum required values */
- if (margin[LEFT] == AUTO) margin[LEFT] = lm;
- if (margin[RIGHT] == AUTO) margin[RIGHT] = rm;
+ if (box->margin[LEFT] == AUTO)
+ box->margin[LEFT] = lm;
+ if (box->margin[RIGHT] == AUTO)
+ box->margin[RIGHT] = rm;
width = available_width -
- (margin[LEFT] + border[LEFT].width +
- padding[LEFT] + padding[RIGHT] +
- border[RIGHT].width + margin[RIGHT]);
+ (box->margin[LEFT] + box->border[LEFT].width +
+ box->padding[LEFT] + box->padding[RIGHT] +
+ box->border[RIGHT].width + box->margin[RIGHT]);
width = width < 0 ? 0 : width;
auto_width = true;
}
+
if (max_width >= 0 && width > max_width) {
/* max-width is admissable and width exceeds max-width */
width = max_width;
auto_width = false;
}
+
if (min_width > 0 && width < min_width) {
/* min-width is admissable and width is less than max-width */
width = min_width;
auto_width = false;
}
- if (!auto_width && margin[LEFT] == AUTO && margin[RIGHT] == AUTO) {
- /* make the margins equal, centering the element */
- margin[LEFT] = margin[RIGHT] = (available_width - lm - rm -
- (border[LEFT].width + padding[LEFT] + width +
- padding[RIGHT] + border[RIGHT].width)) / 2;
+ /* Width was auto, and unconstrained by min/max width, so we're done */
+ if (auto_width)
+ return width;
+
+ /* Width was not auto, or was constrained by min/max width
+ * Need to compute left/right margins */
+
+ /* HTML alignment (only applies to over-constrained boxes)
+ * Additionally, we ignore HTML alignment for any boxes whose
+ * parent has non-default text-align. */
+ if (box->margin[LEFT] != AUTO && box->margin[RIGHT] != AUTO &&
+ box->parent != NULL && box->parent->style != NULL &&
+ css_computed_text_align(box->parent->style) ==
+ CSS_TEXT_ALIGN_DEFAULT) {
+ switch (css_computed_libcss_align(box->parent->style)) {
+ case CSS_LIBCSS_ALIGN_RIGHT:
+ box->margin[LEFT] = AUTO;
+ box->margin[RIGHT] = 0;
+ break;
+ case CSS_LIBCSS_ALIGN_CENTER:
+ box->margin[LEFT] = box->margin[RIGHT] = AUTO;
+ break;
+ case CSS_LIBCSS_ALIGN_LEFT:
+ case CSS_LIBCSS_ALIGN_JUSTIFY:
+ box->margin[LEFT] = 0;
+ box->margin[RIGHT] = AUTO;
+ break;
+ }
+ }
- if (margin[LEFT] < 0) {
- margin[RIGHT] += margin[LEFT];
- margin[LEFT] = 0;
+ if (box->margin[LEFT] == AUTO && box->margin[RIGHT] == AUTO) {
+ /* make the margins equal, centering the element */
+ box->margin[LEFT] = box->margin[RIGHT] =
+ (available_width - lm - rm -
+ (box->border[LEFT].width + box->padding[LEFT] +
+ width + box->padding[RIGHT] +
+ box->border[RIGHT].width)) / 2;
+
+ if (box->margin[LEFT] < 0) {
+ box->margin[RIGHT] += box->margin[LEFT];
+ box->margin[LEFT] = 0;
}
- margin[LEFT] += lm;
+ box->margin[LEFT] += lm;
- } else if (!auto_width && margin[LEFT] == AUTO) {
- margin[LEFT] = available_width - lm -
- (border[LEFT].width + padding[LEFT] + width +
- padding[RIGHT] + border[RIGHT].width +
- margin[RIGHT]);
- margin[LEFT] = margin[LEFT] < lm ? lm : margin[LEFT];
- } else if (!auto_width) {
+ } else if (box->margin[LEFT] == AUTO) {
+ box->margin[LEFT] = available_width - lm -
+ (box->border[LEFT].width + box->padding[LEFT] +
+ width + box->padding[RIGHT] +
+ box->border[RIGHT].width + box->margin[RIGHT]);
+ box->margin[LEFT] = box->margin[LEFT] < lm
+ ? lm : box->margin[LEFT];
+ } else {
/* margin-right auto or "over-constrained" */
- margin[RIGHT] = available_width - rm -
- (margin[LEFT] + border[LEFT].width +
- padding[LEFT] + width + padding[RIGHT] +
- border[RIGHT].width);
+ box->margin[RIGHT] = available_width - rm -
+ (box->margin[LEFT] + box->border[LEFT].width +
+ box->padding[LEFT] + width +
+ box->padding[RIGHT] +
+ box->border[RIGHT].width);
}
return width;
@@ -2416,9 +2452,38 @@ bool layout_line(struct box *first, int *width, int *y,
case CSS_TEXT_ALIGN_CENTER:
x0 = (x0 + (x1 - x)) / 2;
break;
- default:
+ case CSS_TEXT_ALIGN_LEFT:
+ case CSS_TEXT_ALIGN_JUSTIFY:
/* leave on left */
break;
+ case CSS_TEXT_ALIGN_DEFAULT:
+ /* No specified text-align; consider html alignment */
+ switch (css_computed_libcss_align(
+ first->parent->parent->style)) {
+ case CSS_LIBCSS_ALIGN_RIGHT:
+ x0 = x1 - x;
+ break;
+ case CSS_LIBCSS_ALIGN_CENTER:
+ x0 = (x0 + (x1 - x)) / 2;
+ break;
+ case CSS_LIBCSS_ALIGN_LEFT:
+ case CSS_LIBCSS_ALIGN_JUSTIFY:
+ /* leave on left */
+ break;
+ case CSS_LIBCSS_ALIGN_DEFAULT:
+ /* None; consider text direction */
+ switch (css_computed_direction(
+ first->parent->parent->style)) {
+ case CSS_DIRECTION_LTR:
+ /* leave on left */
+ break;
+ case CSS_DIRECTION_RTL:
+ x0 = x1 - x;
+ break;
+ }
+ break;
+ }
+ break;
}
for (d = first; d != b; d = d->next) {
@@ -4177,8 +4242,8 @@ bool layout_absolute(struct box *box, struct box *containing_block,
/* \todo layout_table considers margins etc. again */
if (!layout_table(box, width, content))
return false;
- layout_solve_width(box->parent->width, box->width, 0, 0, -1, -1,
- box->margin, box->padding, box->border);
+ layout_solve_width(box, box->parent->width, box->width, 0, 0,
+ -1, -1);
}
/* 10.6.4 */