How we choose typography for a website
How to choose typography for a website: readability, variable fonts, self-hosting, font-display and font pairing, with concrete criteria.
Before we open a font catalog we ask a duller question first: what does this text actually need to do? A headline has to sell, a paragraph has to read comfortably, a data point has to stand apart from everything around it. Only then do we go looking for type. And on the web there’s a second question that matters just as much: how that font gets to the browser without slowing the page down.
Function first, family second
Each kind of text has a different job, and that defines what to look for.
- Headlines (display). Few words, large size. There’s room for character here: strong shapes, extreme weights, condensed or expanded widths.
- Body text. Many words, small size. It needs to disappear: if someone notices the typeface while reading, something’s off.
- Data and code. Prices, dates, metrics, technical snippets. They need to stand apart from the rest and line up cleanly in columns.
Readability before personality
What we check in any typeface meant for body text:
- A generous x-height. Lowercase letters that are tall relative to the capitals read better at small sizes and on low-density screens.
- Shapes that don’t get confused. The quick test: type
Il1andO0. If you can’t tell them apart, the font will cause trouble in emails, codes and prices. - Full language support. For a site that also runs in Spanish: accents, ñ, and properly drawn
¿and¡, not afterthoughts. - Tabular figures available. So the numbers in a pricing table line up.
- Enough weights. At minimum a real regular and a real bold, not ones faked by the browser.
And the typesetting values we start from:
| Parameter | Starting point |
|---|---|
| Body size | 16 px minimum; often 17 or 18 px |
| Body line height | Between 1.5 and 1.7 |
| Heading line height | Between 1.0 and 1.2 |
| Line length | Between 45 and 75 characters |
| Text contrast | 4.5:1 minimum (level AA) |
We set sizes in relative units (rem) and, for headings, with clamp(), which lets the size scale with the viewport between a minimum and a maximum. That way the text respects the font size each person has set in their browser.
Two families, at most
One for display, one for running text. A third, monospaced, only if there’s data or code to show. Beyond that, the site starts reading like a collage.
How we pair them
- Clear contrast, or none. Two nearly identical sans serifs look like a mistake. Either they share a structure and differ in one obvious trait (width, weight), or they’re plainly different.
- Compatible proportions. Similar x-heights let two families sit on the same line without one looking smaller.
- One lead. If the display face has a lot of character, the text face needs to stay quiet.
This site is an example: Archivo for headlines, making use of its width axis; Instrument Sans for running text; and JetBrains Mono for labels and data. Three families, three jobs that don’t overlap.
Variable fonts: one file, many weights
A traditional font needs one file per style: regular, medium, bold, each with its italic. A variable font packs a whole continuous range into a single file, through axes like weight (wght), width (wdth) or slant.
We prefer them when a design uses three or more weights of the same family: one variable file usually weighs less than the static files combined, and it’s a single download. They also allow in-between values (a weight of 550, say) and let you animate weight or width without switching files.
If the design uses a single weight, a static file can be lighter. We measure case by case.
Self-hosting: fonts on your own domain
We serve fonts from the site’s own domain, not from an external service. Three reasons:
- Performance. It avoids a connection to another server. And the old argument that “visitors already have it cached from another site” no longer holds: modern browsers partition their cache by site.
- Privacy. Loading a font from a third party sends that third party every visitor’s IP address. In 2022, a Munich court ruled against a website precisely for loading Google Fonts remotely without consent.
- Control. The font doesn’t change or disappear because of someone else’s decision.
To do it well: WOFF2 format, files subset to the characters the site actually uses (for English and Spanish, the Latin subset is enough), and a license check. Fonts under the open OFL license can be self-hosted at no cost; commercial ones usually come with a separate web license.
font-display and the text jump
While the font downloads, the browser has to decide what to show. That’s controlled with font-display:
swap: shows text right away in a fallback font and replaces it when the real one arrives. Content is readable from the first moment, but the swap can shift the text.optional: if the font doesn’t arrive almost immediately, the browser sticks with the fallback for that visit. Zero jumps, at the price of some first-time visitors seeing a different typeface.block: hides the text while it waits. We avoid it.
That shift when the font swaps counts toward CLS, one of the metrics we cover in Core Web Vitals explained. We reduce it two ways: preloading only the fonts used on the first screen, and tuning the fallback font with size-adjust and ascent-override so it takes up nearly the same space as the final one.
The real test
Before we call a typeface chosen, we test it with real content, not filler:
- A long paragraph on a phone, in direct sunlight if possible.
- The longest headline on the site, and the shortest.
- A table with numbers.
- Both language versions, if the site is bilingual. Spanish copy tends to run longer than English, and a headline that fits in one language can break in the other.
- Light and dark themes: on a dark background, thin weights look even thinner.
If a long paragraph reads without tiring anyone and a headline is recognizable from a distance, the type is doing its job. Everything else is taste, and taste doesn’t need a debate.
Next step
Typography is one of the decisions we make in the design stage of our process, and it’s part of every custom web development project: identity isn’t picked from a catalog, it’s designed. If your current site is hard to read or slow to show its text, we also review that in our performance and technical SEO audits.