Сложные макеты на Grid

Тренажер по CSS для пользователей с начальным уровнем подготовки.

Тренажер CSS

Эта серия упражнений посвящена созданию сложных и адаптивных макетов с использованием CSS Grid Layout. Вы попрактикуетесь в применении именованных областей (`grid-template-areas`), автоматического размещения элементов (`grid-auto-flow`), выравнивания (`align-items`, `justify-content` и т.д.), объединения ячеек (`span`), создания гибких треков с помощью `minmax()`, а также использования `repeat()` с `auto-fit` или `auto-fill` для построения адаптивных сеток. Задания построены по принципу \"от простого к сложному\" и помогут закрепить навыки работы с продвинутыми возможностями Grid.

Список тем

Создание макета с помощью grid-template-areas

Определите структуру макета страницы, состоящую из шапки (header), основного контента (main), боковой панели (sidebar) и подвала (footer), используя именованные области сетки. Шапка и подвал должны занимать всю ширину, а основной контент и боковая панель - располагаться рядом под шапкой.

CSS
.container {
  display: grid;
  grid-template-columns: 3fr 1fr; /* Определяем 2 колонки */
  grid-template-rows: auto 1fr auto; /* Определяем 3 строки */
  gap: 10px;
  height: 300px; /* Для наглядности */
  border: 1px solid #ccc;
  padding: 10px;
  /* Определите именованные области для макета */
  input1: 
    "header header"
    "main sidebar"
    "footer footer";
}

.header { input2: header; background-color: #a7c5eb; padding: 10px; }
.main { input3: main; background-color: #f0f0f0; padding: 10px; }
.sidebar { input4: sidebar; background-color: #e0e0e0; padding: 10px; }
.footer { input5: footer; background-color: #a7c5eb; padding: 10px; }
HTML
<div class="container">
  <header class="header">Header</header>
  <main class="main">Main Content</main>
  <aside class="sidebar">Sidebar</aside>
  <footer class="footer">Footer</footer>
</div>
Используйте свойство `grid-template-areas` для контейнера `.container`. Задайте строковое представление макета, где каждая строка в значении свойства соответствует ряду сетки, а имена областей (например, 'header', 'main', 'sidebar', 'footer') определяют, какую область занимает ячейка. Одинаковые имена, расположенные рядом, объединяют ячейки в одну область. Используйте точку (`.`) для обозначения пустой ячейки, если это необходимо.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Объединение колонок с помощью span

Создайте сетку 3x2. Первый элемент ('Item 1') должен занимать две колонки первой строки. Остальные элементы должны располагаться в доступных ячейках по порядку.

CSS
.grid-container {
  display: grid;
  input1: repeat(3, 1fr); /* 3 колонки */
  grid-template-rows: repeat(2, 100px); /* 2 строки */
  gap: 10px;
  border: 1px solid #ccc;
  padding: 10px;
}

.item {
  background-color: #bde0fe;
  border: 1px solid #a2d2ff;
  padding: 20px;
  text-align: center;
}

.item1 {
  /* Заставьте этот элемент занимать 2 колонки */
  input2: 1 / input3 input4;
  background-color: #ffafcc; /* Выделяем цветом */
}
HTML
<div class="grid-container">
  <div class="item item1">Item 1</div>
  <div class="item item2">Item 2</div>
  <div class="item item3">Item 3</div>
  <div class="item item4">Item 4</div>
  <div class="item item5">Item 5</div>
</div>
Для элемента, который должен занимать несколько колонок, используйте свойство `grid-column`. Чтобы указать количество объединяемых колонок, используйте ключевое слово `span` и число колонок. Например, `span 2` означает объединить две колонки.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Автоматическое размещение с dense

Имеется сетка с элементами разной высоты. Некоторые элементы занимают две строки. Из-за этого образуются пустые места. Используйте `grid-auto-flow` со значением `dense`, чтобы сетка пыталась заполнить эти пробелы элементами, идущими позже.

CSS
.dense-container {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-auto-rows: 60px; /* Автоматическая высота строк */
  gap: 10px;
  border: 1px solid #ccc;
  padding: 10px;
  /* Добавьте свойство для плотного размещения */
  input1: input2;
}

.dense-item {
  background-color: #fec89a;
  border: 1px solid #fdaa7a;
  padding: 10px;
  text-align: center;
}

.item-tall {
  grid-row: span 2; /* Занимает 2 строки */
  background-color: #d8e2dc; 
}
HTML
<div class="dense-container">
  <div class="dense-item item-tall">1 (Tall)</div>
  <div class="dense-item">2</div>
  <div class="dense-item">3</div>
  <div class="dense-item item-tall">4 (Tall)</div>
  <div class="dense-item">5</div>
  <div class="dense-item">6</div>
  <div class="dense-item">7</div>
</div>
Примените свойство `grid-auto-flow` к грид-контейнеру. Установите его значение в `dense`, чтобы активировать алгоритм плотного размещения, который позволяет элементам 'перепрыгивать' вперед для заполнения пустых ячеек.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Выравнивание элемента внутри ячейки

В сетке 2x2 размещены четыре элемента. Третий элемент ('Item 3') должен быть выровнен по правому краю своей ячейки по горизонтали и по нижнему краю по вертикали.

CSS
.align-container {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  grid-template-rows: repeat(2, 100px);
  gap: 10px;
  border: 1px solid #ccc;
  padding: 10px;
}

.align-item {
  background-color: #e9d8a6;
  border: 1px solid #e7c58d;
  padding: 10px;
}

.item3 {
  background-color: #ee9b00; /* Выделяем цветом */
  /* Выровняйте этот элемент по правому краю */
  input1: input2;
  /* Выровняйте этот элемент по нижнему краю */
  input3: input4;
}
HTML
<div class="align-container">
  <div class="align-item">Item 1</div>
  <div class="align-item">Item 2</div>
  <div class="align-item item3">Item 3</div>
  <div class="align-item">Item 4</div>
</div>
Используйте свойства `justify-self` для горизонтального выравнивания и `align-self` для вертикального выравнивания непосредственно для элемента, который нужно выровнять (`.item3`). Возможные значения включают `start`, `end`, `center`, `stretch`.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Гибкая колонка с minmax()

Создайте двухколоночный макет. Первая колонка (основной контент) должна занимать всё доступное пространство, но не быть меньше 150px. Вторая колонка (боковая панель) должна иметь фиксированную ширину 80px.

CSS
.minmax-container {
  display: grid;
  /* Определите две колонки: гибкую с минимумом и фиксированную */
  input1: input2(150px, input3) 80px;
  gap: 10px;
  height: 250px;
  border: 1px solid #ccc;
  padding: 10px;
}

.minmax-main {
  background-color: #f1faee;
  padding: 10px;
  border: 1px solid #a8dadc;
}

.minmax-sidebar {
  background-color: #a8dadc;
  padding: 10px;
  border: 1px solid #457b9d;
}
HTML
<div class="minmax-container">
  <div class="minmax-main">Main content area that can grow and shrink.</div>
  <div class="minmax-sidebar">Sidebar</div>
</div>
Используйте свойство `grid-template-columns`. Для первой колонки примените функцию `minmax()`. Первый аргумент `minmax()` задает минимальный размер (150px), а второй - максимальный. Чтобы колонка занимала всё доступное пространство, используйте единицу `fr` (например, `1fr`) в качестве максимального значения. Для второй колонки просто укажите фиксированную ширину (80px).
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Адаптивная галерея с auto-fit

Создайте адаптивную сетку для галереи изображений. Элементы сетки должны автоматически подстраиваться под ширину контейнера. Каждый элемент должен иметь минимальную ширину 100px и занимать равную долю доступного пространства.

CSS
.gallery-container {
  display: grid;
  /* Используйте repeat и auto-fit для создания адаптивных колонок */
  input1: input2(input3, minmax(100px, 1fr));
  gap: 10px;
  padding: 10px;
  border: 1px solid #ccc;
}

.gallery-item img {
  display: block;
  width: 100%;
  height: auto;
  aspect-ratio: 1 / 1; /* Делаем изображения квадратными */
  object-fit: cover; /* Масштабируем изображение с сохранением пропорций */
  border: 1px solid #ddd;
}
HTML
<div class="gallery-container">
  <div class="gallery-item"><img src="https://naytikurs.ru/img/1.png" alt="Image 1"></div>
  <div class="gallery-item"><img src="https://naytikurs.ru/img/2.png" alt="Image 2"></div>
  <div class="gallery-item"><img src="https://naytikurs.ru/img/4.png" alt="Image 4"></div>
  <div class="gallery-item"><img src="https://naytikurs.ru/img/5.png" alt="Image 5"></div>
  <div class="gallery-item"><img src="https://naytikurs.ru/img/6.png" alt="Image 6"></div>
  <div class="gallery-item"><img src="https://naytikurs.ru/img/7.png" alt="Image 7"></div>
</div>
Используйте `grid-template-columns` совместно с функцией `repeat()`. В качестве первого аргумента `repeat()` используйте ключевое слово `auto-fit`. В качестве второго аргумента используйте функцию `minmax()`, где минимальное значение - 100px, а максимальное - `1fr`, чтобы колонки равномерно заполняли доступное пространство.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Перекрытие элементов в сетке

Создайте сетку 2x2. Разместите первый элемент ('Item 1') в левой верхней ячейке (1-я строка, 1-я колонка). Второй элемент ('Item 2') должен частично перекрывать первый, располагаясь со 2-й колонки первой строки и занимая две колонки в ширину.

CSS
.overlap-container {
  display: grid;
  grid-template-columns: repeat(3, 1fr); /* 3 колонки для span 2 */
  grid-template-rows: repeat(2, 100px);
  gap: 10px;
  padding: 10px;
  border: 1px solid #ccc;
  position: relative; /* Для z-index */
}

.overlap-item {
  padding: 20px;
  border: 1px solid #555;
}

.item-back {
  background-color: #caf0f8;
  /* Разместите в первой ячейке */
  input1: 1;
  input2: 1;
  z-index: 1;
}

.item-front {
  background-color: rgba(255, 190, 11, 0.7); /* Полупрозрачный для наглядности */
  /* Разместите со второй колонки, занимая 2 колонки, в первой строке */
  input3: 2 / span 2;
  input4: 1;
  z-index: 2; /* Должен быть поверх */
}
HTML
<div class="overlap-container">
  <div class="overlap-item item-back">Item 1</div>
  <div class="overlap-item item-front">Item 2</div>
</div>
Используйте свойства `grid-column` и `grid-row` для точного позиционирования элементов. Для первого элемента укажите `grid-column: 1; grid-row: 1;`. Для второго элемента укажите начальную линию колонки (`grid-column-start: 2;`) и количество занимаемых колонок (`span 2`), а также строку (`grid-row: 1;`). Чтобы перекрытие было видно, можно добавить `z-index`.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку

Вложенная сетка (Nested Grid)

Создайте основной макет 1x2 (одна строка, две колонки). Левый элемент ('Left') должен сам стать грид-контейнером и содержать два дочерних элемента ('Nested 1', 'Nested 2'), расположенных в одну строку.

CSS
.main-container {
  display: grid;
  input1: 1fr 1fr; /* Две равные колонки */
  gap: 15px;
  padding: 10px;
  border: 1px solid #ccc;
  height: 200px;
}

.grid-item {
  padding: 10px;
  border: 1px solid #aaa;
}

.left-item {
  background-color: #d6eaf8;
  /* Сделайте этот элемент грид-контейнером */
  input2: input3;
  /* Определите две колонки для вложенных элементов */
  input4: 1fr 1fr;
  gap: 5px; /* Промежуток для вложенных элементов */
}

.right-item {
  background-color: #d1f2eb;
}

.nested-item {
  background-color: #fcf3cf;
  padding: 5px;
  border: 1px solid #f7dc6f;
  text-align: center;
}
HTML
<div class="main-container">
  <div class="grid-item left-item">
    <div class="nested-item">Nested 1</div>
    <div class="nested-item">Nested 2</div>
  </div>
  <div class="grid-item right-item">
    Right
  </div>
</div>
Для основного контейнера (`.main-container`) задайте `display: grid` и `grid-template-columns`. Для левого элемента (`.left-item`) также задайте `display: grid`, чтобы он стал грид-контейнером. Затем определите для него колонки с помощью `grid-template-columns`, чтобы разместить вложенные элементы.
Заполнить ответами все поля
Результат
Сообщения
Выполнить
Отметить решенным
Показать подсказку
НайтиКурс.Ру