1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-26 18:47:44 +00:00

LibWeb: Allocate storage for pseudo element layout nodes on demand

This saves us 64 bytes for every element that doesn't have pseudo
elements associated with it. Which is most of them. :^)
This commit is contained in:
Andreas Kling 2023-11-19 20:30:13 +01:00
parent 37505d9746
commit 48dbec8a9e
2 changed files with 21 additions and 8 deletions

View file

@ -125,8 +125,10 @@ void Element::visit_edges(Cell::Visitor& visitor)
visitor.visit(m_class_list); visitor.visit(m_class_list);
visitor.visit(m_shadow_root); visitor.visit(m_shadow_root);
visitor.visit(m_custom_element_definition); visitor.visit(m_custom_element_definition);
for (auto& pseudo_element_layout_node : m_pseudo_element_nodes) if (m_pseudo_element_nodes) {
visitor.visit(pseudo_element_layout_node); for (auto& pseudo_element_layout_node : *m_pseudo_element_nodes)
visitor.visit(pseudo_element_layout_node);
}
for (auto& registered_intersection_observers : m_registered_intersection_observers) for (auto& registered_intersection_observers : m_registered_intersection_observers)
visitor.visit(registered_intersection_observers.observer); visitor.visit(registered_intersection_observers.observer);
} }
@ -987,23 +989,33 @@ void Element::children_changed()
void Element::set_pseudo_element_node(Badge<Layout::TreeBuilder>, CSS::Selector::PseudoElement pseudo_element, JS::GCPtr<Layout::Node> pseudo_element_node) void Element::set_pseudo_element_node(Badge<Layout::TreeBuilder>, CSS::Selector::PseudoElement pseudo_element, JS::GCPtr<Layout::Node> pseudo_element_node)
{ {
m_pseudo_element_nodes[to_underlying(pseudo_element)] = pseudo_element_node; if (!m_pseudo_element_nodes) {
if (!pseudo_element_node)
return;
m_pseudo_element_nodes = make<PseudoElementLayoutNodes>();
}
(*m_pseudo_element_nodes)[to_underlying(pseudo_element)] = pseudo_element_node;
} }
JS::GCPtr<Layout::Node> Element::get_pseudo_element_node(CSS::Selector::PseudoElement pseudo_element) const JS::GCPtr<Layout::Node> Element::get_pseudo_element_node(CSS::Selector::PseudoElement pseudo_element) const
{ {
return m_pseudo_element_nodes[to_underlying(pseudo_element)]; if (!m_pseudo_element_nodes)
return nullptr;
return (*m_pseudo_element_nodes)[to_underlying(pseudo_element)];
} }
void Element::clear_pseudo_element_nodes(Badge<Layout::TreeBuilder>) void Element::clear_pseudo_element_nodes(Badge<Layout::TreeBuilder>)
{ {
m_pseudo_element_nodes.fill({}); m_pseudo_element_nodes = nullptr;
} }
void Element::serialize_pseudo_elements_as_json(JsonArraySerializer<StringBuilder>& children_array) const void Element::serialize_pseudo_elements_as_json(JsonArraySerializer<StringBuilder>& children_array) const
{ {
for (size_t i = 0; i < m_pseudo_element_nodes.size(); ++i) { if (!m_pseudo_element_nodes)
auto& pseudo_element_node = m_pseudo_element_nodes[i]; return;
for (size_t i = 0; i < m_pseudo_element_nodes->size(); ++i) {
auto& pseudo_element_node = (*m_pseudo_element_nodes)[i];
if (!pseudo_element_node) if (!pseudo_element_node)
continue; continue;
auto object = MUST(children_array.add_object()); auto object = MUST(children_array.add_object());

View file

@ -412,7 +412,8 @@ private:
Optional<FlyString> m_id; Optional<FlyString> m_id;
Array<JS::GCPtr<Layout::Node>, to_underlying(CSS::Selector::PseudoElement::PseudoElementCount)> m_pseudo_element_nodes; using PseudoElementLayoutNodes = Array<JS::GCPtr<Layout::Node>, to_underlying(CSS::Selector::PseudoElement::PseudoElementCount)>;
OwnPtr<PseudoElementLayoutNodes> m_pseudo_element_nodes;
// https://html.spec.whatwg.org/multipage/custom-elements.html#custom-element-reaction-queue // https://html.spec.whatwg.org/multipage/custom-elements.html#custom-element-reaction-queue
// All elements have an associated custom element reaction queue, initially empty. Each item in the custom element reaction queue is of one of two types: // All elements have an associated custom element reaction queue, initially empty. Each item in the custom element reaction queue is of one of two types: