卡片内多个链接指向同一目标时,Tab会重复聚焦,应合并语义:主链接包裹整个卡片,次要元素改用role="link"并手动处理键盘事件与无障碍属性。

卡片里多个链接共用同一目标时,tab会重复聚焦
用户用键盘导航时,一张卡片内如果同时有标题链接、图片链接、操作按钮链接,且都指向同一页面(比如 /post/123),浏览器默认会给每个 <a> 分配独立焦点。结果按一次 Tab 就卡在同一个逻辑目标上三次——这不是 bug,是语义错误:HTML 认为这是三个不同可交互元素。
解决思路不是隐藏链接,而是合并语义。常见做法:
- 只保留一个主链接,包裹整个卡片内容(用
<a>包<h3>、<img>、<p>等),其他“点击区域”改为<div role="link">并加tabindex="-1",再通过 JS 绑定相同跳转逻辑 - 若必须保留多个
<a>(如 SEO 或 CMS 限制),则给次要链接加aria-hidden="true"+tabindex="-1",并确保它们不暴露给屏幕阅读器 - 绝对不要用
display: none或visibility: hidden隐藏次要链接——它们仍可能被读屏软件捕获或意外获得焦点
role="link" 和原生 <a> 的行为差异
用 role="link" 模拟链接时,它不会自动触发 Enter 或 Space 键跳转,也不自带 href 导航能力。必须手动补全:
- 监听
keydown,对Enter和Space调用window.location.href = "...";或router.push(...) - 设置
tabindex="0"才能被聚焦(tabindex="-1"只允许 JS 聚焦) - 加上
aria-label或aria-labelledby,否则屏幕阅读器只会读“link”,没上下文
例如:<div role="link" tabindex="0" aria-label="阅读文章《前端可访问性实践》">...
立即学习“前端免费学习笔记(深入)”;
图片链接和文字链接共存时的 alt 与 aria-label 冲突
卡片里常有缩略图+标题都指向同个详情页。如果图片已设 alt="文章封面:前端可访问性实践",标题又写 <a href="/post/123">前端可访问性实践</a>,屏幕阅读器可能连续读两遍相似描述。
- 图片链接应设
alt=""(空值),因为它的语义已被标题覆盖;若需保留图片信息,改用aria-describedby="desc-id"指向一段补充说明 - 避免给标题链接再加
aria-label——它会覆盖链接文本,反而丢失可读性 - 检查 Chrome DevTools 的 Accessibility 面板,看“Name”字段是否重复或冗余
卡片组件中容易被忽略的焦点管理细节
可访问性问题往往藏在边界场景里:
- 卡片带“收藏”“分享”等操作按钮时,这些按钮必须和主链接分离,不能塞进同一个
<a>;否则用户无法单独触发操作 - 使用
prefers-reduced-motion媒体查询控制 hover/focus 动画,否则动画可能引发眩晕,且某些系统会禁用焦点样式 - 卡片列表用
<section>或<article>包裹,比纯<div>更利于屏幕阅读器识别结构
最麻烦的不是写对第一个卡片,而是确保第 27 个卡片在动态渲染、懒加载、服务端渲染后,焦点顺序和语义依然一致——这需要把焦点逻辑封装进组件生命周期,而不是靠手动加 tabindex。



















