学会 aspect-ratio,你就能用一行 CSS 干掉过去那套「padding-top 百分比 + 绝对定位」的宽高比黑科技,让图片、视频、卡片在任何屏幕宽度下都保持比例、不再抖动。
第一步:先搞清楚它替代了什么
在 aspect-ratio 出现之前,前端想要一个「宽度自适应、高度按比例」的盒子,标准写法是这样:
.ratio-16x9 {
position: relative;
height: 0;
padding-top: 56.25%; /* 9 ÷ 16 × 100% */
}
.ratio-16x9 > * {
position: absolute;
inset: 0;
}
痛点有三个:比例要自己算成百分比、子元素必须绝对定位、父容器不能有内容高度。aspect-ratio 把这三点一次性解决。
第二步:基本语法
.box {
aspect-ratio: 16 / 9;
}
- 值就是「宽 / 高」,中间斜杠两侧推荐写空格,
16/9 虽然合法,但在某些压缩或预处理器环节容易被误当成除法,写空格最稳。
- 只写一个数字时等价于「n / 1」,所以
aspect-ratio: 1 就是正方形。
- 默认值是
auto,也就是不生效。
第三步:理解它到底怎么算尺寸
这是最容易搞混的地方,记住三条规则:
- 只设了宽度(或宽度由父级/网格决定):高度按比例自动算出来。
- 只设了高度:宽度按比例反推。
- 宽度和高度都设了:aspect-ratio 被忽略,因为你已经手动定死了。
也就是说,aspect-ratio 是「首选比例」而不是「强制比例」。如果你后续又给元素加了 min-height、max-height 或者里面塞了更高的内容,它会让步。
还有一个组合写法值得记:
img {
width: 100%;
height: auto;
aspect-ratio: auto 16 / 9;
}
auto 16 / 9 的意思是:元素自身有内在比例(图片、视频自带)时优先用自身的,没有时才用 16 / 9 兜底。这样图片不会被硬拉成 16:9 变形。
第四步:四个高频场景
1. 响应式视频 / iframe 容器
.video {
width: 100%;
aspect-ratio: 16 / 9;
background: #000;
}
.video iframe {
width: 100%;
height: 100%;
display: block;
border: 0;
}
2. 图片卡片网格,高度统一不塌陷
.grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
gap: 12px;
}
.grid .cover {
width: 100%;
aspect-ratio: 4 / 3;
object-fit: cover;
}
3. 正方形头像
.avatar {
width: 48px;
aspect-ratio: 1;
border-radius: 50%;
object-fit: cover;
}
4. 为图片预留空间,消除加载抖动(CLS)
img 标签写上 width / height 属性,再用 height: auto 配合,浏览器在图片下载完成前就能按比例占好位置,页面不会跳。
注意:给 img 同时写了 width: 100% 和 height: 100%,图片会被拉伸变形,务必配上 object-fit: cover 或 contain。
注意:aspect-ratio 对 display: inline 的元素无效,必须是能设置宽高的盒子(block、inline-block、flex/grid 子项等)。
注意:在 flex 布局里,子项默认 min-height: auto,内容会把比例撑破。遇到这种情况加上 min-height: 0 和 overflow: hidden。
第五步:兼容与降级
aspect-ratio 在 Chrome 88、Firefox 89、Safari 15 起支持,2021 年之后的浏览器基本全绿。如果你的项目还要照顾更老的设备,用 @supports 做渐进增强:
/* 老方案打底 */
.box { position: relative; height: 0; padding-top: 56.25%; }
.box > * { position: absolute; inset: 0; }
/* 支持的浏览器覆盖掉 */
@supports (aspect-ratio: 1 / 1) {
.box {
height: auto;
padding-top: 0;
aspect-ratio: 16 / 9;
}
.box > * { position: static; }
}
注意:降级时一定要把 height: 0、padding-top、子元素的绝对定位一起复位,只改 aspect-ratio 是没用的,盒子会算错。
小结
aspect-ratio: 宽 / 高,斜杠两侧建议写空格,单个数字等价于 n/1。
- 它是「首选比例」:宽高都设死时不生效,min/max-height 能覆盖它。
- 图片用
aspect-ratio: auto 16 / 9 可以优先保留自身比例,避免变形。
- 视频容器、统一高度网格、头像、占位防抖动是最典型的四个用法。
- flex 子项记得加
min-height: 0;老浏览器用 @supports 做降级并完整复位旧写法。
- 以后写宽高比,先想 aspect-ratio,再考虑 padding-top 黑科技。