Код
#статьи

Шпаргалка по Flexbox: свойства, примеры использования и бесплатные тренажёры

Всё об одном из самых востребованных инструментов современной вёрстки.

Иллюстрация: Оля Ежак для Skillbox Media

Flexbox — это один из основных инструментов для создания адаптивных веб-страниц (наравне с CSS Grid), поэтому вот уже более 10 лет он остаётся мастхэв-технологией для верстальщиков и фронтенд-разработчиков.

В этой статье мы расскажем о концепциях Flexbox, свойствах flex-контейнеров и flex-элементов и покажем их действие на простых примерах. А также поделимся лайфхаками для работы с Flexbox в Google Chrome и ссылками на бесплатные тренажёры.

Содержание:


Что такое Flexbox: немного истории

Flexbox (от англ. flex — гибкий) — это модуль CSS, который позволяет удобно управлять расположением, порядком, размерами и отступами между элементами веб-страницы. Сайты, свёрстанные «флексами», получаются адаптивными, то есть выглядят хорошо на разных устройствах: ПК, ноутбуках, планшетах и смартфонах.

До появления Flexbox разработчики верстали веб-страницы с помощью таблиц, CSS-свойств position, float и прочих инструментов, которые на самом деле для этого не предназначены. Например, float определяет, с какой стороны текст, а не группа блоков, будет обтекать элемент. Но так как до начала 2010-х других средств не было, разработчикам приходилось прибегать к подобным «костылям».

К счастью, в 2009 году инициативные разработчики решили навсегда избавиться от вёрстки таблицами и позиционирования и создали Flexbox. Сегодня он, как и CSS Grid, является частью стандарта CSS3 и его не нужно подключать отдельно.

Как начать работу с Flexbox

Перед тем как приступить к вёрстке флексами, стоит познакомиться с составляющими Flexbox и их назначением. Это позволит осмысленно и эффективно использовать возможности инструмента.

Основные понятия

Во Flexbox есть два вида свойств: одни применяются к flex-контейнеру, другие — к элементам, которые в нём расположены.

Flex-контейнер — это «коробка», в которой хранятся flex-элементы (flex item). Чтобы превратить элемент во flex-контейнер, нужно установить ему свойство display: flex или display: inline-flex.

Разница между flex и inline-flex в том, что в первом случае контейнер будет занимать всю ширину экрана (как блочный элемент), а во втором — лишь пространство, занимаемое его содержимым.

Flex-элементы (flex items) — это дочерние элементы flex-контейнера. Мы можем управлять их расположением, размерами и расстоянием между ними.

Изображение: Skillbox Media

Главная ось (main axis) — направление, в котором располагаются flex-элементы.

Поперечная ось (cross axis) — ось, перпендикулярная главной оси.

Обратите внимание: направление главной и поперечной осей можно изменить с помощью свойства flex-direction (см. ниже).

Главный размер (main size) — размер, соответствующий направлению главной оси.

Начало главной оси (main start) — точка, в которой начинается последовательность flex-элементов, расположенных по главной оси.

Конец главной оси (main end) — точка, в которой заканчивается последовательность flex-элементов, расположенных по главной оси.

Поперечный размер (cross size) — размер, соответствующий поперечной оси.

Как создать flex-контейнер. Свойство display: flex

Теперь посмотрим, как ведут себя элементы, когда становятся гибкими. В примере ниже контейнер с классом container содержит три пронумерованных блока div.

HTML:

<div class="container">
        <div class="inner-div">
            <p>1</p>
        </div>
        <div class="inner-div">
            <p>2</p>
        </div>
        <div class="inner-div">
            <p>3</p>
        </div>
      </div>

CSS:

p {
    padding-top: 40px;
    margin: 0;
    font-size: 100px;
    font-family: sans-serif;
    text-align: center;
    vertical-align: middle;
  }


.inner-div {
    height: 200px;
    width: 400px;
    margin: 10px;
    background-color: #096eeb;
  }

Так как блочные элементы занимают всю ширину, то блоки .inner-div располагаются один под другим:

Изображение: Skillbox Media

А теперь назначим родительскому элементу свойство display: flex:

.container {
    display: flex;
}

Вот как изменится расположение внутренних блоков:

Изображение: Skillbox Media

Магия! Блоки выстроились вдоль главной оси, а их ширина уменьшилась так, чтобы все уместились в одном ряду.

Свойства Flexbox

Теперь, когда мы умеем превращать обычные блоки во flex-контейнеры, можно изучить каждое свойство Flexbox.

flex-direction

flex-direction определяет направление основной и поперечной осей в контейнере. Оно может принимать четыре значения:

  • row (по умолчанию) — элементы располагаются в строку, слева направо;
  • row-reverse — элементы располагаются в строку, справа налево;
  • column — элементы располагаются в столбец, сверху вниз;
  • column-reverse — элементы располагаются в столбец, снизу вверх.
.container {
    display: flex;
    flex-direction: row;
    /*flex-direction: row-reverse; */
    /*flex-direction: column; */
    /*flex-direction: column-reverse; */
}

Попробовать в CodePen.

На слайдере ниже показано, как действует на расположение элементов каждое значение flex-direction:

flex-wrap

flex-wrap определяет, будут ли flex-элементы переноситься на другую строку, если им не хватит места в ряду.

Свойство может принимать одно из трёх значений:

  • nowrap (по умолчанию) — элементы не переносятся на новую строку, а сжимаются;
  • wrap — элементы переносятся на новую строку;
  • wrap-reverse — элементы переносятся на новую строку в обратном порядке.

Продемонстрируем действие свойства flex-wrap, для наглядности увеличив количество элементов до восьми:

.container {
    display: flex;
    flex-wrap: nowrap;
    /*flex-wrap: wrap; */
    /* flex-wrap: wrap-reverse; */
}

Попробовать в CodePen.

flex-flow

flex-flow объединяет в одно свойство flex-direction и flex-wrap, позволяя задать их значения в одной строке:

.container {
  display: flex;
  flex-flow: row wrap;
}

Обратите внимание: при использовании flex-flow важно соблюдать правильный порядок: сначала задать значение для flex-direction, потом для flex-wrap, иначе свойство работать не будет.

justify-content

justify-content определяет, как будут распределены элементы вдоль главной оси.

Свойство насчитывает 10 значений, но стабильно во всех браузерах работают следующие:

  • flex-start (по умолчанию): выравнивает элементы по началу главной оси;
  • flex-end: выравнивает элементы по концу главной оси;
  • center: центрирует элементы вдоль главной оси;
  • space-between: распределяет элементы по ширине, с одинаковым пространством между ними. Не добавляет отступы между крайними дочерними элементами и границей родителя;
  • space-around: добавляет пространство вокруг каждого элемента;
  • space-evenly: добавляет пространство не только между элементами, но и между ними и границей контейнера (см. иллюстрации ниже).
.container {
    display: flex;
    justify-content: flex-start;
    /* justify-content: flex-end; */
    /* justify-content: center; */
    /* justify-content: space-between; */
    /* justify-content: space-around; */
    /* justify-content: space-evenly; */
}

Попробовать в CodePen.

align-items

align-items выравнивает содержимое контейнера вдоль по поперечной оси.

У свойства есть пять возможных значений:

  • flex-start: элементы выравниваются по верхнему краю контейнера;
  • flex-end: элементы выравниваются по нижнему краю контейнера;
  • center: содержимое контейнера выравнивается по центру;
  • baseline: элементы выравниваются по базовой линии текста, который в них содержится;
  • stretch: внутренние элементы растягиваются на всю высоту flex-контейнера.
.container {
    display: flex;
    align-items: stretch;
    /*align-items: flex-start;*/
    /*align-items: flex-end;*/
    /*align-items: center;*/
    /*align-items: baseline;*/
}

Попробовать в CodePen.

align-content

align-content действует подобно justify-content — только распределяет элементы относительно поперечной оси и работает с многострочными контейнерами.

Сделаем наш контейнер многострочным: установим фиксированную высоту и включим flex-wrap: wrap.

.container {
    height: 600px;
    flex-wrap: wrap;
    display: flex;
    align-content: flex-start;
/*  align-content: flex-end; */
/*  align-content: center; */
/*  align-content: space-between; */
/*  align-content: space-around; */
/*  align-content: stretch;  */
}

Попробовать в CodePen.

На слайдах ниже показано, как ведут себя ряды при установке разных значений align-content:

gap, row-gap, column-gap

gap — это разрыв между отдельными элементами, строками или колонками внутри flex-контейнера. Значение по умолчанию — none; задаётся пикселями (px) или процентами.

Обратите внимание: разрывы устанавливаются только между элементами, а не между элементами и границами родителя.

Существует три версии свойства:

  • row-gap — устанавливает разрыв между строками;
  • column-gap — устанавливает разрыв между колонками;
  • gap — устанавливает разрыв между строками и колонками. При этом, если задать только значение, оно применяется и к строкам, и к колонкам.
container {
	display: flex;
	gap: 50px;
  /*row-gap: 50px;*/
  /*column-gap: 50px;*/
  /*gap: 50px 100px;*/
}

Попробовать в CodePen.

Вот как будут располагаться блоки при разных значениях и версиях gap:

Свойства flex-элементов

Свойства, с которыми мы познакомились в предыдущем разделе, устанавливаются в стилях контейнера и действуют на всё его содержимое. Но во Flexbox также можно управлять отдельными flex-элементами.

order

order устанавливает порядок расположения элементов во flex-контейнере относительно друг друга.

В качестве значения order принимает любое целое число: чем оно меньше, тем ближе к началу главной оси будет расположен элемент. По умолчанию у каждого элемента значение order равно 0.

HTML:

<div class="container container_view">
        <div class="inner-div item-1">
            <p>1</p>
        </div>
        <div class="inner-div item-2">
            <p>2</p>
        </div>
        <div class="inner-div item-3">
            <p>3</p>
        </div>
</div>

CSS:

.container {
    display: flex;
}

.item-1 {
    order: 2;
}

.item-2 {
    order: 1;
}

.item-3 {
    order: 3;
}

flex-grow

flex-grow позволяет указать, какую долю свободного пространства во flex-контейнере может занимать элемент, или, другими словами, в какой степени он может «расти» вдоль главной оси. В качестве значения можно задать любое неотрицательное число, по умолчанию это 0.

Когда для всех элементов установлено значение flex-grow:1, пространство между ними распределено равномерно. Если же какому-то элементу задать flex-grow: 2, то он вырастет в два раза относительно остальных. При изменении размеров экрана пропорция между элементами сохранится.

CSS:

.container {
  display: flex;
}

.item-1 {
  flex-grow: 0;
}

.item-2 {
  flex-grow: 0;
}

.item-3 {
  flex-grow: 0;
}

Вот как это будет выглядеть:

flex-shrink

flex-shrink, в противоположность flex-grow, позволяет указать, насколько сильно элемент должен сжиматься, если суммарная ширина элементов превышает размер контейнера. Значение может быть любым положительным числом.

По умолчанию у всех дочерних элементов  устанавливается значение этого свойства 1. Элементы с ненулевым значением flex-shrink будут сжиматься, насколько это возможно, с учётом значений flex-shrink других элементов.

CSS:

.container {
    display: flex;
}


.item-1 {
    flex-shrink: 1;
  /*flex-shrink: 2;*/
  /*flex-shrink: 3;*/
}


.item-2 {
    flex-shrink: 2;
  /*flex-shrink: 2;*/
}


.item-3 {
    flex-shrink: 1;
}

Вот как это будет выглядеть в браузере:

flex-basis

flex-basis задаёт размер элемента по главной оси, перед тем как будет распределено оставшееся пространство.

Параметр можно задать в пикселях, в процентах или с помощью ключевых слов:

  • auto (по умолчанию) — в зависимости от значения flex-direction примет значение свойства width или height. Если же соответствующее свойство тоже установлено в auto, то элемент примет размер содержимого;
  • max-content — устанавливает предпочтительную ширину;
  • min-content — устанавливает минимальную ширину;
  • fit-content — устанавливает максимально возможный размер элемента, ограниченный значениями max-content и min-content.

Обратите внимание: flex-basis действует подобно свойству width, только имеет более высокий приоритет. Поэтому если для элемента будут заданы значения обоих свойств, то width будет игнорироваться.

align-self

align-self устанавливает выравнивание отдельного flex-элемента вдоль поперечной оси, переопределяя значение свойства align-items.

Значения align-self задаются для каждого flex-элемента и могут быть следующими:

  • flex-start — выравнивает элемент по началу поперечной оси (cross start);
  • flex-end — выравнивает элемент по концу поперечной оси (cross end);
  • center — выравнивает элемент по центру поперечной оси;
  • stretch (по умолчанию для flex-элементов) — элементы растягиваются на всю высоту контейнера.

На слайдах ниже показано, как ведут себя flex-элементы при разных значениях align-self:

Мы познакомились с самыми важными свойствами Flexbox — их хватит, чтобы верстать полноценные веб-страницы и разбираться в чужом HTML- и CSS-коде. Больше технических деталей и дополнительную информацию о технологии можно найти в документации на портале W3C.

Лайфхак: дебажим Flexbox в Chrome DevTools

В Google Chrome есть фича, которая позволяет экспериментировать со свойствами Flexbox и отлаживать код, не выходя из браузера.

Откройте веб-страницу и зайдите в Chrome DevTools (клавиша F12). Во вкладке Elements рядом с flex-контейнером вы увидите значок flex. Если на него нажать, то вокруг каждого блока появится пунктирная граница, а разрывы (gap) будут заштрихованы.

Скриншот: Chrome DevTools / Skillbox Media

Цвет границ и штриховки можно изменить во вкладке Layout, в разделе Flexbox:

Скриншот: Chrome DevTools / Skillbox Media

Теперь посмотрите на стили контейнера во вкладке Styles. Рядом с селектором, в котором задано свойство display: flex, расположен значок flexbox editor. Кликните на него, чтобы открыть панель редактора: в ней можно устанавливать значения свойств flex-direction, flex-wrap, align-content, justify-content и align-items.

Источник: Chrome DevTools

Так вы можете быстро проверить, какое влияние то или иное свойство окажет на веб-страницу, не переключаясь между браузером и редактором кода. Это упростит разработку и немного сэкономит ваше рабочее время.

Где поупражняться с Flexbox

Статьи и документация — это, конечно, хорошо, но иногда гораздо проще и быстрее осваивать технологии по играм. Вот три бесплатных тренажёра, которые помогут сделать это буквально за час.

Flexbox Froggy

Скриншот: Flexbox Froggy / Skillbox Media

Замечательная минималистичная игра, в которой вам предстоит помочь лягушатам занять свои листья с помощью Flexbox. Каждый уровень сопровождается подсказками и подробной справкой, что позволяет освоить технологию с нуля.

Перейти на сайт Flexbox Froggy

Flexbox Defense

Скриншот: Flexbox Defense / Skillbox Media

А здесь, помимо знания свойств Flexbox, пригодится смекалка: нужно расставить башни так, чтобы они успели убить всех врагов, бегущих по дороге. На последних уровнях будьте готовы поломать голову :)

Перейти на сайт Flexbox Defense

Flex Box Adventure

Скриншот: Flex Box Adventure / Skillbox Media

Жил-был король Артур. Он правил своим королевством честно и справедливо, но у него было три злобных брата, которые похитили золото из его замка. Так начинается игра Flex Box Adventure.

Это, пожалуй, самый весёлый тренажёр по Flexbox. Вам предстоит выполнить 24 миссии, каждая из которых помогает отточить навыки владения инструментом до автоматизма. А если задания покажутся слишком простыми, вы всегда можете повысить уровень сложности.

Перейти на сайт Flex Box Adventure
Жизнь можно сделать лучше!
Освойте востребованную профессию, зарабатывайте больше и получайте от работы удовольствие.
Каталог возможностей
Понравилась статья?
Да

Пользуясь нашим сайтом, вы соглашаетесь с тем, что мы используем cookies 🍪

Ссылка скопирована