必须修改 .navbar-collapse.show 的 transition 和 max-height 属性才生效,因动画纯由 css 的 max-height 过渡控制;需同步增大 max-height(如 120vh)并设 transition: max-height 0.8s ease-in-out !important,避免内容截断或跳变。

直接改 .navbar-collapse.show 的 transition 值才生效
Navbar 移动端菜单的展开动画不是靠 JavaScript 控制,也不是 data-bs-toggle 触发的 JS 逻辑在管速度——它纯靠 CSS 的 max-height 过渡。Bootstrap 5.3+ 把这个过渡写在 CSS 变量 --bs-navbar-collapse-transition 里,但变量只用于内部引用,**你不能靠改变量来覆盖**。必须显式重写 .navbar-collapse.show 的 transition 声明,且加 !important 确保压过默认样式。
- 错误做法:只改
.navbar-collapse基础态,或只调data-bs-*属性 - 正确位置:自定义 CSS 文件必须放在 Bootstrap CSS 之后 加载
- 必须锁定
.navbar-collapse.show,因为收起时max-height: 0,动画全靠这个类触发
max-height 和 transition-duration 必须同步调
把动画从 0.35s 改成 0.8s 后菜单只显示前两行?这不是动画出错,是 max-height 终点值没跟着变大。浏览器对慢速过渡更严格:它会按你写的 max-height 值精确渲染高度,而 Bootstrap 默认的终点值(比如 300px 或 1000px)是固定估算的,不随动画时长动态调整。
- 不能用
max-height: none—— 它不参与 transition,动画会立即跳到展开态 - 避免
max-height: 100%或fit-content—— 这些值无法作为 transition 的合法终点,浏览器会退回到0 - 推荐写法:
.navbar-collapse.show { max-height: 120vh !important; transition: max-height 0.8s ease-in-out !important; } - 精简菜单(≤5 项)可写死像素值:
max-height: 240px,更轻量,减少低端机重排卡顿
别让 dropdown 搞乱动画节奏
折叠菜单里嵌了 .dropdown,点开二级菜单时出现“先展开、再突然撑高”或“动画中途跳一下”,根本原因是 .dropdown-menu 默认 position: absolute,不占 .navbar-collapse 高度,但它的父容器(如 .nav-item)若有 padding-block 或 min-height,视觉上“变高”却没被 max-height 涵盖。
- 给
.nav-item去掉min-height,改用padding-block: 0.5rem控制间距 - 在
.navbar-collapse.show上加padding-bottom: 1rem预留空间,而非依赖自动撑开 - 真要让下拉菜单随文档流撑高:加
.navbar-collapse.show .dropdown-menu { position: static !important; } - 排查是否在
@media (max-width: 991.98px)下误写了.dropdown-menu { top: 100% }—— 移动端折叠态不需要这个
动画曲线选 ease-in-out,别碰 linear
移动端手感关键在缓动函数。ease-in-out 比默认的 ease-in 更平滑,开头不突兀、结尾不生硬;linear 在小屏上会显得机械甚至“卡”,尤其配合慢速过渡时更明显。
- 慎用
cubic-bezier(0.34, 1.56, 0.64, 1)—— 它在某些安卓 WebView 里支持不稳定,优先保底用ease-in-out - 别同时写
top和transform动画 —— 渲染冲突会导致跳变,max-height是唯一该动的属性 - 如果用了自定义图标字体,首次展开可能因字体加载延迟导致高度估算偏小;可临时加
transition: none排查,确认后用font-display: swap优化
动画变慢后最容易被忽略的,是 max-height 终点值必须跟着放大 —— 不是“设得越大越好”,而是要匹配内容真实高度与过渡节奏。很多卡顿和截断问题,根源都在这里。











