Navigation

Blocks of navigation

Semantically identify the important blocks of navigation on a page with either the <nav> element or the role="navigation" attribute. Each creates an ARIA navigation landmark, which screen reader users can target by keyboard command.

If there are two or more navigation regions on the page, name each with aria-label or aria-labelledby to differentiate them.

Indicating the current link within a block of navigation is an example of an easily achievable WCAG Level AAA Success Criterion. It requires two things:

  • style the current link to stand apart visually, and
  • set an aria-current="page" attribute on the link. The attribute must be set on the link since it tends only to work on actionable elements.

 Good example: Pagination

Here, a pagination menu for search results is set in a named nav element. The current link is indicated visually via the CSS, and to screen readers via the aria-current="page" attribute.

CSS

.current-page {
   background-color: #ccc;
   border: 1px solid black;
}

HTML

<nav label="Results by page">
   <ul>
      <li>
         <a href="[…]" aria-label="page 1">1</a>
      </li>
      <li class="current-page">
         <a href="[…]" aria-current="page" aria-label="page 2">2</a>
      </li>
      <li>
         <a href="[…]" aria-label="page 3">3</a>
      </li>
      <li>
         <a href="[…]" aria-label="page 4">4</a>
      </li>
   </ul>
</nav>

Related WCAG resources

Related WCAG resources

Success criteria

Techniques

Skip navigation links

On a poorly-designed website, keyboard users must navigate from the top of the page to the main content area, often through a long list of navigation links and other elements. This can take be tedious and even painful for users with some forms of motor disabilities.

A skip navigation link enables screen reader users and sighted keyboard users to navigate directly to the main content from the top of the page.

A skip link isn’t needed if only a handful of controls separate the main content from the top of the page.

Follow these best practices for skip navigation links:

  • Place the skip navigation link at the top of the page before any other focusable element (link, button, or custom control).
  • The skip link doesn't need to be visible until it receives focus.
  • Use clear link text – e.g. "Skip to Main Content" or "Skip to Content"
  • Use a same-page link, targeting the id attribute value of the destination (usually the <main> element).
  • Assign the destination the tabindex="-1" attribute. This fixes shortcomings in some browsers that move the viewport to the destination but not the focus.
  • Do not hide the skip link using any of these CSS options:
    • Use CSS to permanently position the link off screen
    • Set display: none
    • Set visibility: invisible

HTML

<body>
   <a id="skip-nav" class="show-with-focus" href="#main-content">Skip To Content </a>
      [...]
   <main id="main-content" tabindex="-1">Main Content Goes Here</main>
</body>

CSS

.show-with-focus {
   position: absolute;
   left: -1000px;
   top:-1000px;
   width: 1px;
   height: 1px;
   text-align: center;
   overflow: hidden;
}
.show-with-focus: focus, .show-with-focus: active {
   position: absolute;
   left: 0;
   top: 0;
   width: auto;
   overflow: visible;
   background-color: #FF3;
   border: 1px dotted #000;
}

 Good example: Skip to main content

 "Screenshot of the ESDC IT Accessibility office showing a "Skip to main content" link at the top of the page.  "Screenshot of the source code. The skip link is one item in a list, in a nav element with the label "Skip links""

Related WCAG resources

Related WCAG resources

Success criteria

Techniques

Multiple ways

Provide more than one way to locate a Web page within a set of Web pages. Users may find one technique easier or more comprehensible to use than another.

Use two or more of the following techniques:

  • Provide links to navigate to related Web pages.
  • Provide a Table of Contents.
  • Provide a site map.
  • Provide a search function to help users find content.
  • Provide a list of links to all other Web pages.
  • Link to all of the pages on the site from the home page.

Exception: Note that this WCAG criterion doesn't apply if the web page is the result of, or a step in, a process.

Related WCAG resources

Related WCAG resources

Success criteria

Techniques

Use two or more of the following techniques:

Table of contents

A table of contents serves two purposes:

  • It acts as an overview of the document’s main topics and so allows users to preview the content without having to scroll down and read or skim.
  • It allows readers to navigate directly to a specific section of the document.

The table of contents for a page should reflect the heading structure of the page.

A table of contents is particularly helpful to sighted users with motor disabilities, blind users and keyboard users.

WCAG Success Criterion 2.4.5: Multiple Ways requires that users have multiple avenues for finding web pages on a site. Navigation blocks, search, site maps, or a table of contents can support this Level AA criterion.

 Good example: Table of contents

In this example, a screenshot of a table of contents shows heading text as links. Headings of levels 1, 2 and 3 are included.

Screenshot of a table of contents shows heading text as links.

Related WCAG resources

Related WCAG resources

Success criteria

Techniques

Meaningful sequence

Screen readers read content directly from the DOM (a page’s underlying code after JavaScript has modified it), not the actual screen. They ignore any CSS rules. It’s possible to use CSS (floats, positioning, margins, and padding) to achieve a visual reading order that’s meaningful while under the hood, the reading order of the underlying code (top to bottom) doesn’t make sense. See the example in Failure F1, in Related WCAG resources, below.

Remove CSS styling to simulate the screen reader experience. The content should make sense, reading top to bottom.

To ensure a meaningful reading order, position content in the same sequence as the underlying code.

Related WCAG resources

Related WCAG resources

Success criteria

Techniques

Failures

Focus and focus order

What is focus?

Focus refers to which interactive control on the screen -- a link, form control, button, or custom control -- currently receives input from the keyboard (and from the clipboard when you paste content).

Focus determines where keyboard events go in the page. For instance, if you focus a text input field and start typing, it receives the keyboard events and displays the characters you type. While it has focus, it also receives pasted input from the clipboard. Some of the native controls even have additional keyboard support built in. For instance, with the select element focused you can press the Up and Down arrow keys to select different children, and start typing to auto-complete to one of the available items.

An item with focus also has what’s called a visual focus indicator or focus ring. The style of it depends on the browser or the styling applied by the page author. Firefox, for instance, displays a dashed border, whereas Chrome highlights focused elements with a blue border.

For keyboard users, focus is absolutely critical. It’s the equivalent of a mouse cursor, and it's how they reach all of the interactive controls in an application.

Not all elements are focusable. Non-interactive elements like images, paragraphs, divs, and various other page elements are not focused as you tab through the page. This is by design, as users have no need to focus on something if they can't interact with it.

Focus order

Keyboard users navigate from interactive item to interactive item using the Tab key, in sequential order, following what’s called the focus order. They use the Shift-Tab keys to move backwards in the focus order. Like reading order, focus order is determined by the Web page’s source order. The order of interactive items (links, buttons, form controls and custom controls) in the DOM is the order in which they’re encountered by keyboard users.

The keyboard navigation order must be logical and intuitive. Typically, this means ensuring the navigation follows the visual flow of the page, left to right, top to bottom. It moves through the banner, main navigation, page navigation and controls, then footer on a typical page.

Focus order can be confounded by JavaScript. When JavaScript inserts new content, the content should follow the triggering element, not precede it. Screen reader users will not expect new content to fall before the trigger. Module 10’s section Focus management with JavaScript-injected content goes into greater detail.

Built-in interactive HTML elements – links, buttons and form controls – are implicitly focusable, meaning they receive focus by default without additional markup.

To receive focus, a link must have a populated href attribute.

To prevent a link from receiving focus, remove its href attribute.

To prevent a button or form control from receiving focus, add the Boolean "disabled" attribute. When present, it makes the element not mutable, focusable, or submitted with the form. The user can neither edit nor focus on the control, nor its form control descendants. You can also prevent a control from gaining focus by giving it a tabindex="-1" attribute.

Custom links and controls require a tabindex="0" attribute to receive focus. See Good example: Inserting a custom link into the tab order, below, for all the CSS, HTML attributes and JavaScript required to emulate a link. Important: When possible use a built-in HTML element instead of building a custom control with ARIA.

The tabindex attribute

The tabindex attribute is mostly used as a means of managing focus within widgets.

  • A tabindex attribute value of 0 puts the element in the focus order, at its current location in the DOM.
  • A tabindex value of -1 removes an interactive element from the focus order, but enables it to be targeted by script (and changed) using its focus() method. For instance, with the Tabs widget, only one tab at a time may be in the tab order: the selected tab has tabindex="0", while the inactive tabs have tabindex="-1". The tabindex values change as the keyboard user navigates across the tabs, using the Arrow keys to set focus on a new tab. See the description of the Tabs widget in module 12.
  • A tabindex value greater than 0 is almost always a bad idea and should be avoided. It moves the element to the beginning of the page’s focus order, and is encountered in ascending order with any other positive tabindex values. Positive tabindex values are difficult to maintain and brittle, and their use tends to confound user expectations of focus order. Instead, write the document with the elements in a logical sequence. See Bad example: Page design with positive tab index values, below.

In the example below, press the Tab to move focus forward from link to link, and the Shift-Tab keys to move focus backwards.

The third link is a custom link:

  • The tabindex="0" attribute adds the <span> element to the focus order.
  • The role="link" attribute identifies it to screen reader users.
  • The class="link" attribute enables styling to match default links and to provide a highly-visible keyboard focus indicator.
  • The click event handles mouse and touch input.
  • The keydown event handles Enter key input.
Bing DuckDuckGo Google
View HTML
<a href="http://www.bing.com" class="link">Bing</a> 
<a href="http://www.duckduckgo.com" class="link">DuckDuckGo</a> 
<span 
   tabindex="0" 
   role="link" 
   class="link"
   onclick="goToLink(event, 'http://www.google.ca/')" 
   onkeydown="goToLink(event, 'http://www.google.ca/')">
      Google
</span>
View CSS
<style type="text/css">
   .link:focus, .link:hover {
      outline: 3px solid orange;
   }
   span.link {
      cursor: pointer;
      color: #0000EE;
      text-decoration: underline;
   }
   span.link:active {
      color: #FF0000;
   }
</style>
View Javascript
<script type="text/javascript">
   function goToLink (event, url) {
      var type = event.type;
      if ((type === 'click') || (type === 'keydown' && event.keyCode === 13)) {
         window.location.href = url;    
         event.preventDefault();
         event.stopPropagation();
      }
   }
</script>

The custom link JavaScript is from the Web Accessibility Initiative (WAI) document: Link Examples in the Link pattern of the WAI-ARIA Authoring Practices 1.1. Matt King, JaEun Jemma Ku, James Nurthen, Zoë Bijl, Michael Cooper. Copyright © 2019 W3C® (MIT, ERCIM, Keio).

Element with tabindex = "-1"

A tabindex="-1" attribute value removes the element from the focus order, but allows it to receive programmatic focus. This means focus can be set to it using the element’s JavaScript focus() method.

 Good example: Element with tabindex="-1" receives focus by script

In this example, clicking the button sets focus on the div element.

I am a div

HTML

<button type="button" onclick="document.getElementById('target').focus();">
   Click on me to focus the DIV
</button>
<div id="target" tabindex="-1">
   I am a div
</div>

Element with tabindex > "0"

Using a tabindex attribute value greater than 0 is considered an anti-pattern.

Any tabindex greater than 0 jumps the element to the front of the natural tab order. If there are multiple elements with a tabindex > 0, then the tab order starts from the lowest value greater than zero and works its way up.

Positive tabindex values often create counter-intuitive flow for keyboard users. If you want an element to come sooner in the tab order, move it to an earlier spot in the DOM rather than set a positive tabindex value.

 Bad example: Page design with positive tab index values

The tab order when user tabs the page is as follows:

  • The "Going to" field (tabindex="1")
  • The "Check-in" field (tabindex="2")
  • The "Check-out" field (tabindex="3")
  • A mystery object that has no functionality, and no visible focus indicator (tabindex="4")
  • "More travel" and then follows the natural tab order (tabindex="0").
Screenshot showing the tab order on a page

The positive tabindex is set on just four items in the "Carnival" page. After navigating through the positive tabindex values, keyboard users are sent back to the top, to the first focusable control on the page at the beginning of the natural tab order.

A visually hidden item is in the tab order on the page, creating a "mystery" focus that can lead to confusion. If something is visually hidden, it must not be in the tab order.

Avoid using tabindex values greater than 0. Instead, write the document with the elements in a logical sequence. Ensure the source code (DOM) order matches the visual order to avoid confusion for assistive technology users.

Related WCAG resources

Success criteria

Techniques

Failures

Character key shortcuts

A keyboard shortcut is a terrific convenience for most, but it's a severe barrier for some users with disabilities if the shortcut doesn't include a non-printable key (e.g., Ctrl, Alt). Just by talking, voice input users will unintentionally trigger a shortcut consisting only of letter keys, since their speech input is converted by the software into a string of letters. Users who are prone to accidentally hitting keys will also trigger the shortcut.

WCAG Success Criterion 2.1.4: If a keyboard shortcut is implemented in content using only letter (including upper- and lower-case letters), punctuation, number, or symbol characters, then at least one of the following is true:

Turn off
A mechanism is available to turn the shortcut off;
Remap
A mechanism is available to remap the shortcut to include one or more non-printable keyboard keys (e.g., Ctrl, Alt);
Active only on focus
The keyboard shortcut for a user interface component is only active when that component has focus.

Related WCAG resources (Character key shortcuts)

Related WCAG resources

Success criteria

Techniques

Failures

Back to top