最稳妥纯CSS光标实现是用border-right-color在transparent与currentColor间硬切,配steps(1,jump-end)瞬时切换,禁用opacity防拖影;须设white-space:nowrap、overflow:hidden,并关闭连字font-variant-ligatures:none确保对齐。

用 animation + border-right 模拟光标最稳妥
纯 CSS 实现打字机光标,核心是让一个竖线在文本末尾「闪烁」,而不是真去控制字符逐个出现。最可靠的方式是用 border-right 伪造光标,再配合 @keyframes 控制显隐。它不依赖 JS、兼容性好(IE10+)、不会干扰文本选中或复制。
常见错误是直接对 content 或伪元素做 opacity 动画——这容易导致布局抖动或光标位置偏移。而 border-right 是内联尺寸的一部分,天然贴合文字 baseline。
- 给目标元素设
border-right: 2px solid #000,宽度和颜色按需调整 - 用
animation: blink 1s step-end infinite,step-end能避免淡入淡出,实现硬切换 - 必须加
white-space: nowrap和overflow: hidden,否则光标可能被截断或换行 - 若文本本身有动画(如逐字显示),光标需放在同一容器内,且
animation-delay要同步起始时机
用 ::after 伪元素更灵活但要注意定位
当需要光标独立于文本内容(比如动态替换文案、支持多行)时,::after 是更好的选择。它能脱离文本流控制,也方便叠加阴影或渐变效果。
关键难点在于精准对齐:光标必须紧贴最后一字符右侧,且随字体大小、行高自动适配。硬写 left: 100% 在不同字体下会漂移。
立即学习“前端免费学习笔记(深入)”;
- 给父容器设
position: relative,::after设position: absolute; right: 0; top: 50%; transform: translateY(-50%) -
width推荐用em单位(如0.08em),比px更适应字号缩放 - 避免用
content: "|"—— 字符宽度受字体影响大,且可能被连字规则干扰;坚持用background-color或border - 如果父容器有
padding-right,伪元素要额外减去该值,否则光标会悬空
遇到 font-variant-ligatures 或连字时光标错位怎么办
某些字体(如 SF Pro、Inter)开启连字后,像 fi、fl 会被渲染成单个字形,此时光标若插在 f 和 i 之间,视觉上就卡在字形中间,明显偏左。
这不是 CSS 能直接修正的——浏览器不暴露连字后的实际字形边界。唯一可控的解法是从源头规避。
- 对需要光标的文本容器强制关闭连字:
font-variant-ligatures: none - 或换用不触发常见连字的字体组合,比如
font-family: "SFMono-Regular", Consolas, monospace - 若必须保留连字,可改用「块状光标」:把
border-right换成box-shadow: 2px 0 0 #000,视觉误差相对不那么刺眼
移动端 Safari 上光标动画卡顿或消失
iOS 15+ 的 Safari 对 animation 的硬件加速策略变了,尤其当光标元素有 transform 或透明度变化时,容易触发合成层丢帧,表现为闪烁不均匀甚至暂停。
这不是 bug,而是 Safari 主动降级了非视口内动画的优先级。解决思路是减少合成条件,同时确保动画属性可被 GPU 直接处理。
- 禁用
opacity动画,只用border-color切换(如#000 → transparent) - 避免在光标元素上写
will-change,Safari 对它的处理反而更保守 - 如果页面有大量同类光标,用
animation-play-state: paused控制非激活状态,滚动进视口再play - 测试时务必真机连接 Web Inspector,模拟器的渲染行为和真机差异很大


















