calc() in CSS: mixing units in a single calculation

calc() runs a calculation directly inside a CSS value and lets you mix different units, like a percentage and pixels, in the same expression.
4 min read
Believemy logo

A sidebar that needs to fill the full height of the screen minus the height of a fixed 64-pixel header does not describe easily with a single unit: screen height is naturally a percentage, header height naturally pixels. Writing a value that combines both directly in CSS was impossible before calc() came along.

The function solves exactly that problem: it lets the browser do the arithmetic itself, at the moment it renders the page, with units that have nothing in common to start with.


Definition

calc() is a CSS function that accepts a mathematical expression and returns the result as a property value. It can mix different units within the same expression, something no other CSS syntax allows.

CSS
.sidebar {
  height: calc(100vh - 64px);
}

The calculation does not happen when the CSS is written, but when the browser actually renders the page, which lets it react if the window is resized: 100vh recalculates on every resize, and the subtraction against the fixed 64px follows automatically.


Operators and the spacing trap

The four available operators are +, -, * and /, but they do not all follow the same spacing rule.

OperatorSpace around it
+ and -Required on both sides
* and /Optional, but recommended for readability
CSS
width: calc(100% - 40px); /* correct */
width: calc(100% -40px); /* invalid, ignored by the browser */
width: calc(100%-40px); /* invalid too */
width: calc(100% - 40px * 2); /* correct, space around * is optional */
Good to knowWithout a space around -, the browser can no longer tell whether it is reading a subtraction or a single negative number glued to the previous term: the specification errs on the side of safety and rejects the whole expression rather than guess. The property using it then gets ignored as if calc() had never been written.


Nesting calc() and combining it with variables

A calc() expression can contain another one, and can use a CSS custom property just like any other number, which makes it possible to build a consistent spacing scale from a single base value.

CSS
:root {
  --unit: 8px;
}

.card {
  padding: calc(var(--unit) * 2);
  margin-bottom: calc(var(--unit) * 3 + 4px);
}


Where calc() is accepted

The function works anywhere a length, percentage, number, angle or duration is expected: widths, margins, grid-template-columns, transform, transition-duration. It makes no sense, on the other hand, on a value that is not numeric, such as display: flex or a named colour keyword.


A concrete example: a fixed-width sidebar

A two-column layout, where the sidebar always keeps 280 pixels and the main content fills the rest of the screen, shows off nicely why mixing units in one calculation beats fixing a width to an approximate percentage.

CSS
.main-content {
  width: calc(100% - 280px);
}

If the sidebar's width changes one day, only that single number inside the calc() expression needs updating for the main content to adjust automatically, with no percentage to recompute by hand.


Frequently asked questions

QuestionCan several calc() be nested inside each other?

Yes, a calc() expression can contain another calc() expression, even though it is almost never needed in practice: ordinary parentheses inside a single calc() already group operations perfectly well.

QuestionWhy does calc(100% -20px) fail while calc(100% - 20px) works?

Because without a space, the browser can no longer tell a subtraction's minus sign apart from a negative number's minus sign glued to the previous term. The CSS rule requires a space on both sides of + and - precisely to remove that ambiguity.

QuestionCan calc() be used to compute a colour?

Not directly on a named or hexadecimal colour, but yes on an individual channel inside a notation like hsl(), for instance to lighten a hue by computing its lightness from a CSS custom property.

Related terms

Discover our hTML and CSS glossary

Browse the terms and definitions most commonly used in HTML and CSS development.

Share this article

Want to help us? Share this article on your networks or even better: on your site, in an article or in your newsletter.