ARIA live regions
Overview – ARIA live regions
Introduced to make dynamic page content accessible to screen readers users, ARIA live regions are regions of a web page that announce dynamic updates to their content when the user’s attention and system focus are elsewhere. Example use cases of live regions include:
- User receives a Facebook/Twitter notification
- Stock ticker price increases
- New chat message is received
- Progress bar updates
- Form validation error occurs
- Shopping cart total updates
- A sport scoring section updates periodically to reflect game statistics
- A visible countdown announces once a minute
- User presses the “next" carousel button to advance a slide (slide content is announced)
- User sorts a table by name, prompting the announcement “Sorted alphabetically by name". In this case, the live text may be visually hidden as sighted users don’t need the notification.
WAI-ARIA provides four attributes that enable the author to
identify live regions and their properties:
aria-live
, aria-relevant
,
aria-atomic
, and aria-busy
. WAI-ARIA
also provides five specialized roles for specific types of live
regions.
aria-live
Identify a live region with an aria-live
attribute on
a container element, such as a <span>
or
<div>
. Browsers and the accessibility API
monitor the container for any script-injected text. As soon as
text is injected into the live region, a screen reader will
announce it.
The live region must be empty on page load or when it’s first added to the DOM. It’s preferable to add the live region on page load, but if adding the live region to the DOM dynamically, it’s best practice to wait at least 2 seconds for the accessibility API to identify it before injecting any text.
The aria-live
attribute takes three possible values:
assertive, polite or off.
- aria-live="assertive"
- An assertive announcement interrupts whatever a screen reader is reading. Only use assertive announcements when the user needs immediate feedback.
- aria-live="polite"
- A polite announcement is delayed until the screen reader finishes its current sentence or until the user pauses typing. Use the polite value most of the time.
- aria-live="off"
- Tells screen readers to temporarily suspend aria-live interruptions.
The WAI-ARIA Carousel Carousel (Slide Show or Image Rotator)
described in module 12 uses aria-live="off"
on the
slide container when advancing slides automatically, and
aria-live="polite"
when the user is manually
advancing the slides. This prevents an automatic slideshow’s
announcements from overwhelming a screen reader user trying to
read the page, and facilitates the reading of a manually-operated
slideshow.
Good example: aria-live attribute
Here, a <div>
element provides a container
for a live region, identified by the
aria-live="polite"
attribute. The element is
empty on page load.
HTML
Code begins
<div aria-live="polite" class="wb-inv"></div>
Code ends
After the user clicks a sort button in a table column header,
JavaScript populates the <div>
with text.
The screen reader announces “Sorted alphabetically by name".
HTML
Code begins
<div aria-live="polite" class="wb-inv">
Sorted alphabetically by name
</div>
Code ends
Because the result of the sort is apparent to visual users,
the live region is visually hidden with the WET CSS class
.wb-inv
.
CSS
Code begins
.wb-inv {
clip: rect(1px,1px,1px,1px);
height: 1px;
margin: 0;
overflow: hidden;
position: absolute;
width: 1px;
}
Code ends
aria-atomic
Use the aria-atomic
attribute to specify if the whole
live region should be announced, or only the text that changed.
- aria-atomic="false"
- When a live region is updated, only the updated text is announced. Use this value when the updated text makes sense on its own. This is the default value.
- aria-atomic="true"
- When a live region is updated, the entire region is announced. Use this value when the neighbouring static text in the live region provides necessary context to make sense of the updated text.
Good example: aria-atomic false vs true
In these examples, the updated total price in a purchase process is announced when the user adds a product.
In this first example, the aria-atomic
attribute
is not used, so the default value applies, which is "false".
Only the dynamic content is announced, that is, the price. If
the dynamic content isn’t meaningful on its own, it can easily
confuse users. In this case, the dynamic content alone is
vague: "$84.52".
HTML
Code begins
<p aria-live="polite">
Total price:
<span id="total-price">$84.52</span>
</p>
Code ends
In this second example, the aria-atomic
attribute
is set to "true". All the content of the live region is
announced, providing the necessary context to make sense of
the dynamic content: "Total price: $84.52".
HTML
Code begins
<p aria-live="polite" aria-atomic="true">
Total price:
<span id="total-price">$84.52</span>
</p>
Code ends
aria-relevant
The aria-relevant
attribute specifies which types of
changes to a live region should be announced.
- aria-relevant="all"
- All changes are announced. Use with caution, as this setting can be verbose.
- aria-relevant="additions"
- Insertion of nodes to the live region are announced.
- aria-relevant="removals"
- Removal of nodes to the live region are announced. Reserve for important changes, such as a colleague leaving a chat room.
- aria-relevant="text"
- Changes to the text content (including text equivalents, such as alt text) in the live region are announced.
A live region has an implicit aria-relevant
value of
“additions" and “text", so the attribute isn’t needed if the
design calls for the normal behaviour of announcing added content.
Only use the aria-relevant
attribute if you need to
communicate the removal of content from a live region.
aria-busy
Use the aria-busy
attribute to notify assistive
technology that it should temporarily ignore changes to an element
when things are loading. Set
aria-busy="true"
initially and, once everything is in
place, clear the attribute or set it to
aria-busy="false"
.
Special types of live regions
role="alert"
Use the ARIA alert
role to announce important and
typically time-sensitive information that requires the user’s
immediate attention. Setting role="alert"
is
equivalent to setting aria-live="assertive"
and
aria-atomic="true"
. The only difference is that some
screen readers begin the announcement by saying "alert", to
identify it to users as an alert.
Good example: Using role="alert"
In this example, a <div>
element has a
role="alert"
attribute and is set via CSS to
display: none
.
Removing the CSS display: none
value triggers the
live announcement. Exposing such previously-hidden text is
equivalent to injecting text.
The initial alert has the class name hidden
,
which hides the alert text with CSS
display: none
.
HTML
Code begins
<form id="updateProfile" method="post" action="javascript:void(0)">
<p><button>Update profile<button></p>
<div class="confirm hidden" role="alert">You profile has been updated.</div>
</form>
Code ends
CSS
Code begins
.hidden { display: none; }
Code ends
The alert is triggered by removing the CSS class name
hidden
HTML
Code begins
<form id="updateProfile" method="post" action="javascript:void(0)">
<p><button>Update profile<button></p>
<div class="confirm" role="alert">You profile has been updated.</div>
</form>
Code ends
role="status"
Use the ARIA status
role to announce advisory
information to the user that is less urgent than an alert. Setting
role="status"
is equivalent to setting
aria-live="polite"
and
aria-atomic="true"
.
If an element on the page controls what appears in the status,
assign the controlling element the
aria-controls="IDREF"
attribute, pointing to the
id
attribute value of the element with
role="status"
.
Good example: Use role="status"
In this example, a paragraph with the
role="status"
attribute displays the number of
items in a shopping cart. Because
role="status"
by default uses
aria-atomic="true"
, the whole contents of the
paragraph are announced. When the count updates, the live
announcement kicks in. Screen readers declare the
visually-hidden text "Shopping cart", the revised count, and
the word "items".
The title
attribute on the
<span>
holding the icon provides a visual
label for mouse users. Since support for the
title
attribute is inconsistent across screen
readers, the element is hidden from all of them (using the
aria-hidden="true"
attribute) and the more
reliable visually-hidden text is used to label the icon (using
the WET CSS class .wb-inv
).
The aria-controls="IDREF"
attribute is set on the
button and given the id
attribute value of the
element holding the role="status"
attribute.
Example begins
Shopping cart 0 items
Example ends
HTML
Code begins
<p role="status" id="cart">
<span title="Shopping cart" aria-hidden="true" class="glyphicon glyphicon-shopping-cart"></span>
<span class="wb-inv">Shopping cart</span>
<span id="cart-count">0</span>
items
</p>
<button id="btn" onclick="buy()" aria-controls="cart">Add to cart</button>
Code ends
View JavaScript
Code begins
let counter = 0;
function buy() {
counter += 1;
document.getElementById("cart-count").innerHTML = counter;
}
Code ends
View CSS
Code begins
.wb-inv {
clip: rect(1px,1px,1px,1px);
height: 1px;
margin: 0;
overflow: hidden;
position: absolute;
width: 1px;
}
.glyphicon {
position: relative;
top: 2px;
display: inline-block;
font-family: "Glyphicons Halflings";
font-style: normal;
font-weight: 400;
line-height: 1;
-webkit-font-smoothing: antialiased;
}
.glyphicon-shopping-cart:before {
content: "\e116";
}
Code ends
role="timer"
Use the ARIA timer
role to identify a numerical
counter listing the time elapsed from a starting point or the time
remaining until an end point. The role has the implied value of
aria-live="off"
, to prevent frequent announcements
from overwhelming the screen reader user. However, you can
announce the time at regular intervals by using JavaScript to
briefly set the aria-live="assertive"
and
role="alert"
attributes, overruling
aria-live="off"
and role="timer"
.
Good example: Countdown announcing at intervals
In this example, a countdown uses the
role="timer"
, so is silent in screen readers due
to its implicit aria-live="off"
setting.
HTML
Code begins
<div id="countdown" role="timer" aria-atomic="true">
<span id="number">60</span> seconds left!
</div>
However, at 15-second intervals, JavaScript briefly adds the
aria-live ="assertive"
attribute and replaces the
timer
role with role="alert"
. Screen
readers announce the initial alert, “60 seconds left!", then
the time remaining every 15 seconds: “45 seconds left!", etc.
HTML
Code begins
<div id="countdown" role="alert" aria-live="assertive" aria-atomic="true">
<span id="number">45</span> seconds left!
</div>
An interval of 15 seconds between announcements is too brief in practice and is done here simply to illustrate the technique. One minute is a more practical interval.
Try visiting the live demo (Opens in new tab) with a screen reader running.
View JavaScript
Code begins
function decrement() {
var numElement = document.getElementById('number');
var newNumber = parseInt(numElement.textContent - 1);
if (newNumber > -1) {
numElement.textContent = newNumber;
}
if ((newNumber % 15)===0 || newNumber == 0) {
setAlert();
}
}
function setAlert() {
var liveRegion = document.getElementById('countdown');
liveRegion.setAttribute('aria-live', 'assertive');
liveRegion.setAttribute('role', 'alert');
setTimeout(function() {
liveRegion.removeAttribute('aria-live');
liveRegion.setAttribute('role', 'timer');
}, 999);
}
window.setInterval(function() {
decrement();
}, 1000);
window.addEventListener('load', function () {
setAlert(); //alert on 60 seconds (or beginning)
});
Code ends
role="marquee"
Use the ARIA marquee
role to define an area as a type
of live region with non-essential announcements that change
frequently. Examples include stock tickers and frequently-changing
ad banners.
Elements with the marquee
role have an implicit
aria-live="off"
. As with the timer
role,
the content changes too frequently to announce in screen readers.
Screen reader users can still navigate to the area to read the
text.
A marquee is required to have an accessible name. If a visible
label is present use the aria-labelledby
attribute;
otherwise, use aria-label
.
role="log"
Use the ARIA log
role to keep track of sequential
updates, such as a chat log, messaging history, game log or an
error log. New information is added to the end, old information is
optionally removed from the beginning. Updates to the live region
are announced when the user is idle. The live region defined by
role="log"
has implicit
aria-live="polite"
and
aria-atomic="true"
attribute values.
Related WCAG resources
Related WCAG resources
Success criteria
Techniques
- ARIA19: Using ARIA role=alert or Live Regions to Identify Errors
- ARIA22: Using role="status" to present status messages
- ARIA23: Using role=log to identify sequential information updates