button上用:read-only根本不起作用,因为按钮不支持readonly属性,浏览器直接忽略;只有input、textarea等原生可编辑表单控件才支持:read-only,且必须显式设置readonly属性;禁用状态唯一可靠样式钩子是:disabled,需配合真实disabled属性确保语义、视觉与行为统一。

button上用:read-only根本不起作用
按钮没有readonly属性,浏览器会直接忽略<button readonly></button>这种写法,也不会触发:read-only伪类匹配。你写的button:read-only样式永远不会生效——这不是兼容性问题,而是语义错误。只有<input>、<textarea></textarea>这类可编辑表单控件才支持readonly,且必须是它们原生支持的类型(比如type="text"或type="password")。其他如select、checkbox、button加readonly属性等于没写。
:disabled是禁用状态唯一可靠的样式钩子
只要元素有disabled属性(如<button disabled></button>),浏览器就自动赋予它:disabled状态,并阻止所有交互:不响应点击、不获取焦点、不参与表单提交。这是HTML原生语义,也是CSS样式能准确绑定的唯一依据。常见错误包括:
- 只设
opacity: 0.5或pointer-events: none,但没加disabled属性——按钮仍可被键盘聚焦、屏幕阅读器仍读作“可点击” - 用JS动态切换
disabled时,忘记同步移除/添加属性(比如只改class),导致样式和实际行为脱节 - 在深色模式或高对比度模式下硬编码颜色值,遮罩层在系统主题切换后失效
:read-only和:disabled对表单提交的影响完全不同
这是最常被忽视的实际后果:
-
input:read-only的值仍会随form提交;input:disabled的值则完全不提交 -
:read-only元素仍可获得焦点、选中文本、复制内容;:disabled元素连tab键都跳过它 - 同一个
input若同时设readonly和disabled,:disabled样式优先级更高,且disabled逻辑覆盖readonly
所以别试图用:read-only模拟禁用按钮——它不是设计来干这事的。
立即学习“前端免费学习笔记(深入)”;
该用哪个伪类,取决于你要控制什么行为
简单判断逻辑:
- 要让用户“看得到、点不了、不提交” → 用
disabled+:disabled - 要让用户“看得见、点得进、能复制、但不能改” → 用
readonly+:read-only(仅限input/textarea) - 想给非表单元素(比如
div)加类似只读效果 → 用contenteditable="false",再配:read-only
伪类不是视觉开关,而是语义快照。样式只是副产品,行为一致性才是关键——尤其在a11y和表单逻辑里,错配一个伪类,可能让整个提交流程出错。


















