From bf34b6343972be61573d81829103bb697bc9ea41 Mon Sep 17 00:00:00 2001 From: Luke Wilde Date: Thu, 30 Jan 2025 14:32:24 +0000 Subject: [PATCH] LibWeb: Don't compare the focus chain's GC::Root contents by reference The focus chain always consists of newly created GC::Root objects, so the condition always produced `false`. The fix is to use GC::Root's overloaded operator== method, which compares the pointers of the stored type. This fixes Figma dropdowns and context menus instantly disappearing upon opening them. This is because they become focused when they insert them. Because of this bug, it would fire blur events all the way up to and including the window. Figma listens for the blur event on the window, and when received, it will instantly hide dropdowns and context menus. The intention behind this seems to be hiding them when the user clicks off the browser window, or switches tab. --- Libraries/LibWeb/HTML/Focus.cpp | 2 +- Tests/LibWeb/Text/expected/focus-chain.txt | 30 ++++++++++ .../dom/events/shadow-relatedTarget.txt | 6 +- Tests/LibWeb/Text/input/focus-chain.html | 55 +++++++++++++++++++ 4 files changed, 89 insertions(+), 4 deletions(-) create mode 100644 Tests/LibWeb/Text/expected/focus-chain.txt create mode 100644 Tests/LibWeb/Text/input/focus-chain.html diff --git a/Libraries/LibWeb/HTML/Focus.cpp b/Libraries/LibWeb/HTML/Focus.cpp index 0fbc17e696..d55645a217 100644 --- a/Libraries/LibWeb/HTML/Focus.cpp +++ b/Libraries/LibWeb/HTML/Focus.cpp @@ -44,7 +44,7 @@ static void run_focus_update_steps(Vector> old_chain, Vector // pop the last entry from old chain and the last entry from new chain and redo this step. while (!old_chain.is_empty() && !new_chain.is_empty() - && &old_chain.last() == &new_chain.last()) { + && old_chain.last() == new_chain.last()) { (void)old_chain.take_last(); (void)new_chain.take_last(); } diff --git a/Tests/LibWeb/Text/expected/focus-chain.txt b/Tests/LibWeb/Text/expected/focus-chain.txt new file mode 100644 index 0000000000..d8b0cedbf0 --- /dev/null +++ b/Tests/LibWeb/Text/expected/focus-chain.txt @@ -0,0 +1,30 @@ +== div3 focus +DIV#3 received focus event, target: DIV#3, currentTarget: DIV#3 +DIV#3 received focusin event, target: DIV#3, currentTarget: DIV#3 +DIV#2 received focusin event, target: DIV#3, currentTarget: DIV#2 +DIV#1 received focusin event, target: DIV#3, currentTarget: DIV#1 +window received focusin event, target: DIV#3, currentTarget: window +== div5 focus +DIV#3 received blur event, target: DIV#3, currentTarget: DIV#3 +DIV#3 received focusout event, target: DIV#3, currentTarget: DIV#3 +DIV#2 received focusout event, target: DIV#3, currentTarget: DIV#2 +DIV#1 received focusout event, target: DIV#3, currentTarget: DIV#1 +window received focusout event, target: DIV#3, currentTarget: window +DIV#5 received focus event, target: DIV#5, currentTarget: DIV#5 +DIV#5 received focusin event, target: DIV#5, currentTarget: DIV#5 +DIV#4 received focusin event, target: DIV#5, currentTarget: DIV#4 +DIV#1 received focusin event, target: DIV#5, currentTarget: DIV#1 +window received focusin event, target: DIV#5, currentTarget: window +== div1 focus +DIV#5 received blur event, target: DIV#5, currentTarget: DIV#5 +DIV#5 received focusout event, target: DIV#5, currentTarget: DIV#5 +DIV#4 received focusout event, target: DIV#5, currentTarget: DIV#4 +DIV#1 received focusout event, target: DIV#5, currentTarget: DIV#1 +window received focusout event, target: DIV#5, currentTarget: window +DIV#1 received focus event, target: DIV#1, currentTarget: DIV#1 +DIV#1 received focusin event, target: DIV#1, currentTarget: DIV#1 +window received focusin event, target: DIV#1, currentTarget: window +== window focus +DIV#1 received blur event, target: DIV#1, currentTarget: DIV#1 +DIV#1 received focusout event, target: DIV#1, currentTarget: DIV#1 +window received focusout event, target: DIV#1, currentTarget: window diff --git a/Tests/LibWeb/Text/expected/wpt-import/dom/events/shadow-relatedTarget.txt b/Tests/LibWeb/Text/expected/wpt-import/dom/events/shadow-relatedTarget.txt index 40cea574ad..bb871948af 100644 --- a/Tests/LibWeb/Text/expected/wpt-import/dom/events/shadow-relatedTarget.txt +++ b/Tests/LibWeb/Text/expected/wpt-import/dom/events/shadow-relatedTarget.txt @@ -2,6 +2,6 @@ Harness status: OK Found 2 tests -2 Fail -Fail relatedTarget should not leak at capturing phase, at window object. -Fail relatedTarget should not leak at target. \ No newline at end of file +2 Pass +Pass relatedTarget should not leak at capturing phase, at window object. +Pass relatedTarget should not leak at target. \ No newline at end of file diff --git a/Tests/LibWeb/Text/input/focus-chain.html b/Tests/LibWeb/Text/input/focus-chain.html new file mode 100644 index 0000000000..8120aff51c --- /dev/null +++ b/Tests/LibWeb/Text/input/focus-chain.html @@ -0,0 +1,55 @@ + +
+
+
+
+
+
+
+
+ +