diff --git a/Libraries/LibWeb/Layout/Node.cpp b/Libraries/LibWeb/Layout/Node.cpp index b92f558de04..d513d84db76 100644 --- a/Libraries/LibWeb/Layout/Node.cpp +++ b/Libraries/LibWeb/Layout/Node.cpp @@ -1109,6 +1109,11 @@ GC::Ref NodeWithStyle::create_anonymous_wrapper() const return *wrapper; } +void NodeWithStyle::set_computed_values(NonnullOwnPtr computed_values) +{ + m_computed_values = move(computed_values); +} + void NodeWithStyle::reset_table_box_computed_values_used_by_wrapper_to_init_values() { VERIFY(this->display().is_table_inside()); diff --git a/Libraries/LibWeb/Layout/Node.h b/Libraries/LibWeb/Layout/Node.h index 118feec5a59..fcb87cd09a9 100644 --- a/Libraries/LibWeb/Layout/Node.h +++ b/Libraries/LibWeb/Layout/Node.h @@ -191,6 +191,9 @@ public: // https://drafts.csswg.org/css-ui/#propdef-user-select CSS::UserSelect user_select_used_value() const; + [[nodiscard]] bool has_been_wrapped_in_table_wrapper() const { return m_has_been_wrapped_in_table_wrapper; } + void set_has_been_wrapped_in_table_wrapper(bool value) { m_has_been_wrapped_in_table_wrapper = value; } + protected: Node(DOM::Document&, DOM::Node*); @@ -211,6 +214,8 @@ private: bool m_is_flex_item { false }; bool m_is_grid_item { false }; + bool m_has_been_wrapped_in_table_wrapper { false }; + GeneratedFor m_generated_for { GeneratedFor::NotGenerated }; u32 m_initial_quote_nesting_level { 0 }; @@ -240,6 +245,8 @@ public: virtual void visit_edges(Cell::Visitor& visitor) override; + void set_computed_values(NonnullOwnPtr); + protected: NodeWithStyle(DOM::Document&, DOM::Node*, GC::Ref); NodeWithStyle(DOM::Document&, DOM::Node*, NonnullOwnPtr); diff --git a/Libraries/LibWeb/Layout/TreeBuilder.cpp b/Libraries/LibWeb/Layout/TreeBuilder.cpp index 1b30cd09cb2..83436ca3926 100644 --- a/Libraries/LibWeb/Layout/TreeBuilder.cpp +++ b/Libraries/LibWeb/Layout/TreeBuilder.cpp @@ -784,6 +784,11 @@ Vector> TreeBuilder::generate_missing_parents(NodeWithStyle& root) // An anonymous table-wrapper box must be generated around each table-root. if (parent.display().is_table_inside()) { + if (parent.has_been_wrapped_in_table_wrapper()) { + VERIFY(parent.parent()); + VERIFY(parent.parent()->is_table_wrapper()); + return TraversalDecision::Continue; + } table_roots_to_wrap.append(parent); } @@ -797,6 +802,12 @@ Vector> TreeBuilder::generate_missing_parents(NodeWithStyle& root) auto wrapper_computed_values = table_box->computed_values().clone_inherited_values(); table_box->transfer_table_box_computed_values_to_wrapper_computed_values(*wrapper_computed_values); + if (parent.is_table_wrapper()) { + auto& existing_wrapper = static_cast(parent); + existing_wrapper.set_computed_values(move(wrapper_computed_values)); + continue; + } + auto wrapper = parent.heap().allocate(parent.document(), nullptr, move(wrapper_computed_values)); parent.remove_child(*table_box); @@ -806,6 +817,8 @@ Vector> TreeBuilder::generate_missing_parents(NodeWithStyle& root) parent.insert_before(*wrapper, *nearest_sibling); else parent.append_child(*wrapper); + + table_box->set_has_been_wrapped_in_table_wrapper(true); } return table_roots_to_wrap;