Web Fonts in 2021
Learn the best practices for high-performance sites using web fonts, updated for 2021.
January 13, 2021 (3y ago)
Learn the best practices for high-performance sites using web fonts, updated for 2021.
January 13, 2021 (3y ago)
Typography accounts for 95% of web design. Your font choice can be critical for branding, readability, and performance.
Over time, recommendations for using web fonts have changed as browsers adopted new standards. Now in 2021, I wanted to learn the best practices for using web fonts on high-performance sites.
The fastest way to use a web font is none. Browsers include a set of web-safe fonts (e.g. Arial, Georgia, Times New Roman) you can use by default.
Using web-safe fonts or the system font stack will be the fastest option.
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Helvetica, Arial,
sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol';
If system fonts are the fastest option, why do web fonts exist? Branding, improved design, and cross browser and device consistency. 82% of web pages for desktop use web fonts.
Let's cover five different areas for high-performance web fonts and conclude with a 2021 recommendation.
Google Fonts is responsible for 70% of all web font usage. With over 1000 fonts, they provide easy access to quality fonts, multiple formats, and performant defaults (pre-connecting and swapping).
However, Google Fonts is no longer necessary. Since 2018, Google has advised self-hosting for optimal performance through preloading.
There aren't any caching advantages anymore, either. Let's say you're using the font "Roboto", which is a popular font on Google Fonts. Chances are you've visited another site using "Roboto" and cached the font.
Since October 2020, Chrome no longer allows a shared cache across sites. Safari has worked this way since 2013. "Roboto" will be re-downloaded for every site, regardless of it being cached.
When self-hosting, ensure you cache your font with the Cache-Control
HTTP header. immutable
tells the browser the file will never change. When a request is made within the max-age
(1 year), it avoids the roundtrip to ensure it's the latest content.
Cache-Control: public, immutable, max-age=31536000
If you need Google Fonts, use these optimizations. With the latest changes in the v2 API, you can tailor fonts to specific users and platforms (including variable fonts).
The browser assigns loading priorities to different types of resources. By default, CSS will be loaded before scripts and images. You can influence the importance of resources by preloading critical assets.
Fonts are discovered late by the browser by default. By preloading, we fetch the font file as soon as possible. Then, the browser caches the font making it available immediately.
Preloading can improve performance metrics like Time to Interactive and First Contentful Paint. For example, Shopify saw a 50% (1.2 second) improvement in First Contentful Paint, removing their Flash of Invisible Text (FOIT).
As of 2020, 75% of web fonts use WOFF2. You likely only need this. For example:
<link
rel="preload"
href="/fonts/inter-var-latin.woff2"
as="font"
type="font/woff2"
crossOrigin="anonymous"
/>
Support: All modern browsers except Firefox.
font-display
allows you to modify the rendering behavior of web fonts with values such as auto
, swap
, block
, fallback
and optional
. When loading web fonts, we want to prevent layout shift. This occurs in two ways:
swap
).block
).Browsers currently have a default strategy similar to block
. The only option that eliminates layout shift is optional
. Combined with the other performance optimizations in this article, optional
is your best choice.
@font-face {
font-family: 'Inter';
font-style: normal;
font-display: optional;
src: url(/fonts/inter-var-latin.woff2) format('woff2');
}
Support: All modern browsers
Variable fonts allow us to combine multiple styles and weights (e.g. bold, italic) into a single font file.
@font-face {
font-family: 'Inter';
font-style: normal;
font-weight: 100 900; // Range of weights supported
font-display: optional;
src: url(/fonts/inter-var-latin.woff2) format('woff2');
}
You can try out different variable font options here.
Support: All modern browsers. Even Google Fonts v2 API has support for variable fonts.
Font files contain multiple languages and glyphs, which increase the file size. Subsetting is the removal of characters you don’t need.
For example, we might use the Inter variable font and subset to latin languages.
@font-face {
font-family: 'Inter';
font-style: normal;
font-weight: 100 900; // Range of weights supported
font-display: optional;
src: url(/fonts/inter-var-latin.woff2) format('woff2');
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA,
U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215,
U+FEFF, U+FFFD;
}
font-display: optional
to prevent layout shiftHere's an example of a site implementing all these recommendations.
If you need to use font-display: swap
, future support for Font Metrics Override will reduce layout shift when swapping.
@font-face {
font-family: ...;
src: ...;
ascent-override: 80%;
descent-override: 20%;
line-gap-override: 0%;
...;
}
Got a project?
© created by Abdul Malek || Made with Info