How to Use This Tool
Type a pixel value or a rem value and the others follow. The nesting panel shows the behaviour that makes the choice matter.
What each unit is relative to
- px — an absolute CSS pixel. Fixed, and ignores the user's browser font setting.
- rem — the root element's font size. Usually 16px unless the user has changed it.
- em — the parent element's font size, so it compounds with nesting.
- % — for font-size, identical to em with different syntax. 90% and 0.9em are the same thing.
The compounding
Because em looks at its parent, nested em values multiply. Four levels each at 0.9em, starting from 16px, gives 14.40, 12.96, 11.66 and 10.50 pixels. The same four levels at 0.9rem give 14.40 every time.
This is the practical reason rem became the default for type. A card component styled in em is a different size depending on what it happens to be inside, and nobody notices until it appears in two places at once.
The reason that is not about maths
Users can change their browser's default font size, and some do because they need to. Anything sized in
rem scales with that setting. Anything sized in px does not.
So sizing body text in pixels silently overrides a preference someone set deliberately, and they cannot fix it from their end. This is the strongest argument for rem and it has nothing to do with nesting.
The 62.5% trick, and why to skip it
An old technique sets html { font-size: 62.5% } so that 1rem equals 10px and the mental
arithmetic gets easier. It works, and it has a cost: it overrides the user's chosen font size with a
proportion of it, and any component or third-party stylesheet assuming a 16px root now renders small.
Modern editors show the pixel equivalent of a rem value on hover, which removes the only problem the trick solved. Leave the root alone.
Where em is still right
em is the better unit whenever a value should scale with this element's own text rather than with the page:
- Padding inside a button, so a large button gets proportionally more padding.
- Letter spacing and text indent, which are properties of the type.
- Border radius on a text-sized component, for the same reason.
A useful rule: rem for anything that should match the page, em for anything that should match the element. Media queries are a separate case — they ignore the root font size and use the browser default regardless, so em and rem behave identically there.
