diff --git a/Libraries/LibWeb/DOM/Document.cpp b/Libraries/LibWeb/DOM/Document.cpp index 100f78caba..b8bc63fe3f 100644 --- a/Libraries/LibWeb/DOM/Document.cpp +++ b/Libraries/LibWeb/DOM/Document.cpp @@ -400,13 +400,25 @@ void Document::update_layout() } } -void Document::update_style() +static void update_style_recursively(DOM::Node& node) { - for_each_in_subtree_of_type([&](auto& element) { - if (element.needs_style_update()) - element.recompute_style(); + node.for_each_child([&](auto& child) { + if (child.needs_style_update()) { + if (is(child)) + downcast(child).recompute_style(); + child.set_needs_style_update(false); + } + if (child.child_needs_style_update()) { + update_style_recursively(child); + child.set_child_needs_style_update(false); + } return IterationDecision::Continue; }); +} + +void Document::update_style() +{ + update_style_recursively(*this); update_layout(); } diff --git a/Libraries/LibWeb/DOM/Node.cpp b/Libraries/LibWeb/DOM/Node.cpp index 00db6829e4..aca4a39637 100644 --- a/Libraries/LibWeb/DOM/Node.cpp +++ b/Libraries/LibWeb/DOM/Node.cpp @@ -254,8 +254,17 @@ void Node::set_needs_style_update(bool value) if (m_needs_style_update == value) return; m_needs_style_update = value; - if (m_needs_style_update) + + if (m_needs_style_update) { + for (auto* ancestor = parent(); ancestor; ancestor = ancestor->parent()) + ancestor->m_child_needs_style_update = true; document().schedule_style_update(); + } +} + +void Node::inserted_into(Node&) +{ + set_needs_style_update(true); } } diff --git a/Libraries/LibWeb/DOM/Node.h b/Libraries/LibWeb/DOM/Node.h index 5409d05a66..b34a3a1182 100644 --- a/Libraries/LibWeb/DOM/Node.h +++ b/Libraries/LibWeb/DOM/Node.h @@ -126,7 +126,7 @@ public: Element* parent_element(); const Element* parent_element() const; - virtual void inserted_into(Node&) { } + virtual void inserted_into(Node&); virtual void removed_from(Node&) { } virtual void children_changed() { } @@ -140,6 +140,9 @@ public: bool needs_style_update() const { return m_needs_style_update; } void set_needs_style_update(bool); + bool child_needs_style_update() const { return m_child_needs_style_update; } + void set_child_needs_style_update(bool b) { m_child_needs_style_update = b; } + void invalidate_style(); bool is_link() const; @@ -157,7 +160,8 @@ protected: Document* m_document { nullptr }; mutable WeakPtr m_layout_node; NodeType m_type { NodeType::INVALID }; - bool m_needs_style_update { true }; + bool m_needs_style_update { false }; + bool m_child_needs_style_update { false }; }; }