11 вещей которые я узнал, читая спецификацию flexbox
Содержание:
- Переносы флекс-элементов
- align-self
- Justify Content
- Свойства контейнера flexbox
- Случаи использования
- Контроль роста и сжимания
- Как использовать Flexbox
- CSS Tutorial
- Выравнивание контента внутри контейнера. Три способа.
- The flex-direction Property
- Основы CSS Flexbox
- Разница между устаревшими подходами и современными стандартами
- Что такое Flexbox на самом деле?
- Значение row-reverse
- Реальные примеры
Переносы флекс-элементов
Вы можете использовать свойство flex-wrap и определить, как флекс-элементы переносятся внутри флекс-контейнера.
По умолчанию флекс-элементы не переносятся. Если они слишком широкие и не помещаются во флекс-контейнере, то элементы просто сжимаются до тех пор, пока все они не смогут поместиться. Текст внутри флекс-элементов может по-прежнему переноситься, но только не сами флекс-элементы.
Значение nowrap
Вот что я имею в виду (это поведение по умолчанию).
<!doctype html>
<title>Пример</title>
<style>
.container {
display: flex;
flex-direction: row;
align-items: flex-start;
background: beige;
height: 100vh;
}
.red {
background: orangered;
}
.green {
background: yellowgreen;
}
.blue {
background: steelblue;
}
.container > div {
font-size: 5vw;
padding: .5em;
color: white;
width: 60%;
}
body {
margin: 0;
}
</style>
<div class=»container»>
<div class=»red»>1</div>
<div class=»green»>2</div>
<div class=»blue»>3</div>
</div>
У всех флекс-элементов в данном примере ширина задана как 60%. Это 60 процентов от ширины флекс-контейнера. Вы не можете разместить два элемента такой ширины рядом друг с другом, не говоря уже о трёх. Но поскольку начальное значение flex-wrap равно nowrap, то элементы не переносятся, а вместо этого они сжимаются.
Значение wrap
Теперь давайте добавим flex-wrap: wrap.
<!doctype html>
<title>Пример</title>
<style>
.container {
display: flex;
flex-direction: row;
align-items: flex-start;
background: beige;
height: 100vh;
flex-wrap: wrap;
}
.red {
background: orangered;
}
.green {
background: yellowgreen;
}
.blue {
background: steelblue;
}
.container > div {
font-size: 5vw;
padding: .5em;
color: white;
width: 60%;
}
body {
margin: 0;
}
</style>
<div class=»container»>
<div class=»red»>1</div>
<div class=»green»>2</div>
<div class=»blue»>3</div>
</div>
Значение wrap-reverse
Давайте теперь добавим flex-wrap: wrap-reverse.
<!doctype html>
<title>Пример</title>
<style>
.container {
display: flex;
flex-direction: row;
align-items: flex-start;
background: beige;
height: 100vh;
flex-wrap: wrap-reverse;
}
.red {
background: orangered;
}
.green {
background: yellowgreen;
}
.blue {
background: steelblue;
}
.container > div {
font-size: 5vw;
padding: .5em;
color: white;
width: 60%;
}
body {
margin: 0;
}
</style>
<div class=»container»>
<div class=»red»>1</div>
<div class=»green»>2</div>
<div class=»blue»>3</div>
</div>
align-self
Применяется к дочерним элементам. Позволяет переопределить выравнивание, заданное в align-items для отдельных элементов.
Все возможные значения для свойства:
- flex-start: граница cross-start для элементов располагается на позиции cross-start
- flex-end: граница cross-end для элементов располагается на позиции cross-end
- center: элементы выравниваются по центру поперечной оси
- baseline: элементы выравниваются по своей базовой линии
- stretch (по умолчанию): элементы растягиваютcя, заполняя контейнер (с учётом min-width/max-width)
Обновим стили. Зададим другое выравнивание первому элементу:
.parent { displayflex; border2px solid #FF8C00; padding20px; width760px; align-itemscenter; height300px; } .child { background-color#ededed; border2px solid #768D44; padding30px; margin10px; } .child:first-child { align-self:flex-start; }
В приведенном примере — первый блок находится в начале родительского, а второй и третий выравнены по центру.
Ну и в заключение приведу пример, в которой в строку будут стоят 3 блока. Первый блок будет 200px, сжиматься и растягиваться не будет. Остальные 2 блока будут занимать все оставшееся пространство, причем как растягиваться так и сжиматься. Без flexbox это сделать достаточно проблематично. Посмотрим на код css при использовании flexbox:
.parent { displayflex; border2px solid #FF8C00; padding20px; width760px; } .child { background-color#ededed; border2px solid #768D44; padding30px; margin10px; flex1 200px; } .child:first-child { flex 200px; }
Вот и все! Обзорная экскурсия по flexbox закончена. Экспериментируйте и все получится!
Justify Content
Свойство определяет горизонтальное положение элементов. Это свойство похоже на Flex Wrap, но в justify сохраняется первоначальный порядок элементов.
В следующем примере () все элементы вне зависимости от их ширины имеют горизонтальное позиционирование по центру родительского контейнера. Это похоже на свойства .
Значение добавляет пробелы между всеми inner-элементами, тем самым растягивая строку на всю ширину контейнера:
На первый взгляд следующий пример может показаться идентичным примеру выше. Разница между ними хорошо видна, если элементов будет не целый алфавит, а всего несколько. В следующем примере появляются внешние отступы у крайних нижних элементов.
Пример выше со значением не имеет отступов на угловых элементах. Пример ниже со значением делает равные внешние отступы на всех элементах.
Идентичный прошлому пример с растянутым элементом middle:
Как видите, вам всё равно придётся экспериментировать с flex-элементами, чтобы достичь правильного результата именно для вашего случая. Результат, естественно, зависит и от размеров содержимого.
Свойства контейнера flexbox
Свойство display позволяет определить div в качестве контейнера:
.container { display: flex; }
Flex-direction
CSS flex direction позволяет определить направление, в котором дочерние элементы будут распространяться (четыре значения):
.container { display: flex; flex-direction: row; }
- row — слева направо;
- row-reverse — справа налево;
- column — сверху вниз;
- column-reverse — снизу вверх.
Пример слева направо
Пример справа налево
Пример сверху вниз
Пример снизу вверх
flex-wrap
По умолчанию flexbox располагает дочерние элементы в одну строку. Но, изменив значение flex-wrap, можно разрешить их перенос на новую строку:
.container { display: flex; flex-wrap: nowrap; }
- nowrap — одна строка, слева направо;
- wrap — несколько строк, слева направо;
- wrap-reverse — несколько строк, справа налево.
Пример несколько строк слева направо
Пример несколько строк справа налево
flex-flow
Flex-flow позволяет объединить два описанных выше свойства в одно. Это сокращенное свойство, определяющее flex-direction и flex-wrap:
.container { display: flex; flex-flow: row nowrap; }
justify-content
Определяет, как размещаются внутри div контейнера дочерние элементы. Доступно пять различных значений этого свойства CSS flex:
- flex-start — выравнивает элементы по началу контейнера;
- flex-end — выравнивает элементы по концу контейнера;
- center — выравнивает элементы по центру;
- space-between — элементы размещаются с одинаковыми отступами друг от друга, первый элемент выравнивается по началу контейнера, последний элемент — по концу контейнера;
- space-around — для элементов задаются одинаковые отступы со всех сторон.
Пример flex-start
Пример flex-end
Пример center
Пример space-between
Пример space-around
align-items
Align-items позволяет выровнять элементы по вертикальной оси. Доступно пять различных значений этого свойства CSS flex:
- flex-start — выравнивает элементы по верху;
- flex-end — выравнивает элементы по низу;
- center — центрирует элементы по вертикали;
- baseline — выравнивает элементы по базовому уровню;
- stretch — растягивает элементы, чтобы они соответствовали размерам контейнера.
Пример flex-start
Пример flex-end
Пример center
Пример baseline
Пример stretch
align-content
Выравнивает контент и пространство между полями, когда контент перемещается на несколько строк. Доступно шесть значений этого свойства CSS flex 1:
- flex-start — несколько строк будут смещены к началу контейнера;
- flex-end — несколько строк будут смещены к концу контейнера;
- center — несколько строк будут размещены по центру;
- space-between — для нескольких строк будет задано одинаковое расстояние между ними;
- space-around — для нескольких строк будет задано одинаковое расстояние вокруг них;
- stretch — несколько строк будут растягиваться, чтобы занять все пространство.
Случаи использования
Аватар пользователя
Типичный вариант использования flexbox — пользовательский компонент. Аватар и текстовое содержимое должны находиться в одной строке.
<div class="user"> <img class="user__avatar" src="shadeed.jpg" alt="" /> <div> <h3>Ahmad Shadeed</h3> <p>Author of Debugging CSS</p> </div> </div>
.user { display: flex; flex-wrap: wrap; align-items: center; } .user__avatar { flex: 0 0 70px; width: 70px; height: 70px; }
Обратите внимание, что я добавил для аватара flex: 0 0 70px
Это важно, поскольку в некоторых старых браузерах изображение может выглядеть сжатым, если не установлен параметр flex. Кроме того, flex имеет более высокий приоритет, чем свойство width (в случае flex-direction: row) или height (в случае flex-direction: column)
Кроме того, flex имеет более высокий приоритет, чем свойство width (в случае flex-direction: row) или height (в случае flex-direction: column).
Если мы изменим размер аватара, настроив только свойство flex, width будет проигнорирована браузером.
.user__avatar { /* width будет 100px, а не 70px */ flex: 0 0 100px; width: 70px; height: 70px; }
Заголовок раздела
У вас есть title для заголовка раздела, и он должен занимать все доступное пространство. В этом случае идеально подходит flex: 1.
.page-header { display: flex; flex-wrap: wrap; } .page-header__title { flex: 1; }
Элемент Input для отправки сообщений
Это очень распространено в приложениях для обмена сообщениями, таких как Facebook Messenger или Twitter. Входные данные должны заполнять доступное пространство с фиксированной шириной для кнопки отправки.
form { display: flex; flex-wrap: wrap; } input { flex: 1; /* Другие стили */ }
Приведенные выше примеры являются полезными примерами использования flex-grow. Однако некоторые случаи игнорируются или вообще не упоминаются в некоторых статьях по flex. Давайте рассмотрим их!
Выравнивание элементов на двух картах
Предположим, что CSS-сетка имеет макет из двух столбцов. Проблема в том, что положение дат не совпадают. Они должны быть на одной линии (красной).
Мы можем сделать это с помощью flexbox.
<div class="card"> <img src="thumb.jpg" alt=""> <h3 class="card__title">Title short</h3> <time class="card__date"></time> </div>
Устанавливая flex-direction: column мы можем использовать flex-grow для заголовка, чтобы он заполнял доступное пространство и, таким образом, размещал дату в конце, даже если заголовок короткий.
.card { display: flex; flex-direction: column; } /* Первое решение */ .card__title { flex-grow: 1; }
Кроме того, это возможно без использования flex-grow. Благодаря auto margins и flexbox! Я написал подробную статью об auto в CSS, если вы хотите вникнуть в подробности.
/* Второе решение */ .card__date { margin-top: auto; }
Контроль роста и сжимания
Я потратила большую часть этой статьи, описывая, что делает Flexbox, когда он оставлен на своем устройстве. Разумеется, вы можете больше контролировать свои гибкие элементы, используя flex свойства. Они, надеюсь, кажутся более предсказуемыми с пониманием того, что происходит за кулисами.
Установив свой собственный flex-basis или предоставив самому элементу размер, который затем используется в качестве flex-basis, вы возвращаете управление алгоритмом, сообщая Flexbox, что вы хотите расти или уменьшаться от этого конкретного размера. Можно полностью отключить рост или сжатие, установив для параметра flex-grow или flex-shrink значение 0. На этом этапе, однако, стоит временно использовать желание контролировать flex элементы, чтобы проверить, используете ли вы правильный метод компоновки. Если вы пытаетесь выровнять элементы flex в двух измерениях, вам лучше выбрать макет сетки.
Как использовать Flexbox
(О выборе между Grid и Flexbox можно почитать в статье «Grid — для макетов, Flexbox — для компонентов», — прим. ред. Techrocks).
Допустим, у нас есть документ, в котором по порядку идут три одинаковых элемента-потомка какого-нибудь родительского блока. Они располагаются друг за другом вертикально.
Но что, если нам нужно расположить их в ряд?
Здесь нам на помощь приходит Flexbox. Этот функционал CSS позволяет располагать элементы с учетом строк и столбцов, а также задавать промежутки между ними (пространство вокруг них).
Для начала давайте создадим родительский блок с тремя элементами-потомками внутри него.
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>CSS Position and Flexbox</title> <link rel="stylesheet" href="./index.css"> </head> <body> <div class="parent"> <div class="child-one"></div> <div class="child-two"></div> <div class="child-three"></div> </div> </body> </html>
CSS:
/* Flexbox container */ .parent { background-color: #00AAFF; width: 300px; height: 300px; display: flex; } .child-one { background-color: rgb(116, 255, 116); width: 300px; height: 300px; } .child-two { background-color: rgb(248, 117, 117); width: 300px; height: 300px; } .child-three { background-color: rgb(255, 116, 232); width: 300px; height: 300px; }
Обратите внимание, что для класса установлено свойство. Благодаря этому наши элементы-потомки расположились в ряд
Это расположение, принятое во Flexbox по умолчанию.
Давайте посмотрим другие варианты расположений.
Как располагать элементы при помощи Flexbox
flex-direction
Свойство служит для указания главной оси, по которой будут располагаться элементы. То есть, оно определяет, как элементы будут отображаться на экране: горизонтально или вертикально.
Свойству назначают значение row, если элементы нужно расположить в ряд, слева направо (это значение по умолчанию):
Значение позволяет расположить элементы в виде столбцов, т. е. вертикально:
Значение работает так же, как , но порядок элементов будет обратным. Первый элемент станет последним, а последний — первым. расположение элементов будет противоположным тому, что было бы при значении :
Аналогично, значение служит для расположения элементов вертикально, но в обратном порядке.
justify-content
Это свойство определяет выравнивание элементов вдоль горизонтальной оси контейнера.
Если задано значение , элементы будут располагаться по центру контейнера.
При значении — в начале страницы.
При значении — в конце страницы.
Значение позволяет распределить элементы по ширине flex-блока. Элементы будут разделены промежутками. Расстояния между каждой парой соседних элементов будут одинаковыми, а пустые пространства перед первым элементом и после последнего элемента будут равны половине пространства между парами элементов.
Вы видите, что пространства между , и одинаковые, а пространства перед и после — меньше.
Значение максимизирует пространство между элементами, прижимая первый и последний к началу и концу контейнера по главной оси.
Значение дает эффекта, похожий на эффект от значения , с той разницей, что пространство от краев контейнера до первого и последнего элементов будет таким же, как и пространство между элементами.
align-items
Свойство аналогично свойству , но служит для выравнивания элементов по вертикали. Работает только с фиксированной высотой контейнера.
Значение позволяет центрировать элементы по вертикали.
При значении элементы выравниваются по верхнему краю страницы.
При значении — выравниваются по нижнему краю.
Теперь вы знаете основы Flexbox.
Как выравнивать элементы по центру экрана
Свойства Flexbox можно использовать вместе. Например, если мы хотим расположить элементы по центру и по горизонтали, и по вертикали, мы можем задать и , и .
CSS Tutorial
CSS HOMECSS IntroductionCSS SyntaxCSS SelectorsCSS How ToCSS CommentsCSS Colors
Colors
RGB
HEX
HSL
CSS Backgrounds
Background Color
Background Image
Background Repeat
Background Attachment
Background Shorthand
CSS Borders
Borders
Border Width
Border Color
Border Sides
Border Shorthand
Rounded Borders
CSS Margins
Margins
Margin Collapse
CSS PaddingCSS Height/WidthCSS Box ModelCSS Outline
Outline
Outline Width
Outline Color
Outline Shorthand
Outline Offset
CSS Text
Text Color
Text Alignment
Text Decoration
Text Transformation
Text Spacing
Text Shadow
CSS Fonts
Font Family
Font Web Safe
Font Fallbacks
Font Style
Font Size
Font Google
Font Pairings
Font Shorthand
CSS IconsCSS LinksCSS ListsCSS Tables
Table Borders
Table Size
Table Alignment
Table Style
Table Responsive
CSS DisplayCSS Max-widthCSS PositionCSS OverflowCSS Float
Float
Clear
Float Examples
CSS Inline-blockCSS AlignCSS CombinatorsCSS Pseudo-classCSS Pseudo-elementCSS OpacityCSS Navigation Bar
Navbar
Vertical Navbar
Horizontal Navbar
CSS DropdownsCSS Image GalleryCSS Image SpritesCSS Attr SelectorsCSS FormsCSS CountersCSS Website LayoutCSS UnitsCSS SpecificityCSS !important
Выравнивание контента внутри контейнера. Три способа.
При помощи flexbox мы можем без труда выравнивать элементы без всяких хитростей и магических хаков. Давайте посмотрим, как можно расположить контент внутри блока-родителя:
Способ первый
Укажем flex-контейнеру:
css
123456 |
ul { display: flex; flex-direction: row; justify-content: center; align-items: center;} |
See the Pen text-center-container-1 by Alexandr (@login2030) on CodePen.
Способ второй
css
12345678 |
ul { display: flex; flex-direction: row; justify-content: center;}li { align-self: center;} |
See the Pen text-center-container-2 by Alexandr (@login2030) on CodePen.
Способ третий
css
1234567 |
ul { display: flex; flex-direction: row;}li { margin: auto;} |
See the Pen text-center-container-3 by Alexandr (@login2030) on CodePen.
The flex-direction Property
The property defines in which direction the container
wants to stack the flex items.
Example
The value stacks the flex items vertically (from top to bottom):
.flex-container {
display: flex;
flex-direction: column;}
Example
The value stacks the flex items vertically (but from bottom to top):
.flex-container {
display: flex;
flex-direction: column-reverse;}
Example
The value stacks the flex items horizontally (from left to right):
.flex-container {
display: flex;
flex-direction: row;}
Example
The value stacks the flex items horizontally (but from right to left):
.flex-container {
display: flex;
flex-direction: row-reverse;}
Основы CSS Flexbox
Создание CSS разметки с помощью Flexbox начинается с установки необходимому HTML элементу CSS-свойства со значением или .
После этого данный элемент становится flex-контейнером, а все его непосредственные дочерние элементы – flex-элементами. При этом когда мы говорим о flexbox то подразумеваем под этим только элемент с или и все элементы непосредственно расположенные в нём. Таким образом в CSS Flexbox имеется всего два типа элементов: flex-контейнер и flex-элемент.
<style> .flex-container { display: flex; /* flex || inline-flex */ } <style> <!-- flex-контейнер --> <div class="flex-container"> <div>flex-элемент #1</div> <div>flex-элемент #2</div> <div>flex-элемент #3</div> </div>
По умолчанию flex-элементы во flex-контейнере занимают всю его высоту.
Значение или определяет то, как flex-контейнер будет представлен на странице. Если его необходимо отобразить в виде блока, то используйте значение . Если элемент необходимо представить как строку, то используйте значение . В этом случае он будет занимать столько места странице, сколько необходимо для отображения его элементов.
Устройство flex-контейнера. Направление осей
На рисунке представлена схема устройства flex-контейнера:
Направление расположение flex-элементы в flex-контейнере определяется посредством осей.
В CSS Flexbox имеются две оси. Первая ось называется главной (по умолчанию она направлена слева направо). Вторая — поперечная (по умолчанию направлена сверху вниз), она всегда перпендикулярно главной. Главная ось задаёт основное направление flex-элементов во flex-контейнере, а поперечная ось определяет их направление при переносе на новую линию.
По умолчанию элементы во flex-контейнере располагаются вдоль направления главной оси (т.е. слева направо) на одной линии.
Направление главной оси можно изменить, осуществляется это с помощью CSS-свойства .
flex-direction: row; /* row (слева направо) - по умолчанию row-reverse (справа налево) column (сверху вниз) column-reverse (снизу вверх) */
С помощью этого свойства можно сделать так, чтобы flex-элементы располагались не рядами (rows), а колонками (columns). Осуществляется это с помощью значения или .
По умолчанию flex-элементы не переносятся на новую линию, даже когда им не хватает места в текущей линии. Они просто выходят за её пределы.
Но это можно изменить. Разрешить перенос flex-элементов на новые линии осуществляется с помощью установки flex-контейнеру CSS свойства со значением или .
flex-wrap: wrap; /* nowrap (только на одной линии - по умолчанию) wrap (разрешить перенос flex-элементов на новые линии) wrap-reverse (осуществлять перенос flex-элементов в обратном порядке) */
Значения и CSS-свойства определяют направление поперечной оси.
Свойства и можно указать с помощью универсального CSS свойства :
flex-flow: row nowrap; /* 1 значение - flex-direction, 2 значение - flex-wrap */
Разница между устаревшими подходами и современными стандартами
Теперь, когда у вас есть представление о том, как проблему решали раньше, давайте взглянем, на что способны Flexbox и Grid.
Flexbox и Grid — это идеальные решения для CSS-разметки, являющиеся современными стандартами. Если вам необходимо писать CSS-код на хорошем уровне, то обязательно изучите их.
Решение задачи с помощью Flexbox
Контекст форматирования Flexbox инициализируется путем создания flex-контейнера.
Родительским элементом является . Он содержит боковую панель и основную зону. Создаём контейнер:
И получаем:
Flexbox в действии
Не забудем о пропорциях:
Вуаля! Проблему можно считать решенной:
Задача решена
С Flexbox можно делать много разных вещей:
-
Отцентрировать боковую панель и основную зону по вертикальной оси:
-
Изменить положение одного из дочерних элементов:
-
Менять порядок дочерних элементов без изменения HTML-кода:
И я затронул лишь верхушку айсберга Flexbox.
Flexbox доступен в большинстве поддерживаемых браузеров. Им можно полноценно пользоваться в Firefox с 28 версии, Chrome с 29, Safari с 6.1 и Edge с 12.
Прим. перев. Разобраться с Flexbox поможет наше наглядное введение.
Решение проблемы с помощью Grid
В отличие от Flexbox, который по большей части работает в одном измерении, с CSS Grid вы можете использовать как ряды, так и колонки. Посмотрим, как решить нашу проблему с его помощью.
Начинается всё так же, как и в случае с Flexbox. Создаём контейнер:
Вот весь CSS:
И вот что мы получим:
Первичный вариант
Grid доступен в большинстве поддерживаемых браузеров, хотя и в меньшем количестве. Им можно полноценно пользоваться в Firefox с 52 версии, Chrome с 57, Safari с 10.1 и Edge с 16.
Наше последнее изображение пока никак не отличается от предыдущих. Так в чём же магия?
Что, если мы разделим пропорции ширины, как раньше:
Пропорциональное распределение ширины для дочерних элементов
Да, результат отличается, но нам он не подходит. Боковая панель пока не расположена сбоку от главной зоны.
Вот мы и подошли к сути Grid-разметки. После инициализации Grid-контейнера при помощи необходимо определить ряды и строки внутри него.
Вот как это делается:
Решение в одну строку — красиво, не правда ли? определяет пропорции столбцов в сетке.
Задача решена
Но с помощью Grid можно сделать гораздо больше.
Сначала добавим немного цвета главному блоку, чтобы примеры были более наглядными:
Вот что мы должны получить:
Заливка цветом зоны основного контента
Посмотрим, что хорошего может предложить Grid:
-
Можно определить разрыв между столбцами:
Вот результат:
Нет необходимости в добавлении отступов к блокам и : это делает .
-
Можно сделать столько столбцов, сколько вам нужно. Примеры выше использовали только по одному элементу и . Добавим ещё два:
Grid сам понял, что нам надо — не пришлось даже трогать CSS.
-
Можно определить пробел между строками:
Для упрощения можно использовать сокращение: вместо и .
-
Можно определять размеры строк:
Теперь высота первой, второй и третьей строк равна 200, 300 и 400 пикселей соответственно.
Для начала хватит и этого — но это далеко не всё.
Что такое Flexbox на самом деле?
Спецификация Flexbox описывает метод компоновки так:
Я думаю, что ключевая фраза здесь “распределение пространства и выравнивание контента”. Flexbox — это все о том, чтобы взять кучу элементов (которые имеют разные размеры) и поместить их в контейнер (который сам может быть переменного размера). Flexbox — это мягкость. Он пытается создать наилучший макет для наших элементов, давая большим элементам больше пространства, а меньшим элементам меньше пространства, тем самым сохраняя читаемость контента.
Если люди находят Flexbox сложным и загадочным, это часто потому, что они пытаются использовать Flexbox как grid-систему, пытаясь вернуть контроль над размером и распределением пространства. Когда вы это делаете, Flexbox может показаться странным и сложным, поскольку вы боретесь с тем, что и делает его Flexbox’ом, т.е. с присущей ему гибкостью.
Поэтому шаблоны, которые очень хорошо подходят для гибкой компоновки, это те, в которых нас не так интересует наличие идеального размера каждого элемента. Мы просто хотим, чтобы эти элементы отображались рядом друг с другом.
Существуют также шаблоны, в которых вы хотите иметь строки с переносом, однако вам не нужна строгая сетка. Если мы возьмем оригинальный пример Grid против Flexbox, где мы используем в сетке синтаксис repeat auto-fill, а затем flex-контейнер с переносом строк, то сразу увидим разницу между этими двумя методами.
В примере Grid элементы сетки выстраиваются в строки и столбцы. Когда число столбцов трека изменяется (в зависимости от пространства), элементы всегда переходят в следующую доступную ячейку сетки. На самом деле, нет никакого способа запросить элемент сетки окружить трек, чтобы заполнить по auto-flow сценарию, если есть другие пустые ячейки.
В примере flex итоговые элементы разделяют пространство, оставшееся между ними, таким образом, мы не используем выравнивание по горизонтали и вертикали.
Если у нас flex-basis установлен в auto, и любой из flex-элементов увеличивается, то остальным также будет предоставлено дополнительное пространство, чтобы выравнивание могло быть различным от строки к строке.
Это очень яркий пример того, где мы хотели бы использовать Flexbox над Grid Layout. Если мы хотим, чтобы элементы были обернуты, но занимали пространство, в котором они нуждались, по строкам. Это очень отличается от сетки. Шаблоны, подобные этому, могут представлять собой набор тегов (один или два слова, которые вы хотите хорошо отображать в виде набора элементов), занимающих необходимое пространство, а не жестко вставленных в строгую сетку.
В настоящее время Flexbox также является лучшим способом выполнения вертикального и горизонтального центрирования элемента внутри контейнера.
В будущем (если будет поддержка браузерами свойств Box Alignment вне гибкого макета), мы можем сделать это, не добавляя display: flex в контейнер. На данный момент, однако, все, что вам нужно сделать, это дополнительная строка CSS, что не является проблемой.
Flexbox очень хорошо справляется с небольшими одномерными компонентами. Наборы полей формы, иконок или другой информации можно легко расположить и позволить им быть гибкими без необходимости тщательно устанавливать размеры каждого элемента.
Вы также можете выбрать Flexbox в сценарии, где контент нужно привести к низу контейнера, не давая ему всплывать. В примере, расположенном ниже, я делаю контейнер flex-контейнером, отображая содержимое в виде столбца, а затем позволяю середине расти, выталкивая footer вниз компонента.
При разработке я нахожу, что Flexbox полезен для множества небольших заданий, выполняя правильно выравнивание, распределяя пространство между элементами. Вы безусловно можете использовать одномерный контейнер сетки для некоторых из этих задач, и не беспокоится о том, что вы решили сделать.
Однако я думаю, что Flexbox будет лучшим в ситуации, когда потребуется добавлять дополнительные элементы, которые я не ожидала в своем дизайне. Например, если у меня есть компонент навигации, использующий Grid, я бы создала достаточно треков для всех элементов, так как я не хотела бы, чтобы создавалась новая строка, если бы у меня было “слишком много” элементов. С flexbox, достаточно длинным, я бы разрешил элементам быть гибкими с flex-basis 0 (или auto), тогда бы элементы сами пускали нового компаньона в строку, освобождая ему место.
Значение row-reverse
Вы можете использовать flex-direction: row-reverse, чтобы элементы в ряду отображались в обратном порядке.
<!doctype html>
<title>Пример</title>
<style>
.container {
display: flex;
flex-direction: row-reverse;
align-items: flex-start;
background: beige;
height: 100vh;
}
.red {
background: orangered;
}
.green {
background: yellowgreen;
}
.blue {
background: steelblue;
}
.container > div {
font-size: 5vw;
padding: .5em;
color: white;
}
body {
margin: 0;
}
</style>
<div class=»container»>
<div class=»red»>1</div>
<div class=»green»>2</div>
<div class=»blue»>3</div>
</div>
Реальные примеры
Применяя описанные выше свойства flexbox в различных комбинациях, можно создавать разнообразные шаблоны. Рассмотрим примеры использования Flexbox.
Меню навигации
Основное преимущество CSS flex заключается в том, что элементы могут адаптироваться. Когда размеры экрана изменяются, flexbox изменяет ширину блоков, чтобы они соответствовали родительскому контейнеру. Данная технология использует процентное значение размеров по отношению к родительскому контейнеру, что и позволяет элементам навигации легко адаптироваться к размеру экрана.
Очень просто перейти к размерам на всю ширину экрана устройства, изменив способ, с помощью которого flexbox реагирует на изменения.
Посмотрите, как в приведенном выше примере элементы реагируют на различные размеры экрана. Ниже приведен код HTML и CSS, с помощью которых можно создать адаптивное меню навигации с использованием flexbox:
<nav class="site-navigation"> <ul> <li><a href="">Home</a></li> <li><a href="">Services</a></li> <li><a href="">Products</a></li> <li><a href="">About</a></li> <li><a href="">Contact</a></li> </ul> </nav> .site-navigation ul { background: #eee; list-style: none; margin: 0; padding: 0; /** * Flexbox properties */ display: flex; justify-content: space-around; } .site-navigation a { color: #333; display: block; text-decoration: none; text-align: center; padding: 1rem; } .site-navigation a:hover { background: #d4d4d4; } @media all and (max-width: 600px) { .site-navigation ul { /** * Full width navigation items */ flex-flow: column wrap; padding: 0; } }
Столбцы одинаковой высоты
Вы можете оказаться в ситуации, когда столбец основного контента становится больше, чем столбец боковой панели. Это может привести к проблемам с отображением, если боковая панель имеет свой фоновый цвет.
Посмотрите, как можно создать столбцы одинаковой высоты с помощью CSS flex 1.
Код HTML и CSS, с помощью которых можно создать такой макет:
<div class="column-container"> <div class="column"> <p></p> <p></p> </div> <div class="column"> <p></p> </div> <div class="column"> <p></p> </div> </div> .column-container { display: flex; align-items: stretch; } .column { width: 33%; padding: 2rem; } .column:nth-child(1) { background: red; } .column:nth-child(2) { background: blue; } .column:nth-child(3) { background: green; }
В этом коде CSS единственным свойством, которое нужно задать для получения одинаковых столбцов, является align-items: stretch:
.column-container { display: flex; align-items: stretch; }
Центрирование по вертикали
Получить элемент, выровненный вертикально по центру внутри родительского элемента, ранее было непростой задачей. Это проще было сделать с помощью переходов и абсолютного позиционирования:
.vertically-align-center-child { top: 50%; transform: translateY(-50%); }
Но с помощью flexbox это делается еще проще. Для этого используются два свойства CSS flex1:justify-content и align-items.
<div class="vertical-container"> <div class="vertical-content">Look I'm Vertically Aligned</div> </div> .vertical-container { background:#eee; height: 500px; /** make it flex */ display: flex; /** Vertically center */ align-items: center; /** Horizontally center */ justify-content: center; } .vertical-content { background: #FFF; padding: 3rem; width: 20%; text-align: center; }
Изменение порядка вывода элементов с помощью медиа-запросов
Допустим, у вас есть макет страницы с заголовком, левой боковой панелью, основным контентом, правой боковой панелью и подвалом. Если при разработке мобильной версии ресурса мы зададим отображение всех разделов в полную ширину, то левая боковая панель может выводиться сверху от блока основного контента.
С помощью display flex CSS мы можем изменить порядок вывода различных разделов. Можно переместить блок основного контента перед левым сайдбаром.
Чтобы изменить порядок вывода дочерних элементов, нужно добавить для элемента свойство order и указать, на какой позиции он должен отображаться:
@media only screen and (max-width: 320px) { .site-header { order: 2; } .main-content { order: 1; width: 100%; } .left-sidebar { order: 4; width: 100%; } .right-sidebar { order: 3; width: 100%; } .site-footer { order: 5; } }
Теперь порядок размещения будет следующим:
- Основной контент;
- Заголовок;
- Правая боковая панель;
- Левая боковая панель;
- Подвал.
Просмотрите приведенную ниже демо-версию. Измените размеры окна браузера, чтобы увидеть, как меняются местами области страницы.