Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

JAWS on Chromium-based browsers ignores empty DOM nodes with aria-label #759

Closed
yjbanov opened this issue Sep 15, 2023 · 9 comments
Closed

Comments

@yjbanov
Copy link

yjbanov commented Sep 15, 2023

Summary

JAWS completely ignores empty DOM nodes with aria-label on them. The accessibility focus ring cannot reach those nodes using navigation, hence the text of the label is never announced.

NVDA on Windows, VoiceOver on macOS and iOS, and TalkBack on Android support such DOM structure. Narrator on Windows seems to have the same issue as JAWS.

Expected result

The screen reader should be able to focus on the <div> element (according to the traversal order of the DOM tree) and read its label.

Actual result

There is no way to reach the node using navigation shortcuts. It's as if the element is not there at all.

Example

<div role="text" aria-label="Hello"></div>

Additional Information

A workaround is to insert an artificial child and move the label to it, for example:

<div role="text">
  <span aria-label="Hello"></span>
</div>

Issue #405 may have the same underlying cause.

Why is this important?

This use-case is important for content that's rendered into WebGL (or any other canvas). In this mode, there are no DOM nodes with text content. Instead you only have absolutely positioned nodes annotated with whatever is rendered inside the canvas. Additionally, the developer typically does not own the a11y DOM structure. Instead the developer uses a WebGL framework, and it's the framework that outputs the accessibility DOM tree. So the developer is unable to apply the workaround.

JAWS version and build number

2022.2112.24 ILM

Operating System and version

Windows 11 Home 22H2 22621.1992

Browser and version:

Chrome 116.0.5845.188
Edge 116.0.1938.81

@JAWS-test
Copy link

div has the ARIA role generic: https://www.w3.org/TR/html-aam-1.0/#el-div

the role generic has Name From: prohibited https://w3c.github.io/aria/#generic

So JAWS is not making a mistake here, but your code is wrong. Freedom Scientific must decide whether incorrect code should be output by JAWS as you wish.

@JAWS-test
Copy link

JAWS-test commented Sep 17, 2023

by the way, this also applies to your workaround, since span may not be labelled with an aria-label either.

@yjbanov
Copy link
Author

yjbanov commented Sep 18, 2023

The problem happens with non-div elements too. In particular, we use our own custom <flt-semantics> element in Flutter. To give it a role we use role="text". Unfortunately, that's not a standard ARIA role. Only WebKit implements it in a meaningful way. Other browsers probably fallback to "generic" (which is what you are observing). Since there's no other ARIA role (that I'm aware of) that describes text, I think "generic" + aria-label is the best option today. Alternatives seem worse, such as using incorrect roles ("group", "heading", etc).

Despite the HTML spec treating "generic" + aria-label as a "prohibited" combination, since the spec doesn't provide an alternative, I think it's in the benefit of both the developer and the user to support this combination in practice, until the HTML spec matures enough to support this use-case. Screen readers on all mainstream non-Windows platforms support it, and so does NVDA on Windows. I don't think JAWS would be criticized for interpreting this combination the same way.

@stevefaulkner
Copy link
Contributor

stevefaulkner commented Dec 7, 2023

triage actions

  • test in 2024
  • look into annotations e.g. aria-description
  • review minimum viable role proposal

@stevefaulkner
Copy link
Contributor

@yjbanov do you have a demo that I can test?

@yjbanov
Copy link
Author

yjbanov commented Dec 15, 2023

Here's a demo: https://jaws-issue-759.web.app/

@stevefaulkner
Copy link
Contributor

@yjbanov thanks for the demo

Only WebKit implements it in a meaningful way. Other browsers probably fallback to "generic" (which is what you are observing). Since there's no other ARIA role (that I'm aware of) that describes text, I think "generic" + aria-label is the best option today. Alternatives seem worse, such as using incorrect roles ("group", "heading", etc).

webkit is removing support for role=text

Given that generic roles must not (in spec terms) expose the accessible name, it is not a good idea for JAWS to support it.

I have found a work around that obviates the need for a role or any other ARIA. It uses CSS text. I have tested in JAWS/NVDA in Chrome and Firefox, also VoiceOver/chrome on iOS and Talkback/chrome on Android. All announce the text "Hello"

test case

why does it work? i think because CSS is rendered as a text node in the DOM.

@yjbanov
Copy link
Author

yjbanov commented Feb 20, 2024

I understand regarding role="text". I'll take it up with the browsers to adopt it. However, even without this role, JAWS behavior is broken compared to all other screen readers. Without the text role, all screen readers except JAWS will do the following:

  • Allow the user to focus on the element.
  • Read the label.
  • (In some cases) Will add "empty group".

While "empty group" is an unnecessary and annoying addition, the user can still find and be able to interact with the element. JAWS will skip it as if it's not there.

@yjbanov
Copy link
Author

yjbanov commented Feb 21, 2024

I confirmed today on Safari 17.3.1 on macOS. Safari did remove support for role="text". However, VoiceOver does not ignore or skip over the element containing aria-label. So I think the issue is still valid. Please, reconsider.

auto-submit bot pushed a commit to flutter/engine that referenced this issue Mar 13, 2024
On Windows, where JAWS is a popular screen reader and, [unfortunately](FreedomScientific/standards-support#759), ignores `aria-label` on empty elements, and for user agents that are known web crawlers (that also ignore `aria-label`), render semantic text into the DOM using an additional `<span>` element.

Fixes flutter/flutter#122607
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants