diff --git a/Tests/LibWeb/Text/expected/focus-events.txt b/Tests/LibWeb/Text/expected/focus-events.txt new file mode 100644 index 0000000000..1fddba0e4c --- /dev/null +++ b/Tests/LibWeb/Text/expected/focus-events.txt @@ -0,0 +1,6 @@ + focus target= +focusin target= +blur target= +focusout target= +focus target= +focusin target= diff --git a/Tests/LibWeb/Text/input/focus-events.html b/Tests/LibWeb/Text/input/focus-events.html new file mode 100644 index 0000000000..bfe053e870 --- /dev/null +++ b/Tests/LibWeb/Text/input/focus-events.html @@ -0,0 +1,54 @@ + + + + + diff --git a/Userland/Libraries/LibWeb/DOM/EventHandler.idl b/Userland/Libraries/LibWeb/DOM/EventHandler.idl index afdc2d0082..bbdf381925 100644 --- a/Userland/Libraries/LibWeb/DOM/EventHandler.idl +++ b/Userland/Libraries/LibWeb/DOM/EventHandler.idl @@ -41,6 +41,8 @@ interface mixin GlobalEventHandlers { attribute EventHandler onended; attribute OnErrorEventHandler onerror; attribute EventHandler onfocus; + attribute EventHandler onfocusin; + attribute EventHandler onfocusout; attribute EventHandler onformdata; attribute EventHandler oninput; attribute EventHandler oninvalid; diff --git a/Userland/Libraries/LibWeb/HTML/AttributeNames.h b/Userland/Libraries/LibWeb/HTML/AttributeNames.h index d26321d555..6bee2a2248 100644 --- a/Userland/Libraries/LibWeb/HTML/AttributeNames.h +++ b/Userland/Libraries/LibWeb/HTML/AttributeNames.h @@ -141,6 +141,8 @@ namespace AttributeNames { __ENUMERATE_HTML_ATTRIBUTE(onended) \ __ENUMERATE_HTML_ATTRIBUTE(onerror) \ __ENUMERATE_HTML_ATTRIBUTE(onfocus) \ + __ENUMERATE_HTML_ATTRIBUTE(onfocusin) \ + __ENUMERATE_HTML_ATTRIBUTE(onfocusout) \ __ENUMERATE_HTML_ATTRIBUTE(onformdata) \ __ENUMERATE_HTML_ATTRIBUTE(onhashchange) \ __ENUMERATE_HTML_ATTRIBUTE(oninput) \ diff --git a/Userland/Libraries/LibWeb/HTML/EventNames.h b/Userland/Libraries/LibWeb/HTML/EventNames.h index bd162483e6..731d22470f 100644 --- a/Userland/Libraries/LibWeb/HTML/EventNames.h +++ b/Userland/Libraries/LibWeb/HTML/EventNames.h @@ -51,6 +51,8 @@ namespace Web::HTML::EventNames { __ENUMERATE_HTML_EVENT(error) \ __ENUMERATE_HTML_EVENT(finish) \ __ENUMERATE_HTML_EVENT(focus) \ + __ENUMERATE_HTML_EVENT(focusin) \ + __ENUMERATE_HTML_EVENT(focusout) \ __ENUMERATE_HTML_EVENT(formdata) \ __ENUMERATE_HTML_EVENT(hashchange) \ __ENUMERATE_HTML_EVENT(input) \ diff --git a/Userland/Libraries/LibWeb/HTML/Focus.cpp b/Userland/Libraries/LibWeb/HTML/Focus.cpp index 12e1d7ef09..7fc25b38d8 100644 --- a/Userland/Libraries/LibWeb/HTML/Focus.cpp +++ b/Userland/Libraries/LibWeb/HTML/Focus.cpp @@ -79,6 +79,11 @@ static void run_focus_update_steps(Vector> old_chain, Vect blur_event->set_related_target(related_blur_target); blur_event_target->dispatch_event(blur_event); } + + auto focusout_event = UIEvents::FocusEvent::create(blur_event_target->realm(), HTML::EventNames::focusout); + focusout_event->set_bubbles(true); + focusout_event->set_related_target(related_blur_target); + blur_event_target->dispatch_event(focusout_event); } // FIXME: 3. Apply any relevant platform-specific conventions for focusing new focus target. @@ -123,6 +128,11 @@ static void run_focus_update_steps(Vector> old_chain, Vect auto focus_event = UIEvents::FocusEvent::create(focus_event_target->realm(), HTML::EventNames::focus); focus_event->set_related_target(related_focus_target); focus_event_target->dispatch_event(focus_event); + + auto focusin_event = UIEvents::FocusEvent::create(focus_event_target->realm(), HTML::EventNames::focusin); + focusin_event->set_bubbles(true); + focusin_event->set_related_target(related_focus_target); + focus_event_target->dispatch_event(focusin_event); } } } diff --git a/Userland/Libraries/LibWeb/HTML/GlobalEventHandlers.h b/Userland/Libraries/LibWeb/HTML/GlobalEventHandlers.h index 9206c140fb..79e7d48b8b 100644 --- a/Userland/Libraries/LibWeb/HTML/GlobalEventHandlers.h +++ b/Userland/Libraries/LibWeb/HTML/GlobalEventHandlers.h @@ -34,6 +34,8 @@ E(onended, HTML::EventNames::ended) \ E(onerror, HTML::EventNames::error) \ E(onfocus, HTML::EventNames::focus) \ + E(onfocusin, HTML::EventNames::focusin) \ + E(onfocusout, HTML::EventNames::focusout) \ E(onformdata, HTML::EventNames::formdata) \ E(oninput, HTML::EventNames::input) \ E(oninvalid, HTML::EventNames::invalid) \