height: auto同一份未知高度的内容做展开动画:不可插值的 auto 直接跳变,可插值的 fr 平滑生长。点击卡片单独切换,下方按钮两张一起切。
Instant height change
height: auto;Expands fluidly
grid-template-rows: 0fr → 1fr;transition 只能在可插值的值之间过渡。auto 是布局关键字而不是数值,浏览器无法算出 0 与 auto 之间的中间帧,于是忽略过渡、直接跳到最终布局。经典的 max-height hack 虽然能动,但要拍脑袋猜一个上限,猜大了缓动曲线还会被稀释失真。
.panel {
/* ❌ auto 不可插值,过渡不生效 */
height: auto;
transition: height 600ms;
}fr 是数字、天然可插值:外层 grid 的行高从 0fr 平滑长到 1fr(内容自然高度),子元素只需 min-height: 0 允许被压缩、overflow: hidden 裁掉溢出。全程零 JS、不用测量内容高度,内容再长都适用(Chrome 107+ / Safari 16+ / Firefox 66+)。
.expander {
display: grid;
/* 收起 0fr ↔ 展开 1fr ✅ */
grid-template-rows: 0fr;
transition:
grid-template-rows 600ms;
}
.expander[data-open] {
grid-template-rows: 1fr;
}
.expander > div {
min-height: 0;
overflow: hidden;
}展望:Chrome 129+ 已支持 interpolate-size: allow-keywords 与 calc-size(),可以直接对 height: auto 过渡;在此之前,grid 行高方案是兼容性最好的纯 CSS 解法。