:required伪类仅对原生支持required属性的表单元素(input/select/textarea)生效;需确保属性透传、选择器正确、避开safari旧版组合伪类bug,并注意css优先级与作用域限制。

required伪类不生效?检查表单控件是否原生支持
:required 只对原生支持 required 属性的表单元素有效,比如 <input>、<select></select>、<textarea></textarea>。自定义组件(如 React 封装的 MyInput)或禁用 required 属性的元素不会触发该伪类。
-
<input type="text" required>✅ 匹配:required <div contenteditable="true" required> ❌ 不匹配,<code>contenteditable元素不支持required-
<input type="hidden" required>❌ 浏览器忽略隐藏输入的:required样式(虽属性存在,但伪类不激活) - Vue/React 中若用
v-model或value + onChange管理状态,但没把required属性透传到真实<input>上,样式也不会生效 - 正确写法:
input:required、textarea:required、select:required - 想连带高亮 label,得用相邻/兄弟选择器:
input:required + label(需 label 在 input 后)或input:required ~ label(更宽松) - 如果 label 是包裹结构(
<label><input required></label>),可用label input:required,但注意这匹配的是 label 内部的 input,不是 label 自身 - Safari 14.1 及更早:优先用
:required配合 JS 监听input和blur,动态加 class(如is-invalid) - Chrome/Firefox/Edge 无此问题,
input:required:invalid可直接用 - 不要依赖
:required:valid做成功态提示——它只在用户输入后才成立,初始空值时既不:valid也不:invalid(处于 indeterminate 状态) - 显式提高权重:
input:required, textarea:required, select:required比单个input:required权重略高(多个选择器并列) - 更稳妥:
input[required]和input:required权重相同,但前者兼容所有支持属性选择器的浏览器,且语义明确 - 如果用了 CSS-in-JS 或 scoped style(如 Vue
<style scoped></style>),确认:required没被自动添加属性选择器隔离掉(例如变成input:required[data-v-xxx])
样式写错位置?确保选择器能命中实际渲染的元素
常见错误是把 :required 写在父容器或 label 上,比如 label:required —— 这永远不生效,因为 label 本身没有 required 属性。
浏览器兼容性陷阱:Safari 旧版本不支持 :required 与 :invalid 组合
:required:invalid 这类组合伪类在 Safari ≤ 14.1 中有 bug:即使输入为空,:required:invalid 也不触发。单独用 :required 没问题,但想“只对必填且当前无效的项加红边”,就得绕开。
样式被覆盖?:required 的优先级和 specificity 很关键
:required 本身不增加 specificity,它的权重等同于一个类选择器(.class)。如果已有 input { border: 1px solid #999; },而你写 input:required { border-color: #d32f2f; },它会被前面的规则覆盖(因为同为 element + pseudo-class,但声明顺序靠后 ≠ 自动更高)。
立即学习“前端免费学习笔记(深入)”;
事情说清了就结束。真正卡住人的,往往不是伪类本身,而是它依赖的 HTML 结构是否真实、是否被 JS 干扰、以及 Safari 那个藏得挺深的组合伪类 bug。










