@media 专用于全局布局响应,不适用于组件内部;@container 才是真正的容器查询工具,需显式设置 container-type 且容器必须有明确尺寸,否则无效。

@media 适合调页面整体布局,不是组件内部响应的工具
媒体查询只看 window.innerWidth,不关心组件在哪儿、多宽。一个写死 @media (min-width: 768px) 的卡片,放进宽度仅 300px 的侧边栏里,照样按桌面样式渲染——文字溢出、图片错位、flex 布局崩掉。这不是 bug,是设计定位决定的:它本就该管全局断点,比如导航栏折叠、页脚堆叠、主内容区栅格列数切换。
常见误用场景包括:
- 在 React/Vue 组件 CSS 文件里大量写
@media模拟“组件自适应” - 为同一个组件在不同位置配多套
@media断点(比如首页 vs 弹窗),导致样式重复、维护成本飙升 - 依赖
vw单位假装“相对容器”,但实际还是绑定视口,嵌套后完全失准
@container 必须显式声明 container-type 才生效
浏览器默认不把任何元素当容器,漏设 container-type,@container 规则会被静默忽略,控制台零报错——这是卡住最多人的第一步。
关键实操点:
-
container-type: inline-size最常用,只监听宽度变化,性能开销小;container-type: size同时监听宽高,触发更频繁重排,慎用 - 别对
display: contents或position: absolute的父元素设容器——它们不产生块格式化上下文,container-type直接失效 -
container: <name> / inline-size</name>是简写,命名非必需;没命名时直接写@container (min-width: 400px)即可,无需@container <name></name>
子代选择器 > 在 @container 里容易失效
@container 不改变 CSS 选择器逻辑,.card > .title 仍按 DOM 树匹配直系父子关系。如果框架把内容插入到中间层(比如 .card > .card__body > .title),> 就断了。
更稳妥的做法:
- 锚定容器自身,例如
.card > .title改成.card .title(后代选择器) - 确认真实 DOM 结构,必要时加中间类名,如
.card .card__body .title - 避免在 Shadow DOM 或动态挂载区域用
>,兼容性差且调试困难
兼容性现状:Chrome/Firefox 稳了,Safari 仍要小心命名
Chrome 110+、Firefox 119+ 已稳定支持,Safari 16.4+ 开始支持,但存在一个隐藏坑:container-name 在部分场景下解析失败——比如命名容器嵌套、或与某些 Flex/Grid 组合时。
建议策略:
- 优先用匿名容器 +
container-type组合,绕过命名相关 bug - 降级方案别堆 JS:多数展示型组件直接 fallback 到固定布局更稳;核心交互组件才考虑
ResizeObserver+ class 切换 -
@container规则被不支持的浏览器静默丢弃,无需@supports包裹,但别指望 PostCSS 插件(如postcss-container-queries)能可靠转译
最常被忽略的前提:容器本身得有明确尺寸。没有 width、max-width、flex-basis 或 Grid 约束的元素,container-type 设了也白设——首次渲染时无尺寸信息,@container 不会触发。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











