可访问的 Web 应用程序和组件概述
大多数 JavaScript 库都提供了一个客户端组件库,可以模仿熟悉的桌面界面的行为。通过结合使用 JavaScript、CSS 和 HTML,就可以构建滑块、菜单栏、文件列表视图等。由于 HTML4 规范没有提供语义上描述这类组件的内置标签,因此开发人员通常会 resorting to 使用通用元素,例如 <div>
和 <span>
。虽然这会生成一个看起来与其桌面对应物相似的组件,但标记中通常没有足够的语义信息供辅助技术使用。
问题
对于因任何原因无法查看屏幕的用户来说,网页上的动态内容可能会带来特别大的问题。股票行情、实时 Twitter feed 更新、进度指示器以及类似内容会以辅助技术 (AT) 可能不知道的方式修改 DOM。这时就需要 ARIA 的介入。
示例 1:未使用 ARIA 标签构建的选项卡组件的标记。标记中没有信息可以描述该组件的形式和功能。
<!-- This is a tabs widget. How would you know, looking only at the markup? -->
<ol>
<li id="ch1Tab">
<a href="#ch1Panel">Chapter 1</a>
</li>
<li id="ch2Tab">
<a href="#ch2Panel">Chapter 2</a>
</li>
<li id="quizTab">
<a href="#quizPanel">Quiz</a>
</li>
</ol>
<div>
<div id="ch1Panel">Chapter 1 content goes here</div>
<div id="ch2Panel">Chapter 2 content goes here</div>
<div id="quizPanel">Quiz content goes here</div>
</div>
示例 2:选项卡组件在视觉上可能如何进行样式设置。用户可能在视觉上认出它,但对于辅助技术来说,不存在机器可读的语义。
ARIA
ARIA 通过在标记中添加特殊属性,使开发人员能够更详细地描述其组件。ARIA 旨在填补标准 HTML 标签与动态 Web 应用程序中发现的桌面式控件之间的空白,它提供了描述大多数熟悉 UI 组件行为的角色和状态。
警告: 许多这些功能是在浏览器不支持现代 HTML 功能时添加的。开发人员应始终优先使用正确的语义 HTML 元素,而不是使用 ARIA。
ARIA 规范分为三种不同类型的属性:角色、状态和属性。角色描述了 HTML 4 中尚不可用的组件,例如滑块、菜单栏、选项卡和对话框。属性描述了这些组件的特征,例如它们是否可拖动,是否包含必需的元素,或者是否关联了弹出窗口。状态描述了元素的当前交互状态,告知辅助技术该元素是否忙碌、已禁用、已选中或已隐藏。
ARIA 属性会被浏览器自动解释,并转换为操作系统原生的可访问性 API。因此,具有 role="slider" 的元素将以与操作系统上的原生滑块相同的方式进行控制。
这提供了比上一代 Web 应用程序更一致的用户体验,因为辅助技术用户在使用基于 Web 的应用程序时,可以将他们对桌面应用程序工作方式的所有知识应用进来。
示例 3:添加了 ARIA 属性的选项卡组件的标记。
<!-- Now *these* are Tabs! -->
<!-- We've added role attributes to describe the tab list and each tab. -->
<ol role="tablist">
<li id="ch1Tab" role="tab">
<a href="#ch1Panel">Chapter 1</a>
</li>
<li id="ch2Tab" role="tab">
<a href="#ch2Panel">Chapter 2</a>
</li>
<li id="quizTab" role="tab">
<a href="#quizPanel">Quiz</a>
</li>
</ol>
<div>
<!-- Notice the role and aria-labelledby attributes we've added to describe these panels. -->
<div id="ch1Panel" role="tabpanel" aria-labelledby="ch1Tab">
Chapter 1 content goes here
</div>
<div id="ch2Panel" role="tabpanel" aria-labelledby="ch2Tab">
Chapter 2 content goes here
</div>
<div id="quizPanel" role="tabpanel" aria-labelledby="quizTab">
Quiz content goes here
</div>
</div>
所有主流浏览器和许多辅助技术都 很好地支持 ARIA。
演示更改
动态演示更改包括使用 CSS 更改内容的外观(例如,无效数据周围的红色边框,或选中复选框的背景颜色更改),以及显示或隐藏内容。
状态更改
ARIA 提供了用于声明 UI 组件当前状态的属性。示例如下(但不限于此):
aria-checked
-
指示复选框或单选按钮的状态。
aria-disabled
-
指示元素可见但不可编辑或无法操作。
aria-grabbed
-
指示拖放操作中对象的“抓取”状态。
(要获取 ARIA 状态的完整列表,请参阅 ARIA 状态和属性列表)。
开发人员应使用 ARIA 状态来指示 UI 组件元素的状态,并使用 CSS 属性选择器来根据状态更改调整视觉外观(而不是使用脚本更改元素上的类名)。
可见性更改
当内容可见性发生变化时(即,元素被隐藏或显示),开发人员应更改 aria-hidden
属性值。应使用上述技术来声明 CSS,以便使用 display:none
可视化地隐藏元素。
以下是一个使用 aria-hidden
控制工具提示可见性的工具提示示例。该示例显示了一个 Web 表单,其中包含与输入字段关联的说明的工具提示。
<div class="text">
<label id="tp1-label" for="first">First Name:</label>
<input
type="text"
id="first"
name="first"
size="20"
aria-labelledby="tp1-label"
aria-describedby="tp1"
aria-required="false" />
<div id="tp1" class="tooltip" role="tooltip" aria-hidden="true">
Your first name is optional
</div>
</div>
以下代码显示了该标记的 CSS。请注意,此处没有使用自定义类名,仅使用了 aria-hidden
属性的状态。
div.tooltip[aria-hidden="true"] {
display: none;
}
更新 aria-hidden
属性的 JavaScript 形式如下。请注意,脚本仅更新 aria-hidden
属性;它不需要同时添加或删除自定义类名。
function showTip(el) {
el.setAttribute("aria-hidden", "false");
}
角色更改
ARIA 允许开发人员为本身提供不正确或无语义的元素声明语义角色。元素的 role
不应更改。相反,应删除原始元素,并替换为具有新 role
的元素。
例如,考虑一个“内联编辑”组件:一个允许用户在原地编辑一段文本而无需切换上下文的组件。此组件具有“查看”模式,在该模式下文本不可编辑但可激活;以及“编辑”模式,在该模式下文本可编辑。开发人员可能会尝试使用只读文本 <input>
元素来实现“查看”模式,并将其 ARIA role
设置为 button
,然后在“编辑”模式下通过使元素可写并删除 role
属性来切换到“编辑”模式(因为 <input>
元素本身具有角色语义)。
不要这样做。相反,应使用完全不同的元素来实现“查看”模式,例如具有 role
为 button
的 <div>
或 <span>
,并使用文本 <input>
元素来实现“编辑”模式。
异步内容更改
注意: 建设中。另请参阅 动态区域
键盘导航
开发人员在创建自定义组件时,常常会忽略对键盘的支持。为了能够被各种用户访问,Web 应用程序或组件的所有功能也应可通过键盘进行控制,而无需鼠标。在实践中,这通常涉及遵循桌面上类似组件所支持的约定,充分利用 Tab、Enter、空格键和方向键。
传统上,Web 上的键盘导航仅限于 Tab 键。用户按下 Tab 键以按线性顺序聚焦页面上的每个链接、按钮或表单,使用 Shift-Tab 向后导航。这是一种一维导航方式——向前和向后,一次一个元素。在相当密集的页面上,仅使用键盘的用户通常需要按下 Tab 键几十次才能访问所需的部分。在 Web 上实现桌面式键盘约定有可能显著加快许多用户的导航速度。
以下是 ARIA 启用的 Web 应用程序中键盘导航应如何工作的总结
- Tab 键应将焦点移到整个组件上。例如,制表符指向菜单栏不应该将焦点放在菜单的第一个元素上。
- 方向键应允许在组件内进行选择或导航。例如,使用左右方向键应将焦点移到前一个和下一个菜单项。
- 当组件不在表单内时,Enter 键和空格键都应选择或激活控件。
- 在表单内,空格键应选择或激活控件,而 Enter 键应提交表单的默认操作。
- 如有疑问,请模仿您正在创建的控件的标准桌面行为。
因此,对于上面示例中的选项卡组件,用户应能够使用 Tab 和 Shift-Tab 键在组件容器(我们标记中的 <ol>
)内外进行导航。一旦键盘焦点进入容器内,方向键应允许用户在每个选项卡(<li>
元素)之间导航。从这里开始,约定因平台而异。在 Windows 上,当用户按下方向键时,下一个选项卡应自动激活。在 macOS 上,用户可以按 Enter 或空格键来激活下一个选项卡。有关创建 可键盘导航的 JavaScript 组件 的深度教程描述了如何使用 JavaScript 实现此行为。