Grid auto flow

grid-auto-flow управляет автоматическим размещением элементов в сетке, а grid-auto-columns/rows задают размер неявных (автоматически созданных) треков.

Зачем нужно

Не всегда можно заранее знать количество элементов (список товаров, посты блога). Grid создаёт неявные треки для элементов, которые не поместились в явную сетку. grid-auto-flow и grid-auto-rows/columns управляют этим поведением.

Где используется

  • Динамические списки с неизвестным количеством элементов
  • Плотное заполнение сетки (галереи)
  • Горизонтальный скролл через grid-auto-flow: column
  • Автоматическое размещение без явного указания позиций

Предпосылки

Явные vs неявные треки

.grid {
  display: grid;
  grid-template-columns: 1fr 1fr 1fr; /* 3 явных столбца */
  grid-template-rows: 100px 100px;    /* 2 явные строки */
}

/* Если элементов > 6, создаются НЕЯВНЫЕ строки.
   По умолчанию неявные строки = auto (по содержимому) */

grid-auto-rows

Задаёт высоту неявных строк:

.grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  /* Не задаём grid-template-rows — все строки неявные */

  grid-auto-rows: 200px;
  /* Каждая автоматически созданная строка = 200px */
}

/* С minmax — более гибко */
.grid {
  grid-auto-rows: minmax(150px, auto);
  /* Минимум 150px, растёт под содержимое */
}

/* Чередующиеся размеры */
.grid {
  grid-auto-rows: 100px 200px;
  /* 1-я неявная строка = 100px, 2-я = 200px, 3-я = 100px... */
}

grid-auto-columns

Задаёт ширину неявных столбцов:

.grid {
  display: grid;
  grid-template-rows: repeat(3, 1fr);
  grid-auto-flow: column; /* Элементы идут по столбцам */

  grid-auto-columns: 200px;
  /* Каждый неявный столбец = 200px */
}

/* Горизонтальная полоса прокрутки */
.horizontal-scroll {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: minmax(250px, 1fr);
  gap: 16px;
  overflow-x: auto;
  padding: 16px;
}

grid-auto-flow

Управляет направлением и алгоритмом автоматического размещения.

row (по умолчанию)

Элементы размещаются по строкам: заполняют столбцы слева направо, затем переходят на следующую строку.

.grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-auto-flow: row; /* По умолчанию */
}
/* 1 2 3
   4 5 6
   7 8 9 */

column

Элементы размещаются по столбцам: заполняют строки сверху вниз, затем переходят в следующий столбец.

.grid {
  display: grid;
  grid-template-rows: repeat(3, 100px);
  grid-auto-flow: column;
  grid-auto-columns: 200px;
}
/* 1 4 7
   2 5 8
   3 6 9 */

dense — плотное заполнение

Алгоритм пытается заполнить пустые ячейки маленькими элементами, даже если это нарушает порядок в DOM.

/* Без dense — могут быть пробелы */
.gallery {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-auto-rows: 100px;
  grid-auto-flow: row;
  gap: 8px;
}

.gallery .wide { grid-column: span 2; }
.gallery .tall { grid-row: span 2; }
/* Элемент после wide может оставить пробел, если не влезает */

/* С dense — пробелы заполняются */
.gallery-dense {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-auto-rows: 100px;
  grid-auto-flow: dense; /* или row dense */
  gap: 8px;
}
/* Маленькие элементы «заполнят» пробелы, оставленные большими */

dense меняет визуальный порядок элементов, но не порядок в DOM. Это может нарушить доступность (табуляция пойдёт в DOM-порядке, а не визуальном).

column dense

.grid {
  grid-auto-flow: column dense;
  /* Размещение по столбцам + плотное заполнение */
}

Горизонтальный скролл карточек

.scroll-row {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: minmax(280px, 1fr);
  gap: 16px;
  overflow-x: auto;
  overscroll-behavior-x: contain;
  scroll-snap-type: x mandatory;
  padding: 16px;
}

.scroll-row > * {
  scroll-snap-align: start;
}

/* Скрыть скроллбар (опционально) */
.scroll-row {
  scrollbar-width: none;
}
.scroll-row::-webkit-scrollbar {
  display: none;
}

Неявная сетка на практике

/* Карточный каталог — не знаем количество карточек */
.catalog {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(250px, 1fr));
  grid-auto-rows: minmax(200px, auto); /* Все строки минимум 200px */
  gap: 20px;
}

/* Дашборд — виджеты разного размера */
.dashboard {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-auto-rows: minmax(150px, auto);
  grid-auto-flow: dense; /* Заполнять пробелы */
  gap: 16px;
}

.widget-large {
  grid-column: span 2;
  grid-row: span 2;
}

.widget-wide {
  grid-column: span 2;
}

.widget-tall {
  grid-row: span 2;
}

Частые ошибки

  1. dense без понимания последствий — визуальный порядок не совпадает с DOM, проблемы с табуляцией
  2. Неявные строки с auto — без grid-auto-rows строки имеют высоту auto, что может дать нулевую высоту для пустых ячеек
  3. grid-auto-flow: column без ограничения строк — все элементы встанут в один столбец, если не задать grid-template-rows
  4. Путаница явных и неявных трековgrid-auto-rows не влияет на явные строки из grid-template-rows

Практика

  • Создать сетку без grid-template-rows и настроить grid-auto-rows: minmax(100px, auto)
  • Реализовать горизонтальный скролл через grid-auto-flow: column
  • Сделать галерею с элементами span 2 и dense
  • Сравнить результат с dense и без — увидеть заполнение пробелов
  • Проверить чередующиеся размеры: grid-auto-rows: 80px 120px

Связанные темы

Ресурсы