diff options
author | Andreas Kling <kling@serenityos.org> | 2022-03-21 10:56:02 +0100 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2022-03-21 13:03:33 +0100 |
commit | 59afdb959ff20ac8516ceb180c68084997538b70 (patch) | |
tree | 6a336f0ec448a24f114bdc9d42e681ae42a801e1 /Userland/Libraries/LibWeb/Painting/PaintableBox.cpp | |
parent | 89086c337cd249436a5a77340a9c2e2f8b5bd6dc (diff) | |
download | serenity-59afdb959ff20ac8516ceb180c68084997538b70.zip |
LibWeb: Build stacking context tree lazily
There's no actual need to build the stacking context tree before
performing layout. Instead, make it lazy and build the tree when it's
actually needed for something.
This avoids a bunch of work in situations where multiple synchronous
layouts are forced (typically by JavaScript) without painting or hit
testing taking place in between.
It also opens up for style invalidations that only target the stacking
context tree.
Diffstat (limited to 'Userland/Libraries/LibWeb/Painting/PaintableBox.cpp')
-rw-r--r-- | Userland/Libraries/LibWeb/Painting/PaintableBox.cpp | 10 |
1 files changed, 9 insertions, 1 deletions
diff --git a/Userland/Libraries/LibWeb/Painting/PaintableBox.cpp b/Userland/Libraries/LibWeb/Painting/PaintableBox.cpp index 2cdfbbbf22..670aae965f 100644 --- a/Userland/Libraries/LibWeb/Painting/PaintableBox.cpp +++ b/Userland/Libraries/LibWeb/Painting/PaintableBox.cpp @@ -7,6 +7,7 @@ #include <LibWeb/DOM/Document.h> #include <LibWeb/HTML/HTMLHtmlElement.h> #include <LibWeb/Layout/BlockContainer.h> +#include <LibWeb/Layout/InitialContainingBlock.h> #include <LibWeb/Painting/BackgroundPainting.h> #include <LibWeb/Painting/PaintableBox.h> #include <LibWeb/Painting/ShadowPainting.h> @@ -28,6 +29,11 @@ PaintableBox::~PaintableBox() { } +void PaintableBox::invalidate_stacking_context() +{ + m_stacking_context = nullptr; +} + PaintableWithLines::PaintableWithLines(Layout::BlockContainer const& layout_box) : PaintableBox(layout_box) { @@ -524,8 +530,10 @@ void PaintableBox::for_each_child_in_paint_order(Callback callback) const HitTestResult PaintableBox::hit_test(Gfx::FloatPoint const& position, HitTestType type) const { - if (layout_box().is_initial_containing_block_box()) + if (layout_box().is_initial_containing_block_box()) { + const_cast<Layout::InitialContainingBlock&>(static_cast<Layout::InitialContainingBlock const&>(layout_box())).build_stacking_context_tree_if_needed(); return stacking_context()->hit_test(position, type); + } HitTestResult result { absolute_border_box_rect().contains(position.x(), position.y()) ? this : nullptr }; for_each_child_in_paint_order([&](auto& child) { |