加载笔记内容...
加载笔记内容...
浏览器通过 focus tree 管理可聚焦元素,其遍历顺序由 DOM 顺序 和 tabindex
属性共同决定。在无障碍领域,这对应着 accessibility tree 的构建过程。现代浏览器遵循 WHATWG 焦点规范 的算法:
1焦点顺序 = 自然顺序元素 + tabindex=0 元素(按 DOM 顺序)
2 + tabindex>0 元素(按数值升序排列)
值域 | 可聚焦性 | Tab 键序 | 编程式聚焦 |
---|---|---|---|
未设置 | 依赖元素类型 | 自然顺序 | 支持 |
0 | 强制可聚焦 | 插入自然顺序 | 支持 |
-1 | 强制可聚焦 | 排除顺序 | 支持 |
>0 | 强制可聚焦 | 按值排序 | 支持 |
对于异步加载内容,推荐使用 focus trap 模式。以模态对话框为例:
1function Modal({ isOpen }) {
2 const ref = useRef(null);
3
4 useEffect(() => {
5 if (isOpen) {
6 ref.current.focus();
7 const focusable = ref.current.querySelectorAll(
8 'button, [href], input, select, textarea, [tabindex]:not([tabindex="-1"])'
9 );
10 if (focusable.length > 0) {
11 focusable[0].focus();
12 }
13 }
14 }, [isOpen]);
15
16 return isOpen && (
17 <div role="dialog" ref={ref} tabIndex={-1}>
18 {/* 对话框内容 */}
19 </div>
20 );
21}
当必须自定义控件时,需实现完整的键盘交互范式:
1<div role="button"
2 tabindex="0"
3 aria-pressed="false"
4 onKeyDown={e => e.key === 'Enter' && handleClick()}>
5 Custom Button
6</div>
配合 ARIA 状态管理:
争议点:是否完全禁用 tabindex>0?
解决方案:
1// 安全检测脚本
2document.querySelectorAll('[tabindex]').forEach(el => {
3 const value = parseInt(el.getAttribute('tabindex'));
4 if (value > 0) {
5 console.warn('Avoid positive tabindex:', el);
6 }
7});
1<template>
2 <div v-focus-trap="isActive">
3 <button v-focus-first>Submit</button>
4 </div>
5</template>
6
7<script>
8export default {
9 directives: {
10 focusFirst: {
11 inserted(el) {
12 el.focus();
13 }
14 }
15 }
16}
17</script>
工具 | 检测能力 | 集成方式 |
---|---|---|
axe-core | tabindex >0 检测 | CI/CD 管道 |
Lighthouse | 可聚焦元素审计 | Chrome DevTools |
WAVE | 可视化焦点路径 | 浏览器扩展 |
Jest-axe | 单元测试集成 | 测试套件 |
通过动态调整 tabindex 实现工具栏状态同步:
复杂表格的焦点策略:
避免大规模动态 tabindex 修改,推荐使用 CSS order 属性配合 flex 布局实现视觉顺序调整,同时保持 DOM 顺序不变。
1// 获取当前焦点路径
2document.addEventListener('focus', (e) => {
3 console.log('Focus path:', e.composedPath());
4}, true);
通过 Chrome 的 Accessibility 面板可实时查看元素的 accessibility tree 结构。
焦点管理不应止步于 tabindex 的机械使用,而应将其纳入设计系统的基础架构。建议建立:
正如 W3C 专家 Steve Faulkner 所言:"Focus management is not a feature, it's a fundamental requirement for inclusive design." 通过技术手段与设计思维的结合,我们才能真正实现数字产品的无障碍化。