:active 伪类仅在按压瞬间生效,需配合 transition 和 cursor: pointer 才可见;持久高亮须用 js 控制类名,因 css 无法维持状态;拖拽高亮应使用 dragenter/dragleave 而非 dragover,并确保可访问性与视觉对比度。

直接给元素加 :active 伪类 + transition,再补上 cursor: pointer,就能解决 90% 的点击高亮需求;但若要“按下去就保持高亮”,必须用 JavaScript 控制类名切换,不能只靠 CSS。
为什么 :active 看起来没反应?
常见错误是只写了 :hover,或者写了 :active 但漏了 transition。:active 只在鼠标按下、手指按住的瞬间触发,松开立刻还原——它不是“选中态”,而是“正在按”的瞬时状态。没有 transition 的话,颜色或缩放变化会像闪烁一样突兀,人眼根本抓不住反馈。
- 必须给目标元素显式设置
cursor: pointer,否则用户无法判断它是否可点(尤其在移动端) -
:active不触发于键盘Enter或空格键,无障碍支持弱 - 移动端 touchstart 后如果没有
touch-action: manipulation,可能延迟或不触发:active - 示例写法:
.btn { background: #007bff; transition: background 0.12s ease, transform 0.1s ease; cursor: pointer; }<br>.btn:active { background: #0056b3; transform: scale(0.98); }
如何让高亮“按下去就留着”?
持久高亮本质是状态管理,CSS 伪类做不到,得靠 JS 切换类名。典型场景包括:单选按钮标签高亮、滑块操作后标记已响应、多步骤表单中的当前激活项。
将调研报告、方案对比、数据分析、需求梳理、会议纪要、设计说明、代码评审、学习笔记等任务产物输出为可在浏览器直接打开的单文件 HTML,替代 Markdown 作为最终交付物。Markdown 在信息密度、视觉清晰度和可分享性上已跟不上 AI 产物的丰富度,HTML 能同时承载排版、表格、SVG 等。
- HTML 结构要保证
<input type="radio">在<label></label>前面,才能用:checked + label实现纯 CSS 持久高亮 - 否则统一用 JS:监听
click或change,调用element.classList.toggle("is-active") - 注意避免重复绑定:如果模板是动态渲染的,别在每次插入后都
addEventListener,改用事件委托 - 移动端需同时监听
touchstart,并加preventDefault()防止滚动干扰
拖拽上传区域的高亮为什么一闪就没了?
根本原因是误用 dragover 控制开关——它每秒触发十几次,子元素进出都会反复触发,导致样式疯狂 toggle。真正该用的是 dragenter 和 dragleave,且 dragleave 必须判断离开目标是否还在区域内。
-
dragover事件第一行必须写event.preventDefault(),否则浏览器直接打开文件,根本进不了你的逻辑 -
dragenter中加类如is-drag-over,开启高亮 -
dragleave中不能直接删类,要用event.relatedTarget检查离开位置是否仍在当前容器内 - 拖拽区域不能是
display: none或pointer-events: none的元素,隐藏的<input type="file">接收不到事件
最易被忽略的一点:所有高亮反馈都依赖「用户能明确区分状态变化」。哪怕加了 transition,如果起始色和结束色对比度低于 4.5:1,色觉障碍用户就感知不到;如果高亮仅靠颜色变化而没辅以形状、粗细或图标变动,移动端拇指操作时也容易误判。视觉反馈不是“做了就行”,而是“让人一眼看懂发生了什么”。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!










