hover样式应与基础样式写在同一选择器块中,确保顺序正确;transition须定义在常态下,hover仅改触发值;优先使用transform和opacity实现动画以提升性能。

hover 样式必须写在元素自身选择器里
很多人把 :hover 单独提出来写成独立规则,比如先写 .btn { color: blue; },再写 .btn:hover { color: red; } —— 这本身没错,但一旦顺序反了(比如 hover 规则在前),且没加 !important,就可能被后续普通状态覆盖。CSS 优先级相同的情况下,后声明的规则生效,所以 :hover 必须紧跟在对应元素的基础样式块之后,或至少确保它在样式表中处于更靠后的位置。
更稳妥的做法是把 hover 和常态写在一起:
.card {
background: #f9f9f9;
transition: background 0.2s;
}
.card:hover {
background: #eef2ff;
}- 避免拆成两段定义后忘记顺序
- transition 必须写在常态里,hover 中只改触发值,否则鼠标移入瞬间会“跳”
- 如果用 CSS-in-JS 或模块化方案(如 CSS Modules),确保
:hover和基础类名在同一个作用域内
hover 配合 transform 和 opacity 最安全
用 transform 和 opacity 做 hover 动画,性能远好于改 width、height、left、top 这类触发布局重排(reflow)的属性。浏览器对这两者做了硬件加速优化,动画更顺滑,尤其在移动端。
-
transform: scale(1.05)比width: 110%更推荐 -
opacity: 0.8可以替代background: rgba(0,0,0,0.2)(后者可能触发重绘) - 慎用
margin或padding动画:会挤压邻近元素,造成意外位移
伪类组合要小心层级和可访问性
:hover 和 :focus 经常一起用,但写法不对会导致键盘用户无法看到焦点样式。比如只写 a:hover,不写 a:focus,Tab 切换时链接就没高亮。
立即学习“前端免费学习笔记(深入)”;
- 推荐统一写法:
a:hover, a:focus { outline: 2px solid #007bff; } - 不要写
a:hover:focus—— 这表示“同时悬停又聚焦”,实际几乎不会发生 - 移动端没有 hover,
:hover在 iOS Safari 上只在点击后短暂触发一次,不能依赖它做核心交互反馈 - 如果用
:not(:hover)控制显示隐藏,记得给屏幕阅读器加aria-hidden同步逻辑
hover 不生效?先查这三件事
常见 hover 失效不是语法错,而是环境或结构问题:
- 父元素有
pointer-events: none—— 子元素 hover 全部失效,包括按钮、链接 - 目标元素被其他元素(比如空的
div或遮罩层)盖住,z-index 或 position 导致鼠标根本没碰到它 - 用了
display: none或visibility: hidden的父容器,子元素即使写了 hover 也无意义
调试时临时加一句 * { outline: 1px solid red !important; },能快速看出鼠标到底落在哪个元素上。
hover 看似简单,真正难的是在复杂布局、响应式断点、无障碍要求和性能约束下,让交互既自然又可靠。别只盯着动画效果,先确保它在各种设备和操作方式下都能被用户“触达”。










