diff --git a/dom/base/FragmentOrElement.cpp b/dom/base/FragmentOrElement.cpp index dc4e43064a9b..e5a49ad5dbec 100644 --- a/dom/base/FragmentOrElement.cpp +++ b/dom/base/FragmentOrElement.cpp @@ -1036,9 +1036,14 @@ Element* nsIContent::GetFocusDelegate(bool aWithMouse, whereToLook = root; } - auto IsFocusable = [&](Element* aElement) { + auto IsFocusable = [&](Element* aElement) -> nsIFrame::Focusable { nsIFrame* frame = aElement->GetPrimaryFrame(); - return frame && frame->IsFocusable(aWithMouse); + + if (!frame) { + return {}; + } + + return frame->IsFocusable(aWithMouse); }; Element* potentialFocus = nullptr; @@ -1059,10 +1064,20 @@ Element* nsIContent::GetFocusDelegate(bool aWithMouse, // Found an autofocus candidate. return el; } - } else if (!potentialFocus && IsFocusable(el)) { - // This element could be the one if we can't find an - // autofocus candidate which has the precedence. - potentialFocus = el; + } else if (!potentialFocus) { + if (nsIFrame::Focusable focusable = IsFocusable(el)) { + if (IsHTMLElement(nsGkAtoms::dialog)) { + if (focusable.mTabIndex >= 0) { + // If focusTarget is a dialog element and descendant is sequentially + // focusable, then set focusableArea to descendant. + potentialFocus = el; + } + } else { + // This element could be the one if we can't find an + // autofocus candidate which has the precedence. + potentialFocus = el; + } + } } if (!autofocus && potentialFocus) { diff --git a/dom/html/HTMLDialogElement.cpp b/dom/html/HTMLDialogElement.cpp index 91ee4a9fcf4e..260d168849ff 100644 --- a/dom/html/HTMLDialogElement.cpp +++ b/dom/html/HTMLDialogElement.cpp @@ -140,7 +140,9 @@ void HTMLDialogElement::FocusDialog() { doc->FlushPendingNotifications(FlushType::Frames); } - RefPtr control = GetFocusDelegate(false /* aWithMouse */); + RefPtr control = HasAttr(nsGkAtoms::autofocus) + ? this + : GetFocusDelegate(false /* aWithMouse */); // If there isn't one of those either, then let control be subject. if (!control) { @@ -150,6 +152,8 @@ void HTMLDialogElement::FocusDialog() { FocusCandidate(*control, IsInTopLayer()); } +int32_t HTMLDialogElement::TabIndexDefault() { return 0; } + void HTMLDialogElement::QueueCancelDialog() { // queues an element task on the user interaction task source OwnerDoc() diff --git a/dom/html/HTMLDialogElement.h b/dom/html/HTMLDialogElement.h index 51ffee959f31..6d759ede4ad1 100644 --- a/dom/html/HTMLDialogElement.h +++ b/dom/html/HTMLDialogElement.h @@ -47,6 +47,8 @@ class HTMLDialogElement final : public nsGenericHTMLElement { MOZ_CAN_RUN_SCRIPT_BOUNDARY void FocusDialog(); + int32_t TabIndexDefault() override; + nsString mReturnValue; protected: diff --git a/testing/web-platform/meta/css/css-contain/content-visibility/content-visibility-with-top-layer-006.html.ini b/testing/web-platform/meta/css/css-contain/content-visibility/content-visibility-with-top-layer-006.html.ini deleted file mode 100644 index 8f34edcd100b..000000000000 --- a/testing/web-platform/meta/css/css-contain/content-visibility/content-visibility-with-top-layer-006.html.ini +++ /dev/null @@ -1,5 +0,0 @@ -[content-visibility-with-top-layer-006.html] - expected: - if (os == "android") and fission: [OK, TIMEOUT] - [CSS Content Visibility: offscreen c-v auto content is relevant when in top layer] - expected: FAIL diff --git a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/child-sequential-focus.html.ini b/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/child-sequential-focus.html.ini deleted file mode 100644 index 6f8c4561a74d..000000000000 --- a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/child-sequential-focus.html.ini +++ /dev/null @@ -1,12 +0,0 @@ -[child-sequential-focus.html] - [dialog element with autofocus should get initial focus.] - expected: FAIL - - [Only keyboard-focusable elements should get dialog initial focus.] - expected: FAIL - - [Only keyboard-focusable elements should get dialog initial focus including in subtrees.] - expected: FAIL - - [Only keyboard-focusable elements should get dialog initial focus including in nested buttons.] - expected: FAIL diff --git a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-focus-shadow.html.ini b/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-focus-shadow.html.ini deleted file mode 100644 index 863e564527a6..000000000000 --- a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-focus-shadow.html.ini +++ /dev/null @@ -1,20 +0,0 @@ -[dialog-focus-shadow.html] - expected: - if (os == "android") and fission: [OK, TIMEOUT] - [show: No autofocus, no delegatesFocus, no siblings] - expected: FAIL - - [showModal: No autofocus, no delegatesFocus, no siblings] - expected: FAIL - - [show: Autofocus on shadow host, no delegatesFocus, no siblings] - expected: FAIL - - [showModal: Autofocus on shadow host, no delegatesFocus, no siblings] - expected: FAIL - - [show: Autofocus inside shadow tree, no delegatesFocus, no siblings] - expected: FAIL - - [showModal: Autofocus inside shadow tree, no delegatesFocus, no siblings] - expected: FAIL diff --git a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-showModal.html.ini b/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-showModal.html.ini deleted file mode 100644 index c7357edd2498..000000000000 --- a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/dialog-showModal.html.ini +++ /dev/null @@ -1,5 +0,0 @@ -[dialog-showModal.html] - expected: - if (os == "android") and fission: [OK, TIMEOUT] - [opening dialog without focusable children] - expected: FAIL diff --git a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/show-modal-focusing-steps.html.ini b/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/show-modal-focusing-steps.html.ini deleted file mode 100644 index f0d673d2c214..000000000000 --- a/testing/web-platform/meta/html/semantics/interactive-elements/the-dialog-element/show-modal-focusing-steps.html.ini +++ /dev/null @@ -1,5 +0,0 @@ -[show-modal-focusing-steps.html] - expected: - if (os == "android") and fission: [OK, TIMEOUT] - [focus when a modal dialog is opened] - expected: FAIL diff --git a/testing/web-platform/tests/html/semantics/interactive-elements/the-dialog-element/modal-dialog-backdrop-opacity.html b/testing/web-platform/tests/html/semantics/interactive-elements/the-dialog-element/modal-dialog-backdrop-opacity.html index d8356c7837e5..09c31ce2af95 100644 --- a/testing/web-platform/tests/html/semantics/interactive-elements/the-dialog-element/modal-dialog-backdrop-opacity.html +++ b/testing/web-platform/tests/html/semantics/interactive-elements/the-dialog-element/modal-dialog-backdrop-opacity.html @@ -7,6 +7,9 @@ dialog::backdrop { background-color: rgb(0, 128, 0); opacity: 0.5; } +dialog:focus { + outline: none; +} Test passes if you see a green backdrop at half opacity.