aria-description crash course
The other day I was skimming Webkit’s Safari Technology Preview 153 release notes and noticed that they had added support for
I always found it odd that developers could set an element’s accessible name/label with the
aria-labelledby attributes, but only had
aria-describedby for setting accessible descriptions. So seeing
aria-description being added to Safari was an interesting surprise.
I decided to do a mini dive and test of support for
aria-description to fill in my knowledge gap and be prepared to use it when the time comes. A sort of crash-course, if you will. I’m sharing my findings here in case it’s valuable for anyone else.
Current status #
aria-description property is part of the Accessible Rich Internet Applications 1.3 draft specification. This ARIA GitHub issue provides a bit more context on how it was added. Even though ARIA 1.3 is still in the draft stage, some browsers began adding
aria-description support back in 2021.
Glancing at the support table on a11ysupport.io, Chrome, Edge, and Firefox currently appear to have good support for it.
So once this feature moves from Safari’s beta to the public release, it will have support in the four major browsers.
Accessible descriptions #
Why they’re important #
When sighted users see a control on a web page, they can scan its text and anything near it to understand it. In contrast, non-sighted and visually-impaired users rely on screen readers that step through a page’s elements one-by-one and announce them. These screen readers lean on the accessible name and description to give users valuable information about an element.
For interactive items, accessible names convey to these users what exactly it is. Without a name the control is effectively useless to them, so it should be concise and to-the-point – ex: a button labeled "login", "submit", or "help".
But sometimes there’s supplementary content, instructions, or details that, while not as important as the item’s name, are still helpful for the user to use or understand a control. This complementary information, which can be longer and more verbose, is the accessible description – ex: "the tracking # is the 12-digit number that begins with 'Z'" or "passwords must be at least 8 characters".
Sure, screen reader users might manually find this information like they would anything else. But it’s also possible they miss it by jumping directly to an interactive element. So when we can programmatically associate this helpful info as an accessible description of an item we provide coverage for those situations.
In the image above, if the secondary content is set as an accessible description of the interactive elements then screen readers would announce something like “Password, edit box, must be at least 8 characters long” and “Settings, button, opens a modal” when encountering those elements.
Without the accessible description present the announcements would simply be “Password, edit box” and “Settings, button”, leaving out helpful details.
All interactive elements should have an accessible name, which in
most cases is the item’s text value. If desired, developers can override
that with the
aria-label directly sets a text string as the element's new name, while
aria-labelledby points to the
id of a separate element(s) whose text will become the element's name.
aria-label and aria-labelledby examplehtml
<button aria-label="Edit Settings">Settings</button> <button aria-labelledby="buttonName">Settings</button> <p hidden id="buttonName">Edit Settings</p>
On the accessible description side, developers most-commonly use the
aria-describedby attribute to give an element an accessible description.
aria-describedby works similar to
aria-labelledby, in that it accepts an
id of an element located elsewhere on the page whose text describes the element.
<button aria-describedby="buttonDesc">Settings</button> <p id="buttonDesc">(Opens a modal)</p>
Here, the description is visually next to the button, so sighted users will see it before clicking. That we can create that same association for screen reader users means we’re creating an equal experience.
Developers also frequently hide elements visually in attempts to provide certain information only to screen readers. An extension of the previous technique, it requires keeping that additional page element and applying the
hidden attribute, hiding it with CSS, or adding a “visually hidden” class:
aria-describedby with visually hidden element examplehtml
<button aria-describedby="buttonDesc">Settings</button> <p hidden id="buttonDesc">Opens a modal</p> <!-- or --> <p style="display: none;" id="buttonDesc">Opens a modal</p> <!-- or --> <p class="visuallyHidden" id="buttonDesc">Opens a modal</p>
Whether this is a good practice or not is outside the scope of this blog post, but nevertheless it is common.
But using the new
aria-description now gives authors an option similar to
aria-label which allows them to directly set accessible descriptions without the need for a second element, an option that was missing before.
<button aria-description="Opens a modal">Settings</button>
This is a much cleaner and maintainable approach than using the
aria-describedby property with a hidden node.
If you’re at all curious how browsers determine an item’s name or description, you can check out the Accessible Name and Description Computation specification. Note that this does not reference
aria-description yet as it is not formally standardized.
Translation concerns #
One drawback of using attributes like
aria-label) that contain text content is that they aren’t consistently converted by translation tools. So screen reader users who browse the web in another language may encounter a barrier when hearing an announcement that they don’t understand.
Adrian Roselli’s article aria-label Does Not Translate dives into this issue with the
aria-label property, which has been around longer with better support. He finds that translation for that is spotty at best. So this is likely to be as much, if not more, of an issue with
I did my own quick test using Google Translate on a page featuring an element with both an
Translation markup beforehtml
<button aria-label="Settings" aria-description="Opens a modal">Settings</button>
Translating the page from English to Portuguese resulted in the following markup:
Translation markup afterhtml
<button aria-label="Definições" aria-description="Opens a modal">Definições</button>
In this case, the
aria-label property did get translated while the
aria-description did not, which is a problem. We can assume that other translation tools will have at least this same issue.
As a solution, Adrian recommends in his article to use an element’s default text or the
aria-labelledby attribute for accessible naming. So for accessible descriptions we’d want to use
aria-describedby to point to other page elements that do get translated.
Browsers and screen readers #
I tested the four major desktop browsers (Chrome, Edge, Firefox, Safari) with a screen reader that it is commonly paired with. Note that I’m testing with Safari Technology Preview 153, the beta release that just added
- JAWS (2021.2111.13) + Chrome (105) on Windows 10
- NVDA (2022.2.2) + Firefox (103) on Windows 10
- Narrator (2020) + Edge (105) on Windows 10
- VoiceOver + Safari Technology Preview 153 (16.0) on MacOS 12.5.1
On desktop, I navigated to the test elements in two ways: 1) with the screen reader’s virtual cursor (arrow keys); and 2) with the
For mobile testing, I used two environments. Note that I'm using Safari in the iOS 16 beta.
- TalkBack (13.1.02) + Chrome (105) on Android 11, Samsung Galaxy A20s
- VoiceOver + Safari on iOS 16 beta, iPhone 13
On the mobile devices, I navigated the page using horizontal swipes to move the virtual cursor.
For more background on why I chose these combinations, see the “Testing scope” section of my article Screen readers and drag-and-drop, part 1.
I tested a
button element with the text “Settings”. For easy comparisons, I tested both the
Markup used for browser testinghtml
<!-- version A --> <button aria-description="Opens a modal">Settings</button> <!-- version B --> <button aria-describedby="buttonDesc">Settings</button> <p id="buttonDesc">Opens a modal</p>
Let’s take a look at the support for accessible descriptions.
|Browser / screen reader||
|JAWS + Chrome||“Settings button”||"Settings button opens a modal"||"Settings button"||"Settings button opens a modal"|
|NVDA + Firefox||"Button opens a modal settings"||"Settings button opens a modal"||"Button settings"||"Settings button opens a modal"|
|Narrator + Edge||"Button opens a modal settings"||"Settings button opens a modal"||"Button opens a modal settings"||"Settings button opens a modal"|
|VoiceOver + Safari||“Settings button [pause] more content available”||“Settings button [pause] more content available”||“Settings button [pause] opens a modal”||“Settings button [pause] opens a modal”|
|TalkBack + Android Chrome||"Settings button opens a modal"||N/A||"Settings button opens a modal"||N/A|
|VoiceOver + iOS Safari||"Settings button"||N/A||"Settings button opens a modal"||N/A|
The desktop browsers had mixed support for
JAWS + Chrome supported it only when navigating with the
tab key. The pairing didn’t announce any accessible description with the virtual cursor.
NVDA + Firefox did announce
aria-description with both the virtual cursor and
tab key, which it oddly did not do for
Narrator + Edge supported both properties in both navigation methods.
The big quirk though is with Mac’s VoiceOver + Safari. While it did recognize that an accessible description was present with
aria-description, it did not announce the content as it did for
aria-describedby. It instead announced “more content available” followed by instructions to use the shortcut “VO + CMD + / (slash)” to access it.
When the shortcut is used, a VoiceOver menu opens listing all “additional content”, where you then need to arrow down to the description to hear it. That’s a pretty laborious process.
I mentioned earlier that unlike an accessible name, an accessible description can be more verbose. I wonder if this is VoiceOver’s way to mitigate the possibility of longform descriptive content.
On mobile, TalkBack + Android Chrome had support for
aria-description where VoiceOver + iOS Safari did not.
Though I tested on Safari 16’s beta as I did with desktop, the
aria-description property was not supported. It’s possible that version of WebKit hadn’t yet been incorporated into iOS’s beta yet, so I’ll continue to monitor it and update as needed.
aria-description is a nice addition to the ARIA suite of properties that will come in handy for those times where you absolutely must provide information only to screen reader users. It’s less markup and much simpler than the current method of referencing hidden elements with
However, it’s not ready for production yet. There doesn’t appear to be any translation support currently in the largest online translation tool, a problem in our diverse world.
It also doesn’t have full support across the most popular browser and screen reader pairings – and this was with the nearly latest releases. If you go back even a handful of versions I imagine the support gets weaker and weaker. Many users do not upgrade their devices and software on a regular basis, so we can’t shut them out.
I’m glad I dove into this attribute and look forward to adding it to my toolbox in the future when it’s more widely supported.
Update – 09/12/2022 #
The same day I published this article, Apple released Safari 16 to the public. I just downloaded the public release for both MacOS and iOS and both do not have support for
aria-description. So I'd assume that since there was support in the Safari desktop beta that it will be added in a Safari update in the next month or two.