LibWeb: Fix aria-label precedence in accessible-name computation

This change makes Ladybird give the value of the aria-label attribute
the correct precedence for accessible-name computation required by the
“Accessible Name and Description Computation” and HTML-AAM specs and by
the corresponding WPT tests.

Otherwise, without this change, Ladybird fails some of the WPT subtests
of the test at https://wpt.fyi/results/accname/name/comp_label.html.
This commit is contained in:
sideshowbarker 2024-11-18 04:20:24 +09:00 committed by Sam Atkins
parent 314e5d6bb7
commit 6bfc35b6a9
Notes: github-actions[bot] 2024-11-29 12:19:25 +00:00
3 changed files with 403 additions and 15 deletions

View file

@ -2288,11 +2288,24 @@ ErrorOr<String> Node::name_or_description(NameOrDescription target, Document con
return element->aria_label().release_value();
return total_accumulated_text.to_string();
}
// C. Embedded Control: Otherwise, if the current node is a control embedded
// within the label (e.g. any element directly referenced by aria-labelledby) for
// another widget, where the user can adjust the embedded control's value, then
// return the embedded control as part of the text alternative in the following
// manner:
// D. AriaLabel: Otherwise, if the current node has an aria-label attribute whose value is not undefined, not
// the empty string, nor, when trimmed of whitespace, is not the empty string:
// AD-HOC: Weve reordered substeps C and D from https://w3c.github.io/accname/#step2 — because
// the more-specific per-HTML-element requirements at https://w3c.github.io/html-aam/#accname-computation
// necessitate doing so, and the “input with label for association is superceded by aria-label” subtest at
// https://wpt.fyi/results/accname/name/comp_label.html wont pass unless we do this reordering.
// Spec PR: https://github.com/w3c/aria/pull/2377
if (target == NameOrDescription::Name && element->aria_label().has_value() && !element->aria_label()->is_empty() && !element->aria_label()->bytes_as_string_view().is_whitespace()) {
// TODO: - If traversal of the current node is due to recursion and the current node is an embedded control as defined in step 2E, ignore aria-label and skip to rule 2E.
// https://github.com/w3c/aria/pull/2385 and https://github.com/w3c/accname/issues/173
if (!element->is_html_slot_element())
return element->aria_label().value();
}
// C. Embedded Control: Otherwise, if the current node is a control embedded within the label (e.g. any element
// directly referenced by aria-labelledby) for another widget, where the user can adjust the embedded control's
// value, then return the embedded control as part of the text alternative in the following manner:
GC::Ptr<DOM::NodeList> labels;
if (is<HTML::HTMLElement>(this))
labels = (const_cast<HTML::HTMLElement&>(static_cast<HTML::HTMLElement const&>(*current_node))).labels();
@ -2372,16 +2385,6 @@ ErrorOr<String> Node::name_or_description(NameOrDescription target, Document con
return builder.to_string();
}
// D. AriaLabel: Otherwise, if the current node has an aria-label attribute whose
// value is not undefined, not the empty string, nor, when trimmed of whitespace,
// is not the empty string:
if (target == NameOrDescription::Name && element->aria_label().has_value() && !element->aria_label()->is_empty() && !element->aria_label()->bytes_as_string_view().is_whitespace()) {
// TODO: - If traversal of the current node is due to recursion and the current node is an embedded control as defined in step 2E, ignore aria-label and skip to rule 2E.
// https://github.com/w3c/aria/pull/2385 and https://github.com/w3c/accname/issues/173
if (!element->is_html_slot_element())
return element->aria_label().value();
}
// E. Host Language Label: Otherwise, if the current node's native markup provides an attribute (e.g. alt) or
// element (e.g. HTML label or SVG title) that defines a text alternative, return that alternative in the form
// of a flat string as defined by the host language, unless the element is marked as presentational