Set in the DOM the box generated by the root element

This commit is contained in:
Simon Sapin 2020-04-17 19:45:40 +02:00
parent 09dbf91e7b
commit ee62c7f2e4

View file

@ -9,6 +9,7 @@ use crate::display_list::stacking_context::{
StackingContextBuilder, StackingContextBuilder,
}; };
use crate::dom_traversal::{Contents, NodeExt}; use crate::dom_traversal::{Contents, NodeExt};
use crate::element_data::LayoutBox;
use crate::flow::construct::ContainsFloats; use crate::flow::construct::ContainsFloats;
use crate::flow::float::FloatBox; use crate::flow::float::FloatBox;
use crate::flow::{BlockContainer, BlockFormattingContext, BlockLevelBox}; use crate::flow::{BlockContainer, BlockFormattingContext, BlockLevelBox};
@ -53,6 +54,10 @@ impl BoxTreeRoot {
Node: 'dom + Copy + LayoutNode<'dom> + Send + Sync, Node: 'dom + Copy + LayoutNode<'dom> + Send + Sync,
{ {
let (contains_floats, boxes) = construct_for_root_element(&context, root_element); let (contains_floats, boxes) = construct_for_root_element(&context, root_element);
// Zero box for `:root { display: none }`, one for the root element otherwise.
assert!(boxes.len() <= 1);
Self(BlockFormattingContext { Self(BlockFormattingContext {
contains_floats: contains_floats == ContainsFloats::Yes, contains_floats: contains_floats == ContainsFloats::Yes,
contents: BlockContainer::BlockLevelBoxes(boxes), contents: BlockContainer::BlockLevelBoxes(boxes),
@ -68,7 +73,10 @@ fn construct_for_root_element<'dom>(
let box_style = style.get_box(); let box_style = style.get_box();
let display_inside = match Display::from(box_style.display) { let display_inside = match Display::from(box_style.display) {
Display::None => return (ContainsFloats::No, Vec::new()), Display::None => {
root_element.unset_boxes_in_subtree();
return (ContainsFloats::No, Vec::new());
},
Display::Contents => { Display::Contents => {
// Unreachable because the style crate adjusts the computed values: // Unreachable because the style crate adjusts the computed values:
// https://drafts.csswg.org/css-display-3/#transformations // https://drafts.csswg.org/css-display-3/#transformations
@ -81,45 +89,50 @@ fn construct_for_root_element<'dom>(
let contents = let contents =
ReplacedContent::for_element(root_element).map_or(Contents::OfElement, Contents::Replaced); ReplacedContent::for_element(root_element).map_or(Contents::OfElement, Contents::Replaced);
if box_style.position.is_absolutely_positioned() { let (contains_floats, root_box) = if box_style.position.is_absolutely_positioned() {
( (
ContainsFloats::No, ContainsFloats::No,
vec![ArcRefCell::new( BlockLevelBox::OutOfFlowAbsolutelyPositionedBox(Arc::new(
BlockLevelBox::OutOfFlowAbsolutelyPositionedBox(Arc::new( AbsolutelyPositionedBox::construct(
AbsolutelyPositionedBox::construct(
context,
root_element,
style,
display_inside,
contents,
),
)),
)],
)
} else if box_style.float.is_floating() {
(
ContainsFloats::Yes,
vec![ArcRefCell::new(BlockLevelBox::OutOfFlowFloatBox(
FloatBox::construct(context, root_element, style, display_inside, contents),
))],
)
} else {
let propagated_text_decoration_line = style.clone_text_decoration_line();
(
ContainsFloats::No,
vec![ArcRefCell::new(BlockLevelBox::Independent(
IndependentFormattingContext::construct(
context, context,
root_element, root_element,
style, style,
display_inside, display_inside,
contents, contents,
ContentSizesRequest::None,
propagated_text_decoration_line,
), ),
))], )),
) )
} } else if box_style.float.is_floating() {
(
ContainsFloats::Yes,
BlockLevelBox::OutOfFlowFloatBox(FloatBox::construct(
context,
root_element,
style,
display_inside,
contents,
)),
)
} else {
let propagated_text_decoration_line = style.clone_text_decoration_line();
(
ContainsFloats::No,
BlockLevelBox::Independent(IndependentFormattingContext::construct(
context,
root_element,
style,
display_inside,
contents,
ContentSizesRequest::None,
propagated_text_decoration_line,
)),
)
};
let root_box = ArcRefCell::new(root_box);
root_element
.element_box_slot()
.set(LayoutBox::BlockLevel(root_box.clone()));
(contains_floats, vec![root_box])
} }
impl BoxTreeRoot { impl BoxTreeRoot {
@ -158,7 +171,14 @@ impl BoxTreeRoot {
.fragments .fragments
.into_iter() .into_iter()
.map(|fragment| ArcRefCell::new(fragment)) .map(|fragment| ArcRefCell::new(fragment))
.collect(); .collect::<Vec<_>>();
// Zero box for `:root { display: none }`, one for the root element otherwise.
assert!(children.len() <= 1);
// There may be more fragments at the top-level
// (for positioned boxes whose containing is the initial containing block)
// but only if there was one fragment for the root element.
positioning_context.layout_initial_containing_block_children( positioning_context.layout_initial_containing_block_children(
layout_context, layout_context,
&initial_containing_block, &initial_containing_block,