css变量不能用于@media条件,因媒体查询解析早于变量求值;正确做法是将断点写死在@media中,用变量传递样式值。

var(--breakpoint) 不能出现在 @media 条件里,浏览器会直接忽略整条规则——这不是 bug,是 CSS 规范明确禁止的行为。
@media 解析时机早于 CSS 变量计算
媒体查询的条件必须在样式计算前就确定真假,而 var() 是在级联(cascade)阶段才求值的,两者发生在不同生命周期。所以哪怕你写了 @media (min-width: var(--sm)),浏览器连语法校验都过不去,压根不进解析流程。
- 浏览器遇到这种写法,会静默丢弃整个
@media块 - DevTools 的 Styles 面板里根本看不到这条规则,不像其他错误还能报个 warning
- 所有主流引擎(Blink、WebKit、Gecko)行为一致,没商量余地
正确做法:用变量「承载值」,但断点逻辑仍靠硬编码或 JS
CSS 变量适合做“状态容器”,不是“动态条件生成器”。真正起作用的断点,还是得写死在 @media 里,再通过变量把值“透传”下去:
:root {
--font-size-base: 16px;
}
@media (max-width: 480px) {
:root {
--font-size-base: 14px;
}
}
.text {
font-size: var(--font-size-base);
}
- 断点数值(
480px)必须显式写出,不可替换 -
:root里重设变量,是为了让后续样式能响应变化 - 这种写法兼容性好,从 IE11(需 polyfill)到最新 Safari 都稳
容易踩的坑:以为构建工具或 JS 能绕过限制
有人试过用 PostCSS 把 var(--sm) 替换成实际像素值,这确实可行,但要注意:
- 构建时替换 ≠ 运行时响应:改了变量值,不会触发媒体查询重匹配
- JS 动态改
document.documentElement.style.setProperty('--sm', '320px')对@media毫无影响 -
matchMedia()+ JS 手动切换 class 是唯一真·运行时方案,但失去 CSS 原生的声明式优势
@media 里的断点永远得是字面量,变量只管“样式输出”,不管“何时生效”。这个分工边界一旦混淆,调试时就会卡在“为什么明明设了变量,样式就是不换”。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











