Skip to main content
WCAGrules
Quick navigation

Do not build controls outside the accessibility API

F15 is a documented failure under the name, role and value rule, and it is the broadest failure that rule has. The title carries the part people miss. A control fails if it does not use the accessibility API for its technology, or if it does so incompletely. Half an implementation is the same finding as none. A slider that reports its role and never its value tells the user they have found a volume control and not how loud it is. ARIA is the mechanism where the technology supports it, and a native element is better wherever one exists. One boundary is worth knowing before you write your report. Keyboard operation, target size and color contrast are all real requirements and none of them belong to this rule, so a control that is perfectly exposed and unreachable by keyboard has a different finding against it.

How we find it in an audit

Reviewers open the accessibility tree and read what each custom control publishes. Role, name, current value, and whether the value updates when the control moves. The published order of preference is the accessibility checker for the technology first, browser developer tools second, an assistive technology third, and we use more than one because they disagree with each other. Automated tools catch missing roles and missing names reliably. Whether the value keeps up with the widget is something you have to move the widget to see.

How affected users experience it

A screen reader reads the accessibility tree, not the screen. A custom control that publishes nothing to it is announced as whatever text happens to be inside, or as nothing at all, so a beautifully built volume slider arrives as a piece of prose. The half-built version is worse in one specific way. The user is told there is a slider, tries to set it, and gets no feedback about where it landed, so they are adjusting something blind and hoping. Someone using speech input cannot address the control by name, because it has not got one.

Passes vs. fails

Passes: name, role, and state exposed. Fails: a control with no identity.

Passes

<div role="slider" tabindex="0" aria-label="Volume" aria-valuemin="0" aria-valuemax="100" aria-valuenow="40" onkeydown="handleArrows(event)"></div>
<!-- Better still, where a native control exists: -->
<input type="range" min="0" max="100" value="40">

Fails

<div class="slider">
  <div class="slider-thumb" onmousedown="startDrag(event)"></div>
</div>

How this gets tested

The W3C publishes test rules that define what a checker looks for here.

The other techniques filed under this rule

23 guides on this site are filed under 4.1.2 Name, Role, Value. W3C documents this one as a failure of that rule, so it describes a way the rule gets broken rather than a way to pass it.

This guide is our interpretation of W3C technique F15: Failure of Success Criterion 4.1.2 due to implementing custom controls that do not use an accessibility API for the technology, or do so incompletely. W3C publishes its techniques as guidance rather than as the standard, and says so on every one of them. The success criterion is what conformance is measured against, and a technique is one documented way to meet it.

Go somewhere useful

Find tools, resources and your workspace.

29 destinations