Центрирование страницы
Описание паттерна
Этот паттерн позволяет центрировать контент на странице с помощью CSS, используя функцию max() и margin-inline для создания адаптивных отступов.
Код паттерна
.container {
margin-inline: max(20px, (100% - 960px) / 2);
}Постановка задачи
Нужно центрировать контентный блок так, чтобы:
- на узких экранах у него были стабильные боковые отступы по
20px; - на широких — блок оставался по центру и не «растягивался» шире
960px; - решение было декларативным, без медиазапросов и лишних обёрток, корректно работало в LTR/RTL.
Традиционный подход («старый способ»)
Чаще всего делали так:
.container {
margin: 0 auto; /* центрируем блок */
max-width: 960px; /* ограничиваем ширину */
}
body {
/* добавляем отступы по бокам
* чтобы контент не прилипал к краям экрана
*/
padding: 0 20px;
}Далее в зависимости от конкретной задачи решение могло быть немного видоизменено, например если у блока должен быть фоновый цвет. В этом случае у body обнуляли отступы и переносили их на container.
body {
padding: 0;
margin: 0;
}
.container {
padding: 20px;
margin: 0 auto;
max-width: 960px;
}Современный подход
.container {
margin-inline: max(20px, (100% - 960px) / 2);
}Эта запись одновременно создаёт минимальные боковые поля 20px и центрирует контент, когда места больше чем 960px.
Пошаговый разбор выражения
-
margin-inlineЛогическое свойство, задаёт оба боковых внешних отступа: начало и конец строки (вместо
margin-left/right). Оно учитывает направление письма (LTR/RTL), поэтому правило универсально.

-
max()Функция берёт наибольшее из двух значений. Нам нужно «не меньше, чем 20 px», но если свободного пространства больше — использовать большую величину для центрирования.

- A =
20px— нижняя граница боковых полей на узких экранах.

- B =
(100% - 960px) / 2— половина «лишней» ширины контейнера относительно960px.

Для удобного расчёта представим, что размер всего сайта 1200px (100%).

Оставшаяся часть сайта равна: 100% - 960px = 240px. Вместо 1200px используем 100%, так как это ширина всего сайта на любом размере экрана.

Половина оставшейся части сайта равна: 240px / 2 = 120px. Это и будет отступ слева и справа.

Итоговое значение отступа слева и справа: max(20px, 120px) = 120px.
-
Какое итоговое значение будет у
max():(100% - 960px) / 2Пусть
W— ширина содержащего блока.- Если
W ≤ 960px, тоW - 960px ≤ 0, а значит выражение даёт0или отрицательное число → берёмmaxс20px⇒ получаем20px. - Если
W > 960px, то(W - 960px) / 2— это ровно тот отступ слева и справа, который центрирует блок шириной960px.
- Если
-
Точка переключения
Решим, когда оба аргумента равны:
max(20px, (100% - 960px) / 2) = 20px- При
W < 1000px→ берём20px. - При
W ≥ 1000px→ берём(W − 960) / 2.
Почему
1000px? Потому что960px + (20px * 2) = 1000px. - При
Итого, поведение полностью описывается одной формулой, без @media.
Примеры использования
Пример №1: Базовый пример
Добавьте в проект класс .container и примените его к блоку, который нужно центрировать.
.container {
margin-inline: max(20px, (100% - 960px) / 2);
}<div class="container">
<p>
Я очень современный блок. Мне звонили из Баленсиаги, а я не взял трубку, так как выше этого.
</p>
</div>Я очень современный блок. Мне звонили из Баленсиаги, а я не взял трубку, так как выше этого.
Пример №1. Базовый пример
Пример №2: С использованием кастомных свойств
Если в проекте используются кастомные свойства, то можно использовать их для центрирования. Статичные значения в этом случае можно пернести на кастомные свойства.
.container {
--container-width: 960px;
--gutter: 20px;
margin-inline: max(var(--gutter), (100% - var(--container-width)) / 2);
}Поддержка браузерами
Поддержка браузеров:
- Chrome 87+ (из-за
margin-inline) - Firefox 75+ (из-за
max()) - Safari 14.1+ (из-за
margin-inline)
Обсудить паттерн
Этот паттерн можно обсудить на GitHub — задавайте вопросы, делитесь идеями и опытом.
Если у вас есть мысль для нового паттерна, пример из практики или предложение по улучшению — расскажите об этом в обсуждении: любой вклад помогает развивать проект.