背景

弹窗打开后焦点仍停在背景,键盘用户会不知道当前操作范围。可访问性需要设计焦点进入、停留和恢复的完整流程。

核心判断

  1. 打开时将焦点移到有意义的控件或标题,提供可访问名称。
  2. 模态弹窗限制背景交互,并处理 Tab 循环与 Escape。
  3. 关闭时恢复到触发控件,触发控件消失时选择合理后备目标。

最小示例

下面保留核心逻辑;业务类型、调用入口和环境配置按项目补齐。

let trigger: HTMLElement | null = null;

async function openDialog() {
  trigger = document.activeElement instanceof HTMLElement
    ? document.activeElement
    : null;
  open.value = true;
  await nextTick();
  dialogRef.value?.focus(); // 容器配置 tabindex="-1"
}

async function closeDialog() {
  open.value = false;
  await nextTick();
  if (trigger?.isConnected) trigger.focus();
}

边界与误区

给容器 focus 前需满足可聚焦条件,如 tabindex=-1。仅移动焦点不能完成 focus trap,aria-modal 也不会自动禁用背景。

验证方式

只用键盘完成打开、填写、取消和重开,再用屏幕阅读器检查名称与顺序;异步加载内容不能把用户正在使用的焦点抢走。

小结

打开时保存触发元素,关闭时恢复焦点,并为 modal 提供键盘逃生路径。