2.3. Navigation Shortcuts
Introduction
Let's talk about the websites with a lot of links at the top of the page before the actual main content.
The keyboard-only users are forced to tab through every single link before they can reach the main content. We, as web creators, can make better than that, right?
A common way to bypass this is to create "Skip Navigation Links". The basic concept involves two elements: A trigger and a target.
<!-- Trigger: a link pointing to an #id -->
<a href="#main" class="skipLink">Skip to main content</a>
<!-- Target: A part of the page with the same id -->
<!-- Some browsers will only focus <main> if tabindex="-1" is used -->
<main id="main" tabindex="-1">...</main>
We can visually hide the skip links by default and only show it when focused.
.skipLink:not(:focus) {
/* hide visually the link using .sr-only styles */
position: absolute;
width: 1px;
height: 1px;
/* rest of .sr-only styles... */
}
.skipLink:focus {
/* link styles when it's focused */
}
This skip link must be one of the first elements in the DOM to be quickly accessed through the keyboard.
Exercise
In the exercise page, let's create a "Skip Navigation" link to jump directly to the main section of the page.
🎯 Goal: Create navigation shortcuts through the page.
Bonus
#1 Target styling
When creating skip links using id #, we can style using the CSS pseudo-selector :target.
🎯 Goal: Use :target to style the main area when it's focused.
Limitation: With this approach, you'll notice the target animation only works once. Because the #main selector is added to the page URL, when triggered again it will be ignored, unless the URL no longer contains that selector. To overcome this, JS would be required.
#2 Using Tabindex
We can create "Skip Navigation" for other scenarios. For example, in a "Back to Top" shortcut.
Usually people implement this widget with a scroll mechanism but forget about the keyboard aspect.
🎯 Goal: In the "Back to Top", add keyboard support by using tabindex and JavaScript.
🍀 Toggle hint #1 - JS focus behavior
When using elTitle.focus(), you'll notice the scroll to top is not smooth anymore. The focus() specs accepts a parameter that solves this problem… ;)
#3 Scroll behaviors
The scroll to top is smooth, always. Based on what we've learned so far, do you think this behavior is inclusive?
That's right… it doesn't respect the user's motion preferences! In JavaSacript is possible to detect if a media query matches, using window.matchMedia().
🎯 Goal: Modify the scroll behavior to respect the user preference.
🍀 Toggle hint #1 - Using JS media
The media you'll need to use is:
const motionReduced = window.matchMedia("(prefers-reduced-motion: reduce)");
if (motionReduced.matches) {
/* ... */
}
Further reading
WCAG Success Criterion
Exercise takeaways
(After the exercise) Reveal takeaways
- Include a "Skip navigation" in websites with long headers.
- When actions change the position on the page, ensure the focus follows along.
- Use
tabindexwith caution, only to enhance keyboard navigation.