You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Canvas中使用@font-face自定义字体无需页面元素预加载?

如何在Canvas中直接使用未在页面元素中引用的自定义字体?

这个问题的核心原因是浏览器的字体懒加载机制:为了优化性能,浏览器只会加载那些被页面DOM元素实际使用到的字体,未被引用的字体不会主动加载,所以你在Canvas里直接调用时,字体还没加载完成,浏览器就会用系统字体替代。

你的临时方案用visibility:hidden的元素触发加载确实能生效,但确实不够优雅。这里推荐使用标准的FontFace API来主动加载字体,这才是无需依赖页面元素的最佳实践。

具体实现步骤:

  1. 创建FontFace实例:为每个自定义字体创建对应的FontFace对象,指定字体名称和资源路径
  2. 等待字体加载完成:通过load()方法加载字体,并用Promise.all确保所有字体都加载完毕
  3. 添加字体到文档:加载完成后,将字体添加到document.fonts集合中
  4. 绘制Canvas文本:确认字体加载完成后,再执行Canvas的绘制逻辑

完整代码示例:

window.onload = function() {
  // 1. 定义所有需要的自定义字体
  const fontDefinitions = [
    new FontFace('Amsterdam Graffiti', 'url("./fonts/amsterdam.ttf")'),
    new FontFace('Army Rust', 'url("./fonts/ARMY RUST.ttf")'),
    new FontFace('Badaboom BB', 'url("./fonts/BADABB__.TTF")')
  ];

  // 2. 批量加载字体,全部完成后再绘制
  Promise.all(fontDefinitions.map(font => font.load()))
    .then(loadedFonts => {
      // 3. 将加载好的字体添加到文档可用字体中
      loadedFonts.forEach(font => document.fonts.add(font));
      
      // 4. 现在可以安全地绘制Canvas文本了
      drawCanvasContent();
    })
    .catch(err => {
      console.error('字体加载失败:', err);
    });
};

function drawCanvasContent() {
  const fontprevcanvas = document.getElementById("fontprevcanvas");
  const ctx = fontprevcanvas.getContext("2d");
  
  ctx.font='28px Amsterdam Graffiti';
  ctx.textAlign = "center";
  ctx.fillText('test1', 40, 40);
  
  ctx.font='28px Army Rust';
  ctx.textAlign = "center";
  ctx.fillText('test2', 40, 80);
  
  ctx.font='28px Badaboom BB';
  ctx.textAlign = "center";
  ctx.fillText('test3', 40, 120);
}

为什么这个方法更好?

  • 主动可控:完全不需要依赖任何DOM元素,直接通过API主动加载字体
  • 时机精准:通过Promise确保所有字体加载完成后再绘制,彻底避免字体未就绪导致的 fallback
  • 标准规范:FontFace是W3C标准API,现代主流浏览器(Chrome 66+、Firefox 58+、Safari 12.1+、Edge 79+)都支持
  • 错误处理:可以通过catch捕获字体加载失败的情况,方便排查问题

如果需要兼容更旧的浏览器,可以结合document.fonts.ready事件(它会在所有文档字体加载完成后触发),但优先推荐FontFace API,因为它的灵活性和可控性更强。

内容的提问来源于stack exchange,提问作者L777

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 09:07:54