必须用 translate-x-full 而非 translate-x-[-100%],因百分比依赖父宽而 fixed 定位下父宽常未定义,导致偏移不准;100vw 是视口单位更可靠,且需配合 peer-checked、fixed 定位与显式 transition 才能稳定运行。

直接用 translate-x-full + peer-checked + 固定定位就能跑通,别碰 left、hidden 或 JS 控制显隐——动画卡、层级乱、移动端点不关闭。
为什么必须用 translate-x-full 而不是 translate-x-[-100%]
百分比值依赖父容器宽度计算,而侧边栏通常是 position: fixed,父容器往往没设宽,导致偏移不准;100vw 是视口单位,更可靠。Tailwind 的 translate-x-full 编译为 transform: translateX(100%),但实际生效仍受上下文影响。右抽屉推荐显式写 translate-x-[100vw](方括号绕过预设限制),左抽屉用 -translate-x-[100vw]。
- 初始隐藏状态:右抽屉加
translate-x-full,左抽屉加-translate-x-full - 打开状态统一用
translate-x-0,别写translate-x-[0px]——后者不触发硬件加速 - 如果用了
sm:translate-x-full响应式类,记得在桌面断点里覆盖掉:@media (min-width: 640px) { .sidebar { transform: translateX(0); transition: none; } }
peer 结构必须严格满足“同级、相邻、前置”
peer 不是魔法,它只对紧邻的兄弟元素生效。侧边栏要响应汉堡按钮点击,结构顺序必须是:<input> → <button> → <aside>,三者平级且 <input> 在最前。
-
<input>必须带id,<button>的for属性必须精确匹配该id - 不能把
<input>放进<button>内部,也不能嵌套在<label>里——这会让peer-checked完全失效 -
<input>需用sr-only(而非hidden或display: none)隐藏,否则屏幕阅读器无法识别其状态
过渡动画必须显式声明 transition-transform 和初始 transform
只写 transition-transform 不生效——浏览器需要明确的起始 transform 才能插值。哪怕初始是 translate-x-0,也得显式写出,不能靠继承或默认值。
立即学习“前端免费学习笔记(深入)”;
- 侧边栏容器必须带初始位移类,例如:
fixed top-0 left-0 h-screen w-64 -translate-x-full transition-transform duration-300 ease-in-out - 别只写
transition或transition-all:transition默认包含所有属性,transition-all会意外过渡opacity或scale,拖慢性能 - 动画曲线建议用
ease-in-out或自定义cubic-bezier(.25,.46,.45,.94),比linear更自然 - iOS Safari 有渲染闪动问题,可加
will-change: transform, opacity优化
桌面端必须显式重置状态,不能依赖 peer-checked
peer-checked 是纯 CSS 状态,缩放窗口从移动端切到桌面端时,<input> 仍保持勾选,侧边栏会卡在展开状态。
- 桌面端断点需强制重置样式,例如:
lg:translate-x-0 lg:static lg:inset-0 lg:z-0 - 遮罩层(overlay)必须和侧边栏同级,
z-index介于两者之间(如侧边栏z-40,遮罩z-30,主内容z-10) - 遮罩层需
width: 100vw; height: 100vh;,不留空隙;内部元素默认有pointer-events-auto,但若侧边栏内按钮点不动,需手动补上
真正难调的不是动画本身,而是 peer 的 DOM 位置约束、fixed 下的 transform 基准错乱、以及桌面端断点覆盖时漏掉的 transition: none —— 这三点漏一个,侧边栏就可能卡住、闪退或点不关闭。



















