mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 14:47:44 +00:00
LibWeb: Invalidate less style when moving between hovered nodes
Instead of invalidating style for the entire document, we now locate the nearest common ancestor between the old and new innermost hovered node, and only invalidate that ancestor and its descendants. This drastically reduces the amount of style update work when mousing around on GitHub (and any other pages, really.) It's actually really really snappy now. Very cool! :^)
This commit is contained in:
parent
f1711a562a
commit
0e8b538e0a
1 changed files with 24 additions and 1 deletions
|
@ -672,6 +672,26 @@ void Document::set_inspected_node(Node* node)
|
|||
m_inspected_node->layout_node()->set_needs_display();
|
||||
}
|
||||
|
||||
static Node* find_common_ancestor(Node* a, Node* b)
|
||||
{
|
||||
if (!a || !b)
|
||||
return nullptr;
|
||||
|
||||
if (a == b)
|
||||
return a;
|
||||
|
||||
HashTable<Node*> ancestors;
|
||||
for (auto* node = a; node; node = node->parent_or_shadow_host())
|
||||
ancestors.set(node);
|
||||
|
||||
for (auto* node = b; node; node = node->parent_or_shadow_host()) {
|
||||
if (ancestors.contains(node))
|
||||
return node;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void Document::set_hovered_node(Node* node)
|
||||
{
|
||||
if (m_hovered_node == node)
|
||||
|
@ -680,7 +700,10 @@ void Document::set_hovered_node(Node* node)
|
|||
RefPtr<Node> old_hovered_node = move(m_hovered_node);
|
||||
m_hovered_node = node;
|
||||
|
||||
invalidate_style();
|
||||
if (auto* common_ancestor = find_common_ancestor(old_hovered_node, m_hovered_node))
|
||||
common_ancestor->invalidate_style();
|
||||
else
|
||||
invalidate_style();
|
||||
}
|
||||
|
||||
NonnullRefPtr<HTMLCollection> Document::get_elements_by_name(String const& name)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue