diff options
author | Martin Robinson <mrobinson@igalia.com> | 2025-04-07 19:49:05 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2025-04-07 17:49:05 +0000 |
commit | 2b63e60e8f2740f55a3a4fa0d918097e3b6fec97 (patch) | |
tree | e4cf9eff85b7520766e52ab83477fc87f930da25 /components/layout_2020 | |
parent | a5c547259f4a1eda8f266e6cc3f673d21d66723b (diff) | |
download | servo-2b63e60e8f2740f55a3a4fa0d918097e3b6fec97.tar.gz servo-2b63e60e8f2740f55a3a4fa0d918097e3b6fec97.zip |
layout: Add initial support for the `::marker` pseudo-element (#36317)
This change adds support for the `::marker` pseudo-element and ensure
that
markers are cached into the box tree. This is only initial support,
there are a few
things missing such as animations, transitions, and support the
`content` CSS
property.
Testing: There are WPT tests for this change.
Signed-off-by: Martin Robinson <mrobinson@igalia.com>
Signed-off-by: Martin Robinson <mrobinson@igalia.com>
Diffstat (limited to 'components/layout_2020')
-rw-r--r-- | components/layout_2020/dom.rs | 4 | ||||
-rw-r--r-- | components/layout_2020/dom_traversal.rs | 4 | ||||
-rw-r--r-- | components/layout_2020/flow/construct.rs | 4 | ||||
-rw-r--r-- | components/layout_2020/lists.rs | 6 | ||||
-rw-r--r-- | components/layout_2020/query.rs | 4 |
5 files changed, 13 insertions, 9 deletions
diff --git a/components/layout_2020/dom.rs b/components/layout_2020/dom.rs index f8b3d6f9c29..2e8a823c11e 100644 --- a/components/layout_2020/dom.rs +++ b/components/layout_2020/dom.rs @@ -34,6 +34,7 @@ pub struct InnerDOMLayoutData { pub(super) self_box: ArcRefCell<Option<LayoutBox>>, pub(super) pseudo_before_box: ArcRefCell<Option<LayoutBox>>, pub(super) pseudo_after_box: ArcRefCell<Option<LayoutBox>>, + pub(super) pseudo_marker_box: ArcRefCell<Option<LayoutBox>>, } /// A box that is stored in one of the `DOMLayoutData` slots. @@ -222,6 +223,7 @@ where let cell = match pseudo_element_type { PseudoElement::Before => &data.pseudo_before_box, PseudoElement::After => &data.pseudo_after_box, + PseudoElement::Marker => &data.pseudo_marker_box, _ => unreachable!( "Asked for box slot for unsupported pseudo-element: {:?}", pseudo_element_type @@ -235,6 +237,7 @@ where let cell = match pseudo_element_type { PseudoElement::Before => &data.pseudo_before_box, PseudoElement::After => &data.pseudo_after_box, + PseudoElement::Marker => &data.pseudo_marker_box, _ => unreachable!( "Asked for box slot for unsupported pseudo-element: {:?}", pseudo_element_type @@ -248,6 +251,7 @@ where *data.self_box.borrow_mut() = None; *data.pseudo_before_box.borrow_mut() = None; *data.pseudo_after_box.borrow_mut() = None; + *data.pseudo_marker_box.borrow_mut() = None; // Stylo already takes care of removing all layout data // for DOM descendants of elements with `display: none`. } diff --git a/components/layout_2020/dom_traversal.rs b/components/layout_2020/dom_traversal.rs index bcb6555fd13..5800637c50f 100644 --- a/components/layout_2020/dom_traversal.rs +++ b/components/layout_2020/dom_traversal.rs @@ -236,6 +236,10 @@ fn traverse_element<'dom, Node>( ) where Node: NodeExt<'dom>, { + // Clear any existing pseudo-element box slot, because markers are not handled like + // `::before`` and `::after`. They are processed during box tree creation. + element.unset_pseudo_element_box(PseudoElement::Marker); + let replaced = ReplacedContents::for_element(element, context); let style = element.style(context); match Display::from(style.get_box().display) { diff --git a/components/layout_2020/flow/construct.rs b/components/layout_2020/flow/construct.rs index ef73ee3d007..c7667231260 100644 --- a/components/layout_2020/flow/construct.rs +++ b/components/layout_2020/flow/construct.rs @@ -393,7 +393,7 @@ where is_list_item: false, }, NonReplacedContents::OfPseudoElement(contents).into(), - BoxSlot::dummy(), + info.node.pseudo_element_box_slot(PseudoElement::Marker), ); } @@ -405,7 +405,7 @@ where ) { self.block_level_boxes.push(BlockLevelJob { info: info.clone(), - box_slot: BoxSlot::dummy(), + box_slot: info.node.pseudo_element_box_slot(PseudoElement::Marker), kind: BlockLevelCreator::OutsideMarker { contents, list_item_style, diff --git a/components/layout_2020/lists.rs b/components/layout_2020/lists.rs index ee60a82ef01..d5a1f863865 100644 --- a/components/layout_2020/lists.rs +++ b/components/layout_2020/lists.rs @@ -19,11 +19,7 @@ pub(crate) fn make_marker<'dom, Node>( where Node: NodeExt<'dom>, { - // TODO: use `PseudoElement::Marker` when we add it. - let marker_info = info.pseudo( - context, - style::selector_parser::PseudoElement::ServoLegacyText, - )?; + let marker_info = info.pseudo(context, style::selector_parser::PseudoElement::Marker)?; let style = &marker_info.style; let list_style = style.get_list(); diff --git a/components/layout_2020/query.rs b/components/layout_2020/query.rs index 108a4e0540c..cf745376ecf 100644 --- a/components/layout_2020/query.rs +++ b/components/layout_2020/query.rs @@ -131,7 +131,7 @@ pub fn process_resolved_style_request<'dom>( None => layout_element, }; - let style = &*layout_element.resolved_style(); + let style = &*layout_element.style(context); let longhand_id = match *property { PropertyId::NonCustom(id) => match id.longhand_or_shorthand() { Ok(longhand_id) => longhand_id, @@ -1122,7 +1122,7 @@ where let element = node.as_element().unwrap(); let parent_style = if node.is_connected() { if element.has_data() { - node.to_threadsafe().as_element().unwrap().resolved_style() + node.to_threadsafe().as_element().unwrap().style(context) } else { let mut tlc = ThreadLocalStyleContext::new(); let mut context = StyleContext { |