Grid layout

Free Preview
Продолжительность: 19 мин

Надеюсь вы справились с flexbox и пришло время познакомиться с другим подходом к построению макетов - CSS Grid Layout

Немного истории, для чего нужен grid и что это такое

С ростом сложности веб-приложений стало понятно, что flexbox, при всей своей мощности, не всегда удобен для построения двумерных макетов. Он отлично подходит для:

  • выстраивания элементов в строку или колонку;
  • выравнивания контента;
  • небольших компонентов и UI-блоков.

Но как только речь заходит о полноценной сетке страницы — с колонками, строками, областями и сложной структурой — flexbox начинает требовать дополнительных обёрток и усложнять разметку. Для решения этой задачи был создан CSS Grid Layout.

CSS Grid — это система компоновки, которая позволяет создавать двумерные сетки, управляя расположением элементов одновременно по строкам и колонкам. Grid особенно хорошо подходит для:

  • сеток карточек;
  • основных layout-блоков страницы;
  • галерей;
  • сложных адаптивных макетов.

В отличие от flexbox grid работает сразу в двух направлениях, а элементы можно располагать не только последовательно, но и в произвольных ячейках сетки, при этом структура макета задаётся на уровне контейнера.

Grid-container и grid-template

Как и в случае с flexbox, работа с grid начинается с контейнера. Чтобы сделать элемент grid-контейнером, ему нужно задать свойство display: grid. Все непосредственные потомки такого контейнера становятся grid-элементами.

Основу grid-сетки составляют строки и колонки. Они задаются с помощью свойств grid-template-columns и grid-template-rows. Рассмотрим следующий пример:

.grid {
  display: grid;
  grid-template-columns: 300px 200px 550px;
  grid-template-rows: 200px 200px 200px;
}
css

В данном примере мы создаем контейнер, в котором будет 3 колонки и 3 строки. Число строк и столбцов определятся количесвтом значений, указанных через пробел. Также здесь мы используем фиксированные размеры в пикселях, но также можно использовать и другие величины, рассмотренные на одном из предыдущих уроков.

Еще размеры колонок и строк можно задавать с помощью специальной единицы измерения, которую мы не встречали ранее. Это fr (сокращение от fragment). 1fr — одна доля доступного пространства. Например, вот такая запись grid-template-columns: 1fr 3fr, означает, что мы создаем две колонки, при этом первая займет 1/4 доступной ширины, а вторая - 3/4. Другими словами мы должны сложить все значения чтобы получить количество долей, а потом отдать каждому из элементов соответсвующую часть. Фрагменты можно комбинировать с другими единицами измерений. Например такая запись grid-template-columns: 2fr 1fr 200px означает, что третья колонка всегда будет иметь фиксированные размер в 200 пикселей, а первая и вторая будут разными в зависимости от доступной ширины экрана и займут 2/3 и 1/3 доступного места соответвенно.

Еще мы можем использовать функции в CSS для создания более короткой записи. Наприме так grid-template-columns: repeat(3, 1fr) мы создаем 3 колонки одинаковой ширины. repeat(3, ...) - означает повторить три раза.

Особенности верстки с использованием grid

Верстка с использованием grid имеет ряд особенностей. Также как и во flexbox у нас есть ряд свойств позволяющих настроить поведение элементов внутри сетки. Давайте рассмотрим этим особенности.

Автоматическое построение сетки

Во-первых стоит помнить что grid умеет сам создавать строки, если элементов больше, чем помещается в одну строку. Например рассмотрим такой код:

.grid {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
}
css

Если элементов будет больше четырёх, они автоматически перейдут на следующую строку.

Отступы между элементами

Для задания расстояния между строками и колонками используется свойство gap.

.grid {
  display: grid;
  gap: 20px;
}
css

Также можно задавать отступы отдельно:

grid-row-gap: 20px;
grid-column-gap: 10px;
css

Выравнивание элементов внутри grid

Grid поддерживает выравнивание элементов и всей сетки. Названия свойств для выравнивания уже знакомы нам из урока про flexbox и работают они похожим образом:

  • justify-items — выравнивание элементов по горизонтали внутри ячеек;
  • align-items — выравнивание по вертикали;
  • justify-content и align-content — выравнивание всей сетки внутри контейнера.

Позиционирование элементов по индексам строк и колонок

По умолчанию grid автоматически размещает элементы по порядку — слева направо и сверху вниз. Но одно из ключевых преимуществ CSS Grid заключается в том, что мы можем явно указать, в какой ячейке должен находиться элемент. Для этого используются свойства grid-column и grid-row или более подробные:

  • grid-column-start
  • grid-column-end
  • grid-row-start
  • grid-row-end

При работе с индексами важно понимать, что мы работаем не с колонками как таковыми, а с линиями между ними. Для наглядности обратите внимание на рисунок: grid-columns.png Ключевой момент здесь, что в нашем контейнере 3 колоки, а линий для определения положения элементов - 4. Для потомка в таком контейнере мы можем определить что он должен занять место от 1 линии до 3 с помощью свойства grid-column: 1/3. И тогда элемент расположится так, как показано на рисунке ниже: grid-example.png

Вместо указания конкретной линии окончания можно использовать ключевое слово span:

.item {
  grid-column: 1 / span 2;
}
css

Это означает начать с линии 1 и занять две колонки.

Также можно использовать следующую запись grid-column: span 2. В этом случае элемент займёт две колонки, начиная с автоматически определённой позиции.

Области grid (grid-template-areas)

Еще одна мощная возможность grid — именованные области. Суть этого подхода состоит в том: что на уровне контейнера мы можем назначить имена определенным ячейкам, а затем на уровне дочерних элементов определить в каких ячейках должен располагаться тот или иной потомок:

.grid {
  display: grid;
  grid-template-columns: 1fr 3fr;
  grid-template-areas:
    "sidebar content"
    "footer  footer";
}

.sidebar {
  grid-area: sidebar;
}

.content {
  grid-area: content;
}

.footer {
  grid-area: footer;
}
css

grid-areas.png

Думаю что в процессе изучения урока у вас мог возникнуть вопрос: "А когда использовать flexbox, а когда grid?". Тут нет однозначного ответа, но простое правило поможет определиться:

  • Flexbox — для одномерных задач (строка или колонка);
  • Grid — для двумерных макетов и сеток.

Давайте попробуем применить Grid на практике.