unicode-range 是 @font-face 中指定字符范围的描述符,能实现按字符集匹配字体,但不自动分文件下载;真正按需加载需拆分为多个独立 font-family 的 @font-face 声明并配不重叠的 unicode-range,如英文 u+0020-007f、中文 u+4e00-9fff,并在 font-family 列表中按优先级排序。

unicode-range 是什么,它真能按字符集加载字体?
能,但限制很明确:unicode-range 只在 @font-face 规则中生效,且仅控制「该字体是否参与该字符的渲染匹配」,不触发单独的字体文件下载。也就是说,浏览器仍会下载整个字体文件(除非你提前把中文字体和英文字体拆成两个独立的 @font-face 声明,并各自配 unicode-range),但它会知道“这个字只用这个字体渲染”。
常见误解是以为加了 unicode-range 就自动懒加载或按需请求——不是。真正实现“分别加载”,靠的是把中英字体拆成两个独立的 @font-face,再用 unicode-range 划定各自负责的码点范围。
- 英文常用范围:
U+0020-007F(ASCII 基本拉丁)、U+0080-00FF(Latin-1 Supplement) - 简体中文常用范围:
U+4E00-9FFF(CJK Unified Ideographs) - 别漏掉空格、标点、数字:它们大多落在
U+0020-007F,必须包含,否则英文段落里中文标点可能 fallback 失败
如何写两个 @font-face 并正确配 unicode-range?
关键不是写对范围,而是让浏览器能「优先匹配」对应字体。顺序很重要:把更窄、更具体的 @font-face 放前面,避免被宽泛的声明覆盖。
@font-face {
font-family: 'Inter';
src: url('inter.woff2') format('woff2');
unicode-range: U+0020-007F, U+0080-00FF, U+0100-017F, U+0180-024F;
}
@font-face {
font-family: 'Noto Sans SC';
src: url('noto-sc.woff2') format('woff2');
unicode-range: U+4E00-9FFF, U+3400-4DBF, U+20000-2A6DF, U+2A700-2B73F;
}
注意点:
-
unicode-range值之间用逗号分隔,不能用空格或换行连接 - 中文范围推荐至少包含
U+4E00-9FFF(常用汉字)+U+3400-4DBF(扩展 A);如果要支持生僻字或古籍,才加后面的扩展区 - 英文字体不要写
U+0000-FFFF这种全范围——它会吃掉所有字符,导致中文根本不会匹配到中文字体
font-family fallback 链怎么写才不踩坑?
写了 @font-face 不等于字体就自动生效。你得在 font-family 里显式列出它们,且顺序决定匹配优先级:
body {
font-family: 'Inter', 'Noto Sans SC', system-ui, sans-serif;
}
这里的关键逻辑是:
- 浏览器逐个检查每个字体是否支持当前字符
- 先查
'Inter':它只声明了拉丁字母等范围,遇到汉字直接跳过 - 再查
'Noto Sans SC':它声明了中文范围,匹配成功 - 如果两个字体都声明了重叠范围(比如都写了
U+0020-007F),浏览器选列表里靠前的那个
常见错误是把中文字体放前面:font-family: 'Noto Sans SC', 'Inter', ... ——这样所有英文字符也会先尝试用 Noto 渲染,白白浪费性能,还可能因字重/字宽不一致导致排版跳动。
实际加载效果怎么验证?
别只看 DevTools 的 Network 标签——它显示的是字体文件是否被请求,而不是“哪个字符用了哪个字体”。真正要看的是:
- 打开 Chrome DevTools → Elements → 选中一段文字 → 右侧 Styles 面板下拉到底,找 Computed 标签页 → 展开
font-family,能看到实际生效的字体名 - 更直接:选中单个汉字,右键 → Inspect,再看 Computed 中的
font-family;再选一个英文字母对比 - 用
getComputedStyle(el).fontFamily在 Console 里查,但注意它返回的是最终解析后的字体族名(如"Inter", "Noto Sans SC"),不是当前字符实际使用的那个
容易被忽略的是:如果页面初始 HTML 里只有英文,中文字体文件可能延迟加载(直到首次渲染中文时才触发),这是正常行为;但如果你在首屏就混排中英文,务必确保两个字体都已预加载(用 <link rel="preload" as="font">)。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











