layout: Implement inline margins.

Improves the Google SERPs.

We mark `html/rendering/replaced-elements/images/space.html` as failing.
This test tested whether `<img hspace>` and inline margins do the same
thing. Since this was trivially the case before (since we implemented
neither) and now is not, this test now fails.
This commit is contained in:
Patrick Walton 2015-05-04 17:23:29 -07:00
parent 92f46e3149
commit b17b90c8df
10 changed files with 190 additions and 57 deletions

View file

@ -15,12 +15,11 @@ use std::hash::{Hash, Hasher};
use std::sync::Arc;
use util::fnv::FnvHasher;
use util::logical_geometry::{WritingMode, LogicalMargin};
use util::logical_geometry::{LogicalMargin, PhysicalSide, WritingMode};
use util::geometry::Au;
use url::Url;
use cssparser::{Parser, Color, RGBA, AtRuleParser, DeclarationParser,
DeclarationListParser, parse_important, ToCss};
use geom::num::Zero;
use geom::SideOffsets2D;
use geom::size::Size2D;
@ -5723,21 +5722,78 @@ pub fn modify_style_for_replaced_content(style: &mut Arc<ComputedValues>) {
style.box_.make_unique().vertical_align =
longhands::vertical_align::computed_value::T::baseline
}
// Reset margins.
if style.margin.margin_top != computed::LengthOrPercentageOrAuto::Length(Au(0)) ||
style.margin.margin_left != computed::LengthOrPercentageOrAuto::Length(Au(0)) ||
style.margin.margin_bottom != computed::LengthOrPercentageOrAuto::Length(Au(0)) ||
style.margin.margin_right != computed::LengthOrPercentageOrAuto::Length(Au(0)) {
let mut style = style.make_unique();
let margin = style.margin.make_unique();
margin.margin_top = computed::LengthOrPercentageOrAuto::Length(Au(0));
margin.margin_left = computed::LengthOrPercentageOrAuto::Length(Au(0));
margin.margin_bottom = computed::LengthOrPercentageOrAuto::Length(Au(0));
margin.margin_right = computed::LengthOrPercentageOrAuto::Length(Au(0));
}
}
/// Sets `border_${side}_width` to the passed in values.
/// If `border_${side}_width` == 0 also sets `border_${side}_style` = none.
/// Adjusts borders, padding, and margins as appropriate to account for a fragment's status as the
/// first or last fragment within the range of an element.
///
/// Specifically, this function sets border/padding/margin widths to zero on the sides for which
/// the fragment is not outermost.
#[inline]
pub fn make_border(style: &ComputedValues, border_width: LogicalMargin<Au>) -> ComputedValues {
let mut style = (*style).clone();
let physical_border = LogicalMargin::to_physical(&border_width, style.writing_mode);
% for side in ["top", "right", "bottom", "left"]:
style.border.make_unique().border_${side}_width = physical_border.${side};
if physical_border.${side} == Zero::zero() {
style.border.make_unique().border_${side}_style = BorderStyle::none;
pub fn modify_style_for_inline_sides(style: &mut Arc<ComputedValues>,
is_first_fragment_of_element: bool,
is_last_fragment_of_element: bool) {
fn modify_side(style: &mut Arc<ComputedValues>, side: PhysicalSide) {
let mut style = style.make_unique();
let border = style.border.make_unique();
match side {
PhysicalSide::Left => {
border.border_left_width = Au(0);
border.border_left_style = BorderStyle::none;
style.padding.make_unique().padding_left =
computed::LengthOrPercentage::Length(Au(0));
style.margin.make_unique().margin_left =
computed::LengthOrPercentageOrAuto::Length(Au(0))
}
PhysicalSide::Right => {
border.border_right_width = Au(0);
border.border_right_style = BorderStyle::none;
style.padding.make_unique().padding_right =
computed::LengthOrPercentage::Length(Au(0));
style.margin.make_unique().margin_right =
computed::LengthOrPercentageOrAuto::Length(Au(0))
}
PhysicalSide::Bottom => {
border.border_bottom_width = Au(0);
border.border_bottom_style = BorderStyle::none;
style.padding.make_unique().padding_bottom =
computed::LengthOrPercentage::Length(Au(0));
style.margin.make_unique().margin_bottom =
computed::LengthOrPercentageOrAuto::Length(Au(0))
}
PhysicalSide::Top => {
border.border_top_width = Au(0);
border.border_top_style = BorderStyle::none;
style.padding.make_unique().padding_top =
computed::LengthOrPercentage::Length(Au(0));
style.margin.make_unique().margin_top =
computed::LengthOrPercentageOrAuto::Length(Au(0))
}
}
% endfor
style
}
if !is_first_fragment_of_element {
let side = style.writing_mode.inline_start_physical_side();
modify_side(style, side)
}
if !is_last_fragment_of_element {
let side = style.writing_mode.inline_end_physical_side();
modify_side(style, side)
}
}
pub fn is_supported_property(property: &str) -> bool {