Handle Focus
To make your components accessible to people with disabilities, program them to handle which element has focus and can receive input.
Web browsers are fully navigable with the keyboard using the tab key. For accessibility purposes, users who rely on keyboard navigation need a visual cue to see which element has focus. People with low vision also use screen readers to navigate web pages. Screen readers read aloud the elements on the page, including the element that has focus. As a developer, you need to ensure that when a user tabs through a page, the browser moves focus to the next logical element.
When a user tabs through a page, interactive elements like <a>
, <button>
, <input>
, and <textarea>
receive focus automatically. Elements that are not natively focusable, such as <div>
or <span>
, can use tabindex="0"
to receive keyboard focus.
Only 0
and -1
tabindex values are supported. Assigning tabindex="0"
means that the element focuses in standard sequential keyboard navigation. Assigning it tabindex="-1"
removes the element from sequential keyboard navigation. For more information, see Keyboard Accessibility.
For custom components, focus skips the component container and moves to the elements inside the component.
Let’s look at some code.
In this example, when a user tabs, focus moves from a button element in parent
to an input element in child
, skipping child
itself.
To add focus to a custom component, use the tabindex
attribute. In the parent template, we set the child component's tabindex
to 0
to add the child component itself to the navigation sequence.
When creating custom components that contain focusable elements, you might find yourself managing tab indexes or setting focus manually on these elements. To manage focus automatically, set delegatesFocus
to true
.
Let’s say we have a custom component with a button, which behaves like a native HTML button.
Using delegatesFocus
enables the following cases.
- Adds focus to the native button HTML element using
coolButton.focus()
. - If you click a node inside shadow DOM and the node is not a focusable area, the first focusable area becomes focused. This is similar to when you click on a label and focus jumps into an input.
- When a node inside shadow DOM gains focus, the
:focus
CSS selector applies to the host in addition to the focused element.
Don’t use tabindex
with delegatesFocus
because it throws off the focus order.