不能。aria-required仅对具有明确表单控件语义(如role="textbox")且可聚焦(tabindex)的元素生效,单独用于div/span会被浏览器忽略;必须配合role、tabindex和含“必填”字样的aria-label才能被读屏正确播报。

aria-required 能不能用在 div 或 span 上
不能。浏览器会静默忽略 aria-required="true" 加在 <div>、<code><span></span>、<button></button> 等非输入型元素上——它只对可聚焦、可输入的控件有意义,且必须已通过 role 或原生语义明确其为“表单控件”。
常见错误是给一个自定义封装的 <myinput></myinput> 组件外层 <div> 加 <code>aria-required,结果读屏完全不播报“必填”,因为该 <div> 没有 <code>role,也不可聚焦、不可输入。
- ✅ 合法:带
role="textbox"的<div tabindex="0">,或 <code>role="combobox"+aria-expanded的下拉容器 - ❌ 无效:没设
role的<div>;<code><span></span>即使加了tabindex="0"也不行(缺少输入语义) - ⚠️ 风险:滥用会导致部分读屏跳过整个字段,或报 WAI-ARIA 规范警告
-
tabindex="0"让它能被键盘聚焦(否则aria-required不生效) -
aria-label必须包含字段名和“必填”字样——仅靠aria-required="true"不会播报“必填”二字 - 不能省略
aria-label改用aria-labelledby,除非你确保关联的<label></label>文本里已含“必填”
非原生框标必填的正确写法
必须同时满足三个条件:声明角色(role)、支持聚焦(tabindex)、显式标注必填(aria-required="true")。缺一不可。
例如一个用 <div> 实现的富文本编辑器:
<pre class="brush:php;toolbar:false;"><div role="textbox" aria-required="true" aria-label="正文内容,必填" contenteditable="true" tabindex="0"></div></pre>
<ul>
<li>
<code>role="textbox" 告诉辅助技术这是个可编辑文本区域
为什么只写 aria-required="true" 还是没读出来
因为 aria-required 是状态属性,不是文本提示。它只告诉读屏“这个字段逻辑上必填”,但不提供任何播报文案。如果 label 或 aria-label 里没出现“必填”“required”“*”等关键词,NVDA、VoiceOver 就只会读“编辑框”,不会提“必填”。
- ❌ 错误:
<div role="textbox" aria-required="true" tabindex="0"> → 读屏只说“编辑框” <li>✅ 正确:<code><div role="textbox" aria-required="true" aria-label="标题,必填" tabindex="0"> → 读屏说“标题,必填,编辑框” <li>⚠️ 注意:<code>aria-label必须包含原始字段名,“必填”不能单独出现,否则用户不知道是哪个字段 - 启用必填:先确保元素已有
role和tabindex,再设aria-required="true" - 禁用必填:设
aria-required="false"(不是移除属性) - 同步更新:若 JS 同时切换了原生
required(比如在<input>上),也必须同步操作aria-required,否则语义不一致 - 验证是否生效:用 Chrome DevTools 的 Accessibility Inspector 查看 Computed Properties 里的 “Required” 是否为 true/false
动态切换必填状态时怎么更新 aria-required
不能直接移除 aria-required 属性,也不能设成 aria-required="" 或 aria-required="1"——这些值无效,部分读屏会忽略或误读。
aria-label 里的“必填”二字,以及忘记给自定义控件加 tabindex。这两个点一缺,aria-required 就等于没写。











