Будущая CSS-функция inherit()

13.01.2026 • css

Введение

В будущей спеке CSS Values and Units Module Level 5 есть интересная функция inherit(). Да, именно функция, а не значение, как мы привыкли.

Думаю, фантазией тут можно навернуть очень много всего (получение произвольных свойств родителя, например), так что просто разберём задумку, возможные применения и текущий статус.

Функционал

Задумка очень простая: это как var(), только значение берётся из родительского элемента, а не из текущего. Выглядит как-то так:

.smth {
    --smth: inherit(--prop, 0px);
}

Функция получает имя переменной, которое нужно получить, а также опциональное фолбечное значение.

В чём отличие от стандартного var()? Посмотрим на примере. Значение --accent задано для обоих элементов, и в дочернем можно получить любое из них.

<div class="parent">
    <div class="child"></div>
</div>
.parent {
    --accent: #fff;
}
 
.child {
    --accent: #000;
 
    /* Чёрный цвет #000, так как var() берёт значение с текущего элемента */
    background: var(--accent);
    /* Белый цвет #fff, берём с родителя */
    border-color: inherit(--accent);
}

Варианты использования

Глядя первый раз, можно подумать, что функция немного бесполезна. Как часто у нас есть разные значения CSS-переменной у родительского элемента и у текущего?

Думаю, всё дело в том, что мы просто не привыкли использовать CSS-переменные таким способом, и это требует нового подхода. А именно, с такой функцией можно будет определять значения рекурсивно.

Деревья

<div class="tree-item">
    <div class="tree-item__name">--level: 1</div>
    <div class="tree-item">
        <div class="tree-item__name">--level: 2</div>
        <div class="tree-item">
            <div class="tree-item__name">--level: 3</div>
        </div>
    </div>
</div>
.tree-item {
    --level: calc(inherit(--level, 0) + 1);
}
 
.tree-item__name {
    padding-left: calc(var(--level) * 20px);
 
    &:hover {
        background-color: rgb(45, 157, 194);
    }
}
--level: 1
--level: 2
--level: 3

Можно подумать, что пример немного надуманный, так как вложенностью с фиксированным паддингом можно добиться того же самого внешнего вида, однако добавление фона всё меняет, так как нам нужен элемент, который будет растягиваться на всю ширину.

Вложенные фоны

Часто в дизайн-системах определяют цвета разных “уровней”: самый тёмный, чуть светлее, ещё чуть светлее и так далее (или наоборот, светлые цвета). И часто есть задача выделить какой-то блок на сайте цветом из палитры. Разумеется, цвет должен отличаться от окружения.

Если вариантов вкладывания много, то может оказаться так, что цвета стоит определять динамически. И inherit() даёт ещё один способ это реализовать:

.block {
    --level: calc(inherit(--level, 0) + 1);;
 
    background-color: hsl(var(--accent) var(--saturation) calc(100 - 10 * var(--level)));
}
Block level 1
Block level 2
Block level 3
Block level 3

Данный пример требует доработки для реальной жизни, но, думаю, идея понятна.

Текущий статус

Пока что браузеры хотят с этим экспериментировать и нигде фича не реализована. Спека в статусе драфта.

Итого

Фича требует переосмысления того, как мы пишем код. Похожего эффекта можно добиться и сейчас, например, реализуя элементы через компоненты одного или другого фреймворка с ручной установкой значения из какого-то контекста:

const Component = ({ children }) => {
    const level = useContext(LevelContext);
 
    return <LevelContext.Provider value={level + 1}>
        <div style={{ '--level': level }}>
            {children}
        </div>
    </LevelContext.Provider>;
};

Но с inherit() всё это будет реализовать проще и быстрей. Возможно, стоит покопать другие задачи и вполне окажется, что есть и другие применения.

Мне нравится мысль, что если sibling-index() даёт нам способ понять, какой элемент по счёту, то inherit() даёт нам способ понять, на какой вложенности элемент находится.

На самом деле, можно не просто увеличивать значение на 1, а задумать что-то более дерзкое. Текущий CSS заточен под один способ наследования и только под одно свойство за раз. А с inherit() мы можем поменять обычную логику. Вывернуть её наизнанку, наследовать через один уровень вложенности или кто знает что угодно ещё.

Посмотрим, куда нас заведёт человеческая фантазия)

Обсудить в Telegram