问题1:字体文件过大,解决方案:Fontmin - 字体子集化
介绍 Fontmin是一个纯JS字体子集化方案,用于压缩字体文件。
依赖node环境。
其原理是扫描项目中的文字,将用到的字从字体文件中单独拿出来组成一个子集字体文件。
可以达到大幅度减小字体文件尺寸的效果。
相关资源
安装 1 npm install --save-dev fontmin
使用 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 const fs = require("fs"); const Fontmin = require("fontmin"); //扫描文件目录 const scanFolder = (dir, done) => { let results = []; fs.readdir(dir, (err, list) => { if (err) { return done(err); } let i = 0; (function iter() { let file = list[i++]; if (!file) { return done(null, results); } file = dir + "/" + file; fs.stat(file, (err, stat) => { if (stat && stat.isDirectory()) { scanFolder(file, (err, res) => { results = results.concat(res); iter(); }); } else { results.push(file); iter(); } }); })(); }); }; //Fontmin根据文字内容生成压缩后的字体子集 const generateFinalHTML = (finalString) => { const fontmin = new Fontmin() .src('static/fonts/*.ttf') // 需要压缩的所有字体文件 .dest('static/fonts/') // 压缩后文件存储路径 .use( Fontmin.glyph({ text: finalString, hinting: false, }) ) .use( Fontmin.ttf2woff({ deflate: true, }) ); fontmin.run((err) => { if (err) { throw err; } }); }; //获取目录下所有文件的文字内容 scanFolder("dist", (n, results) => { let set = new Set(); results.forEach((file) => { const result = fs.readFileSync(file, "utf8"); const currentSet = new Set(result); set = new Set([...set, ...currentSet]); }); generateFinalHTML(Array.from(set).join("")); });
问题2:FOIT(Flash of Invisible Text )字体闪现问题 问题描述 浏览器在加载字体时,默认不展示文本内容,在现代浏览器中,FOIT会导致这种现象出现至多3秒。
如果有文字混搭(有的字体需要加载,有的字体不需要)那么用户可能就会发现“网页只显示部分字体”的情况,用户体验很差。
解决步骤1:font-display:swap
:未加载到字体时,优先显示替代字体,而不是空白(MDN文档 )。 font-display
属性决定了一个@font-face在不同的下载时间和可用时间下是如何展示的。
1 2 3 4 5 6 7 8 @ font-face { font-family: ExampleFont; src: url(/path/to/fonts/examplefont.woff)format('woff' ), url(/path/to/fonts/examplefont.eot)format('eot' ); font-weight: 400 ; font-style: normal; font-display: fallback; }
解决步骤2:preload
:预加载字体文件,提前加载字体。 1 <link rel="preload" type="font/woff" href="/fonturl" as ="font" crossorigin="true" >
解决步骤3:document.fonts.ready
接口 :浏览器处理完成字体加载后的回调(加载成功或者失败都会触发回调) 1 2 3 4 document .fonts.ready.then(() => { this .fontLoaded = true })