Values and visual language

Typography

Set a readable font stack, size, line height, line length, weight, and spacing without fighting browser or user preferences.

Most of a web page is text. Get the typography right and the page already looks decent with no other styling. Here is the foundation I start from:

body {
  font-family: system-ui, sans-serif;
  font-size: 1rem;
  line-height: 1.5;
}

h1,
h2 {
  line-height: 1.1;
}

The font stack

font-family takes a list. The browser tries each font in order and uses the first one it has. system-ui is the operating system’s interface font: San Francisco on a Mac, Segoe UI on Windows, Roboto on Android. It’s already installed, so it loads instantly and looks native. sans-serif is the fallback if for some reason system-ui isn’t available.

Font size

1rem is the browser’s default, 16px unless the user changed it. I don’t set body text smaller than that. If a user set a bigger default, rem respects it.

Line height

line-height: 1.5 means each line is 1.5 times the font size. Notice there’s no unit. That’s deliberate.

A unitless line height inherits as a multiplier. Each element applies it to its own font size. A paragraph at 16px gets 24px lines, a heading at 40px gets 60px lines. Set line-height: 24px instead and the heading inherits a fixed 24px, and its lines overlap.

Body text reads best around 1.5. Headings are short and large, so they look better tighter. That’s why the second rule sets them to 1.1.

Line length

Long lines are tiring to read. Keep prose between roughly 60ch and 70ch, like we did with max-width: 65ch in the units lesson. Wide screens don’t mean wide paragraphs.

Hierarchy

Use size and font-weight to show what’s important. But keep the HTML honest. An h2 is an h2 because it’s a second-level heading, not because you wanted that size. If you need a smaller heading, style it, don’t change its level.

Web fonts

If you load a custom font, the fallback is what people see for the first moment, and forever if the download fails. Choose one with similar proportions, and load only the weights you use. Each weight is another file.

The fallback also affects layout: different fonts have different widths, so lines break differently while the font loads. Emulate a slow connection in the Network panel and watch the transition.

Let text grow

Never put text in a box with a fixed height. Translations run longer, users zoom, headlines change. Text that gets clipped is a bug you shipped. Let containers grow, and if a design only works with a short heading, the design needs work.

Try this on the course page. Replace the hero headline with one three times longer, then zoom to 200%. Then, in the Styles panel, uncheck font-family to see the fallback. The page should stay readable through all of it.

Lesson completed