CSS Grid или Flexbox: что и когда использовать
Почему спор Grid против Flexbox не утихает
Вы верстаете макет. По привычке хватаетесь за Flexbox, но на полпути понимаете, что боретесь с браузером: вложенные обёртки, процентные ширины и неуклюжие хаки для выравнивания. А коллега настаивает, что CSS Grid решил бы всё в три строки. Оба инструмента мощны, но решают разные задачи. Неправильный выбор ведёт к хрупкому CSS и потерянным часам.
Это руководство отсекает лишний шум. Вы изучите основные ментальные модели CSS Grid и Flexbox, увидите сравнение бок о бок и получите практический чек-лист для принятия решений, который можно применить сразу.
Основные ментальные модели
Flexbox — одномерный. Он размещает элементы вдоль одной оси (строка или столбец) и распределяет пространство. Представьте его как гибкую линию, которая может переноситься. Grid — двумерный. Он определяет строки и столбцы одновременно, позволяя размещать элементы в точной матрице. Думайте о нём как о таблице для вашей страницы.
Ни один не «лучше». Они дополняют друг друга. В большинстве реальных макетов используются оба: Grid для общего скелета страницы, Flexbox для мелких компонентов вроде навигационных панелей или групп кнопок.
Когда использовать Flexbox
Выбирайте Flexbox, когда ваш макет в основном течёт в одном направлении и размер контента должен определять макет. Типичные сценарии:
- Навигационные панели: ряд ссылок, которые должны равномерно распределяться или прижимать логотип влево, а меню вправо.
- Содержимое карточек: выравнивание иконки, заголовка и описания по вертикали внутри карточки.
- Группы кнопок: набор кнопок с одинаковыми отступами.
- Центрирование одного элемента: классическое
display: flex; justify-content: center; align-items: center;. - Динамический контент: когда вы не знаете, сколько будет элементов, и хотите, чтобы они естественно переносились.
Flexbox отлично справляется с распределением оставшегося пространства и выравниванием элементов относительно друг друга. Он ориентирован на контент: элементы определяют размер контейнера.
Когда использовать CSS Grid
Выбирайте Grid, когда нужно контролировать и строки, и столбцы, или когда хотите разместить элементы в определённых областях независимо от их порядка в HTML. Идеальные случаи:
- Макет страницы: шапка, сайдбар, основной контент, подвал, arranged in a template.
- Сложные сетки карточек: галерея, где некоторые карточки занимают две колонки или строки.
- Перекрывающиеся элементы: размещение элементов друг на друге с использованием одной и той же ячейки сетки.
- Одинаковые отступы: использование
gapдля равномерного распределения строк и столбцов. - Адаптивность без медиазапросов:
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));создаёт адаптивную сетку одной строкой.
Grid ориентирован на макет: вы определяете структуру, а элементы размещаются в ней. Это делает его идеальным для общей архитектуры страницы.
CSS Grid против Flexbox: быстрое сравнение
| Особенность | Flexbox | CSS Grid |
|---|---|---|
| Размерность | 1D (строка или столбец) | 2D (строки и столбцы) |
| Подход | Ориентирован на контент | Ориентирован на макет |
| Размещение элементов | На основе потока, порядок может меняться | Явное размещение в ячейках |
| Перенос | flex-wrap | Неявно через треки сетки |
| Поддержка gap | Да (современные браузеры) | Да |
| Лучше всего для | Компоненты, панели инструментов, центрирование | Макеты страниц, сложные сетки |
Как эффективно их объединять
Настоящий сильный ход — вкладывать один в другой. Типичный паттерн:
- Используйте Grid для основных областей страницы: шапка, сайдбар, основной контент, подвал.
- Внутри шапки используйте Flexbox для выравнивания логотипа и навигационных ссылок.
- Внутри основной области используйте Grid для галереи карточек.
- Внутри каждой карточки используйте Flexbox для вертикального размещения изображения, заголовка и текста.
Этот гибридный подход сохраняет ваш CSS модульным и избегает излишнего усложнения. Вы получаете структурный контроль Grid там, где он нужен, и гибкое выравнивание Flexbox для мелких деталей.
Практические примеры кода
Flexbox: навигационная панель
.nav {
display: flex;
justify-content: space-between;
align-items: center;
gap: 1rem;
}
.nav-links {
display: flex;
gap: 1.5rem;
list-style: none;
}
Grid: адаптивная галерея карточек
.gallery {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
gap: 1.5rem;
}
Эта единственная строка обрабатывает любой размер экрана без медиазапросов. Flexbox не может сделать это так же чисто, потому что у него нет определений столбцов.
Grid: макет страницы с именованными областями
.page {
display: grid;
grid-template-areas:
"header header"
"sidebar main"
"footer footer";
grid-template-columns: 200px 1fr;
grid-template-rows: auto 1fr auto;
min-height: 100vh;
}
.header { grid-area: header; }
.sidebar { grid-area: sidebar; }
.main { grid-area: main; }
.footer { grid-area: footer; }
Именованные области делают макет самодокументируемым. Перестановка страницы становится вопросом редактирования строки шаблона.
Распространённые ошибки и как их избежать
- Использование Flexbox для 2D-макета: вы получаете вложенные flex-контейнеры и процентные ширины. Переключитесь на Grid.
- Использование Grid для простого ряда элементов: это работает, но Flexbox часто проще и гибче для неизвестных размеров контента.
- Забывание
min-width: 0для flex-элементов: предотвращает проблемы с переполнением при длинном тексте или изображениях. - Чрезмерное использование
order: изменение визуального порядка без обновления порядка в DOM вредит доступности. По возможности используйте размещение в Grid. - Игнорирование
gap: и Grid, и Flexbox поддерживаютgap, что устраняет хаки с margin.
Чек-лист для принятия решений: что использовать?
Задайте себе эти вопросы:
- Нужно ли макету контролировать и строки, и столбцы? → Grid.
- Контент течёт в одном направлении и размер должен определяться контентом? → Flexbox.
- Нужно разместить элементы в определённых областях или перекрыть их? → Grid.
- Вы выравниваете несколько элементов внутри контейнера? → Flexbox.
- Хотите адаптивную сетку без медиазапросов? → Grid с
auto-fit.
Если всё ещё не уверены, начните с Flexbox для компонентов и Grid для страницы. Вы всегда можете отрефакторить позже.
FAQ
Можно ли использовать CSS Grid и Flexbox вместе?
Абсолютно. Они созданы, чтобы дополнять друг друга. Используйте Grid для общей структуры страницы и Flexbox для мелких компонентов, таких как навигационные панели, панели инструментов и содержимое карточек.
Устарел ли Flexbox с появлением Grid?
Нет. Flexbox остаётся лучшим выбором для одномерных макетов и размеров, определяемых контентом. Grid не замена; это дополнительный инструмент для двумерных макетов.
У какого лучше поддержка браузерами?
Оба поддерживаются во всех современных браузерах, включая Chrome, Firefox, Safari и Edge. Для очень старых браузеров могут понадобиться запасные варианты, но для большинства проектов сегодня можно использовать любой из них без опасений.
Готовы быстро протестировать свои идеи макета? Используйте наш конвертер HTML в изображение, чтобы превратить ваши HTML/CSS-макеты в изображения для дизайн-ревью или документации.