使用rel preload预加载字体

80

我正在使用以下代码片段中捕获的<link> HTML标签,将rel属性设置为preload来预加载字体;

<link rel="preload" href="fonts/32ADEO.woff2" as="font" type="font/woff2">

虽然这个方法可以加载字体,但它会导致字体被重复加载。

在Google Chrome浏览器的网络选项卡中的截图显示了字体被加载了两次 - 如下所示;

enter image description here

此外,在Google Chrome浏览器的控制台选项卡中,我收到以下警告消息;
“使用链接预加载预加载了资源https://example.com/new-v8/fonts/32A0E0.woff2,但在窗口的加载事件后的几秒钟内未被使用。 请确保它具有适当的'as'值,并且是有意预加载的。”
我做错了什么,如何解决?

当我调用disqus插件时,我收到了相同的消息:资源https://c.disquscdn.com/next/embed/styles/lounge.188f59a1df04c219bf32da7f76545092.css已经使用链接预加载,但在窗口加载事件后的几秒钟内未被使用。请确保它具有适当的“as”值,并且是有意预加载的。 - eQ19
preload 的目的是:“指定页面很快会需要的资源,你希望在浏览器的主渲染进程启动之前尽早开始加载。这确保它们更早地可用,并且不太可能阻止页面的渲染,从而提高性能。”。https://developer.mozilla.org/zh-CN/docs/Web/HTML/Preloading_content - Avatar
7个回答

49

当我尝试预加载谷歌字体时,一直收到警告。

后来发现是因为该字体从谷歌以样式形式加载,我通过设置as="style"并使用rel="stylesheet preload prefetch"解决了这个问题。

请参见以下代码示例:

<link 
 as="style"
 rel="stylesheet preload prefetch" 
 href="https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;500&display=swap" 
 type="text/css" 
 crossorigin="anonymous" />

开心编程 =)


7
<link rel="prefetch"> 在浏览器中已经得到很长时间的支持,但它的用意是为了预取在下一次导航/页面加载中将要使用的资源。 - YektaDev
这只发生在您使用Google字体而不是常规字体的情况下,我想是吗? - gaurav5430

37

71
我在我的preload的<link>标签中添加了crossorigin="anonymous",但仍然收到preload警告。 - Aaron Franke

16

我不知道是否重复了已经在这里解决的问题,但我想提醒您,需要在加载字体的源(例如CSS文件)之后放置rel="preload"链接。


这帮助我识别了我的问题。我在一个Angular应用程序中遇到了这个问题,该应用程序正在延迟加载fontawesome CSS / font,并且导致渲染延迟。 - ktsangop
不是我的问题,它之前和之后都能工作。而且没有“crossorigin”属性时,在慢速3G网络上性能提高了50%,但是有了crossorigin属性后,它变得瞬间完成,我对这个功能的表现感到震惊。 - Barbz_YHOOL
这背后的原因是什么? - gaurav5430

12
在我的情况下,在Chrome浏览器中更改为rel="stylesheet preload"即可解决问题。以下是最少量的代码,它有效<link rel="stylesheet preload" href="path/to/stylesheet" as="style" />。而无法解决的是: <link rel="preload" href="path/to/stylesheet" as="style" />

这似乎适用于CSS文件,但我猜不适用于字体文件? - gaurav5430
1
这是对我有效的解决方案。这是一个Rails应用程序,它试图从CDN加载bootstrap.css文件。 - Jack

3

我使用自己托管的字体时遇到了这个问题。我像这样预加载它:

<link rel="preload" href="/fonts/SomeFont.woff2" as="font" type="font/woff2" crossorigin>

问题在于webpack会在编译后的CSS字体路径中添加哈希值。
/* Before */
@font-face {
    font-family: "SomeFont";
    src: url("../fonts/SomeFont.woff2") format("woff2");
}

/* After (Webpack Output) */
@font-face {
    font-family: "SomeFont";
    src: url("../fonts/SomeFont.woff2?7d18a001dd0b6e04c2393") format("woff2");
}

所以我将相同的哈希添加到预加载标签中,问题解决了!
<link rel="preload" href="/fonts/SomeFont.woff2?7d18a001dd0b6e04c2393" as="font" type="font/woff2" crossorigin>

1
在 Nuxt 3 中有类似的事情。由于某种原因,在开发过程中,它会在 @font-face 规则的 src 属性中添加 /_nuxt 路径。尽管两个路径(即 @font-facesrc 版本 (/_nuxt/fonts/SomeFont.woff2) 和 <link rel="preload"> 版本(/fonts/SomeFont.woff2))都指向完全相同的文件,但浏览器似乎无法理解这一点。 - Anoesj Sadraee
你是如何在index.html文件名中添加哈希的? - Manos Kaparos
我只是复制了带哈希的文件名,并将其粘贴到index.html中。 - Staysee
使用django-compressor进行相同的操作,将Font Awesome的scss转换并使用哈希作为“缓存破坏器”。请参阅COMPRESS_CSS_HASHING_METHOD以禁用它。 - undefined

1
在我的情况下,属性的顺序很重要。例如,这个顺序是正确的。
<link rel="preload" href="/fonts/opensans-regular.woff2" as="font" type="font/woff2" crossorigin>

尽管如此,这并没有...
<link rel="preload" as="font" type="font/woff2" href="/fonts/opensans-regular.woff2" crossorigin>

如果你在typeas属性前放置href,似乎会更好。当然,别忘了在最后加上crossorigin属性!


1
我甚至更享受了这个过程。除了这个警告之外,我发现我的浏览器同时下载了woffwoff2,尽管它只应该下载woff2。改变@font-facesrc描述符的顺序帮助了我。最终,对我而言,解决方案看起来像这样:
<link href="/assets/fira-sans-condensed-v5-max-regular.woff2" rel="preload" as="font" type="font/woff2" crossorigin>
<link href="/assets/bundle.css" rel="stylesheet">

@font-face
{
    font-display: swap;
    font-family: "Fira Sans Condensed";
    font-style: normal;
    font-weight: 400;
    src: url("/assets/fira-sans-condensed-v5-max-regular.woff") format("woff");
    src: url("/assets/fira-sans-condensed-v5-max-regular.woff2") format("woff2");
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接