Usually, fonts are either downloaded from a third-party source, such as Google Fonts, or from a file that is stored in the build folder.
After running the build we get a static folder that houses 2 folders: js, css.
If we downloaded some font files they will be inside a third folder: media.
We can manually download them, or download a npm package, like
@fontsource
, that inside it has the files.
The browser will then load those at its own pace, but that will probably cause a UI flicker of the default browser fonts and then the desired fonts.
For a better UI feel, we have to tell the browser to preload them.
In order to achieve that we need to add a link
tag that preloads the href
it's given:
<link
rel="preload"
href="https://fonts.gstatic.com/s/poppins/v20/pxiEyp8kv8JHgFVrJJfecnFHGPc.woff2"
as="font"
crossOrigin="anonymous"
/>
But how do I know what to put inside the href
?
For that, we need to open the network tab in the dev tools, see what the browser loads, and copy it :)
To locate the font request, choose the Font filter at the top.
If we are using React
we can add this link
tag to the index.html
(just like in Vanilla JS
) or inside our App.tsx
, but to access the head
tag from App.tsx
we'll need to use the help of the react-helmet-async
library.
All it does is insert its children to the head
tag.
And of course, instead of "dirting" our App.tsx
with more code, we can wrap it in a separate component - <PreloadFonts />
This nav bar, for example, will look like this for a split second (the gif is slowed down for a better look at the change).
But after preloading the font we get no flicker:
The same process applies to the fonts that come from a library or font files that we downloaded, the only difference is that the href
will be relative, like so:
<link
rel="preload"
href="/static/media/libre-franklin-latin-400-normal.woff2"
as="font"
type="font/woff2"
crossOrigin="anonymous"
/>
Now my question is why not all fonts are preloaded automatically if there is an evident UI flicker?!
Top comments (6)
Сongratulations 🥳! Your article hit the top posts for the week - dev.to/fruntend/top-10-posts-for-f...
Keep it up 👍
This is always a great practice 👍✨
Thanks for the article!
This is indeed a good question, but thanks to your article we at least have a good way to prevent flicker to happen.
Thanks, I just implemented this in my design system!
This is great practice but it sometimes takes more time to load fonts if the page is using multiple or multiple weight of the fonts
I solve it with
style.css
index.html