Переменные препроцессора

В препроцессорах обычно встроена математика. Например, в Sass для вычисления значения мы можем сделать следующее:

$padding: 1rem;

.element {
  padding: $padding + 2rem; /* получим значение 3rem; */
  margin-bottom: $padding * 2; /* получим значение 2rem; */ 
}

В препроцессорах математика работает с разными единицами измерения разных типов. Но как и в нативном calc(), действуют те же ограничения -  можно смешивать единицы измерения одного типа, а умножение и деление должны выполняться с числами без единиц измерения.

CSS-переменные

Помимо удивительной способности calc() смешивать единицы измерения есть ещё одна замечательная вещь - это использование ее с кастомными свойствами. Кастомные свойства могут иметь значения, которые затем используются в вычислениях, и выражаются они через css-переменные:

html {
  --spacing: 10px;
}
.box {
  padding: calc(var(--spacing) * 2);
}

Кастомные свойства также могут ссылаться друг на друга. Ниже пример, в котором используется математика сначала для вычесления самих кастомных свойств (обратите внимание на отсутствие функции calc()), а затем уже для применения их в стилизации (важно, что в конечном итоге математическое выражение должно находиться внутри calc().

html {
  --spacing: 10px;
  --spacing-L: var(--spacing) * 2;
  --spacing-XL: var(--spacing) * 3;
}
.box[data-spacing="XL"] {
  padding: calc(var(--spacing-XL));
}

Возможно, на первый взгляд кажется чем-то сложным и лишним, поскольку теперь нам нужно запомнить функцию calc(), в которой мы затем используем свойство... Но это потенциально интересно с точки зрения удобочитаемости.

Пользовательские свойства также могут быть получены из HTML, что иногда бывает чертовски круто и полезно.

<div style="--index: 1;"> ... </div>
<div style="--index: 2;"> ... </div>
<div style="--index: 3;"> ... </div>
div {
  /* значение index пришло из HTML */
  animation-delay: calc(var(--index, 1) * 0.2s); /* значение 1 после запятой является фаллбечным */
}

В качестве значения css-переменной мы можем указать просто число, а разрядность добавить уже в выражении:

html {
  --importantNumber: 2;
}
.box {
  /* В этом свойстве мы добавляем размерность */
  padding: calc(var(--importantNumber) * 1rem);
}