不一定。原生自带语义和键盘交互能力,无需额外role或aria-label;仅当用或模拟按钮时,才必须同时设置role="button"、tabindex="0"、aria-label(或可见文本)及键盘事件处理。

按钮必须有明确的role和aria-label吗?
不一定。原生 <button></button> 元素自带语义和键盘交互能力,屏幕阅读器能自动识别其角色、状态和标签。只有当用 <div> 或 <code><span></span> 模拟按钮时,才必须手动加 role="button" 和 aria-label(或 aria-labelledby)。否则反而会破坏默认行为,比如触发两次点击事件。
- 优先用
<button></button>,而不是<div onclick="..." tabindex="0"> <li>如果用了非语义元素,必须同时设置:<code>tabindex="0"、role="button"、aria-label(或确保内部有可读文本) - 避免给原生
<button></button>再加role="button"——这是冗余且可能干扰某些 AT(辅助技术) - 被跳过焦点流(不响应
Tab) - 被屏幕阅读器宣布为“禁用”
- 触发样式伪类
:disabled - 始终用原生
disabled属性控制禁用状态 - 不要用
pointer-events: none或仅靠 CSS 隐藏交互 - 若需动态启用/禁用,直接操作
button.disabled = true/false - 普通提交按钮、链接式按钮不需要
aria-pressed - 必须配合
role="button"使用(原生<button></button>可以直接用,但需确保 JS 同步更新属性) - 切换状态时,务必同步更新
aria-pressed值和视觉样式(例如通过 class 控制背景色)
为什么disabled按钮仍能被键盘聚焦?
因为没正确使用原生 disabled 属性。用 disabled 的 <button disabled></button> 会自动:
但很多人用 CSS 类(如 class="btn-disabled")配合 JavaScript 禁用逻辑,却忘了移除 tabindex 或保留 aria-disabled="true"。结果是视觉上灰掉,但键盘用户仍能聚焦并误触。
aria-pressed 该用在什么场景?
只用于切换按钮(toggle button),比如“播放/暂停”、“显示/隐藏侧边栏”。它告诉辅助技术当前是“按下”还是“弹起”状态,对应 aria-pressed="true" 或 aria-pressed="false"(不能省略值)。
文章转信息图。将文章/笔记转化为手机可读的 HTML 信息图,自动匹配视觉风格。触发场景:文章转图、笔记转图、信息图、转小红书图、做张图、可视化这篇文章、文生图。
<button aria-pressed="false" onclick="togglePlay()">▶ 播放</button>
图标按钮为什么总被读作“空白”?
因为 SVG 或字体图标本身没有文本内容,屏幕阅读器找不到可播报的文本。即使加了 alt(对 SVG 无效)或 title(部分 AT 不读),也不如显式提供可访问名称可靠。
- 对纯图标按钮,用
aria-label直接提供说明,例如:<button aria-label="删除这条消息"><svg>...</svg></button> - 如果图标旁已有可见文字(如“ 关闭”),无需额外
aria-label,但需确保文字与图标包裹在同一<button></button>内 - 避免只靠
aria-hidden="true"隐藏图标却不提供替代文本——这等于删掉了所有信息
颜色对比、焦点轮廓、鼠标悬停反馈这些虽重要,但可访问性第一道关卡,永远是:按钮有没有被正确识别为按钮,以及它到底在干什么。漏掉其中一环,键盘用户或屏幕阅读器用户就卡住了。










