Використання Flexbox в CSS3 для адаптивного дизайну
У цій статті ми хочемо більш детально зупинитися на використанні flexbox в CSS3, в якості одного з просунутих способів досягнення адаптивності на сайті.
При створенні CSS складність макетів була не такою, якою вона буває в наші дні. Раніше макети були з фіксованою шириною і невеликими варіаціями розташування блоків, а сьогодні макети сайтів можуть набувати практично будь-яких обрисів. Все це змушує розробників придумувати хаки для CSS, щоб контент відображався більш-менш правильно.
Flexbox (гнучкі коробки) – це відносно новий режим розмітки в CSS3, призначений для поліпшення вирівнювання, напрямку та порядку елементів в контейнері, навіть якщо він є динамічним або з невідомими розмірами. Це найважливіша особливість – можливість змінювати ширину або висоту дочірніх елементів в блоці, щоб найкращим чином заповнити обсяг контейнера, доступний при різних розмірах екрану.
Що таке Flexbox?
Flexbox – це режим розмітки, створений для впорядкування елементів на сторінці таким чином, щоб вони вели себе передбачувано для випадків адаптивності сторінки під різні розміри екрану і для різних пристроїв.
Використовуючи flexbox, контейнер і його дочірні елементи можуть бути розташовані в будь-якому напрямку: вліво, вправо і навіть вгору або вниз. Ви можете вибрати потрібний порядок елементів на сторінці та впорядкувати їх, вирівняти вміст по ширині справа наліво за допомогою однієї властивості, і навіть додати будь-яку кількість стовпців в розмітку сторінки свого сайту. Розмір блоків також є гнучким, оскільки елементи можуть збільшуватися, щоб зайняти вільний простір, або стискатися, щоб не допустити переповнення.
На даний момент flexbox підтримується практично всіма сучасними браузерами, включаючи Android і iOS.
Коли використовувати Flexbox при верстці макету
В одній з попередніх статей ми писали про використання сіток в якості методу для респонсивного дизайну. Хоча за допомогою Flexbox технічно можна зверстати повний макет для сайту, він не призначений виключно для цієї мети. Швидше, він краще підходить для стилізації окремих контейнерів, таких як контейнер основного контенту, бічна панель (сайдбар), хедер та інших подібних розділів. Все ж сітки краще підходять для створення всього макету.
Різниця полягає в тому, як flexbox взаємодіє з браузерами, в яких завантаження сторінки відбувається поступово. Спочатку контент розтягується горизонтально, щоб заповнити весь екран. У міру завантаження всіх інших контейнерів горизонтальне відображення динамічно налаштовується і стискається для заповнення всієї ширини екрану, щоб включити оточуючі елементи.
Іншими словами користувач на долю секунди побачить зовсім не той макет, який планувався. Але після повного завантаження сторінки все, звичайно ж, вирівнюється.
Контейнери, дочірні елементи і Flex
Перш ніж ми почнемо писати код CSS з використанням flexbox, є деякі важливі концепції, з якими в першу чергу потрібно ознайомитися:
- flexbox – контейнер стає flexbox після того, як підключається властивість
display
із значеннямflex
абоinline-flex
- flex item – дочірній елемент в flexbox
- головна вісь (main axis) – це головна вісь, уздовж якої вирівнюються елементи
- перехресна вісь (cross axis) – вісь, перпендикулярна до головної осі. Також називається поперечною віссю
- головний початок/головний кінець (main-start/main-end) – флекс елементи додаються до контейнера, який починається з боку головного початку, і закінчується до головного кінця
- перехресний початок і кінець (cross start/end) – флекс лінії заповнюються items (елементами) і поміщаються в контейнер, який починається з боку перехресного початку флекс контейнера та йде до перехресного кінця
- властивість основного розміру (main size) – ширина або висота флекс елемента, в залежності від того, що знаходиться в основному вимірі головної осі, є основним розміром елемента. Властивість основного розміру елемента flex – це властивість ширини або висоти, в залежності від того, що знаходиться в основному вимірі
- властивість перехресного розміру (cross size) – ширина або висота флекс елемента, в залежності від того, що знаходиться в вимірі поперечної осі, є перехресним розміром елемента. Властивість перехресного розміру залежить від ширини або висоти елементів, що знаходяться в поперечному вимірі
В CSS є певні властивості, на які не впливає властивість flexbox, оскільки вони фактично не роблять контейнери блоками:
column-* float clear vertical-align ::first-line та ::first-letter
Створення HTML5 контейнера
Тепер ми можемо почати будувати макет, використовуючи flexbox. Для цього створіть кістяк html-сторінки (або ж в php
, якщо ви використовуєте CMS).
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Заголовок сторінки</title> </head> <body> </body> </html>
Створіть батьківський контейнер div
всередині body
:
<div class="content"> </div>
Усередині цього контейнера ви можете додати будь-який контент.
Для тесту я створю три блоки з невеликою інформацією, і блок з основним контентом під ними.
<div class="content"> <div class="blok">Блок інформації №1</div> <div class="blok">Блок інформації №2</div> <div class="blok">Блок інформації №3</div> <article>Тут основний контент.</article> </div>
Тепер, щоб надати цьому кістяку деяких фарб, додамо кілька основних стилів CSS (ви можете це зробити за допомогою окремого підключеного файлу css стилів, або ж заключити ці стилі в тег <style></style>
в розділі head
).
Створення і стилізація Flexbox
Щоб створити flexbox, нам потрібно визначити властивість display
для потрібного контейнера. У нашому прикладі це властивість для батьківського елемента:
.content { display: flex; }
Цей крок створить flexbox
на рівні блоку. В якості альтернативи (якщо ви хочете застосувати inline стилі) ви можете використовувати inline-flex
замість flex
.
Тепер додамо трохи CSS стилів, щоб протестувати роботу нашого створеного flexbox.
Стилі для респонсивності
Є багато властивостей, які ми можемо включити для flexbox, щоб створити адаптивний макет.
Щоб розмістити флекс елементи в потрібному порядку, досить додати властивість order
і короткий запис властивості flex
.
.blok { order: 1; flex: 1 1 30%; } article { order: 2; flex: 1 1 auto; }
Спочатку все це може здатися трохи важким, але практика розставить все на свої місця.
Властивості order
передається номер, щоб повідомити браузеру, який флекс елемент відображати перед іншими. Для order
з номером 1
– флекс елемент буде показуватися першим. Для 2 – другим, для 3 – третім, і так далі.
Ви також можете використовувати негативні числа. Якщо ви раптом зрозумієте при верстці, що вам потрібно додати флекс елемент перед першим, який вже розміщений, ви можете встановити новому флекс елементу властивість order: -1;
.
Короткий запис flex
складається з трьох властивостей:
flex-grow
– визначає, яку частину вільного простору може зайняти контейнер, в співвідношенні з іншими контейнерами. Це може бути тільки позитивне числоflex-shrink
– властивість, яка визначає фактор стиснення flex елемента. Flex елементи будуть заповнювати контейнер за значеннямflex-shrink
, коли стандартна ширина flex елементів ширше, ніж flex контейнер. Негативні числа не мають впливуflex-basis
– початковий розмір флекс елемента до застосування будь-яких флекс розмірів і перед тим, як буде зайнято вільний простір, або при нестачі місця. Може бути задано в пікселях або відсотках
Деякі пояснення по короткому записові властивості:
flex: initial
абоflex: 0 1 auto
– цей параметр робить розмір флекс елемента відносним вмісту, який знаходиться всередині нього. Він збільшується, якщо багато контенту і стискається, якщо контенту небагато.flex: auto
абоflex: 1 1 auto
– будь-який з цих параметрів дозволяє флекс елементу стискатися і збільшуватися в міру необхідності, щоб підлаштовуватися під будь-який розмір екрану.flex: none
абоflex: 0 0 auto
– це відключає гнучкість розміру і встановлює розмір флекс елемента фіксованим і нерегульованим для користувача при будь-якому розмірі екрану.- Відносний гнучкий розмір з
flex: 1 % px
. Позитивне число спочатку встановлює частину вільного місця, яке флекс елемент займає щодо інших флекс елементів. Другий номер дозволяє зменшити розмір елемента на менших екранах. Третє значення в пікселях (або відсотках) встановлює початковий розмір елемента flex, але майте на увазі, що це значення також відключає властивістьflex-basis
, що означає, що цей початковий розмір не гарантується. Якщо для відображення цього початкового розміру є достатньо місця, то він показується, але якщо місця недостатньо, то він не відображається. Це особливо вірно, якщо порядок показу елемента знаходиться нижче в списку, а інші попередні елементи вище в порядку займають більшу частину простору. Прикладом цього параметра будеflex: 2 1 0%
.
Щоб будь-який з цих параметрів спрацював, вам потрібно спочатку встановити розмір flexbox`а із зазначенням висоти і ширини.
Ґрунтуючись на прикладі CSS-стилів вище, ось як можуть виглядати стилі CSS для flexbox з додаванням розміру:
.content { display: flex; width: 75%; height: 450px; }
За допомогою цих стилів всі флекс елементи в прикладі відображаються в одному рядку. Оскільки я хочу відобразити флекс елементи в один ряд, а основний контент під ними, мені потрібно додати властивість flex-flow
і встановити його значення для перенесення вмісту в рядках.
Щоб виконати цю функцію, мені потрібно додати цю властивість для flexbox контейнера:
.content { display: flex; flex-flow: row wrap; /* флекс елементи заповнюють собою рядок (row) */ width: 75%; height: 450px; }
Коли один або кілька флекс елементів займають собою всю ширину flexbox, інші флекс елементи, що йдуть після них, переміщаються на новий рядок.
Тепер, щоб більш-менш розуміти, де який блок, і які він має розміри, додамо кілька додаткових стилів. Також, весь текстовий контент ми уклали в тег p
і додали цьому тегу кілька стилів:
<div class="content"> <div class="blok"><p>Блок інформації №1</p></div> <div class="blok"><p>Блок інформації №2</p></div> <div class="blok"><p>Блок інформації №3</p></div> <article><p>Тут основний контент.</p></article> </div>
Стилі CSS:
.content { display: flex; flex-flow: row wrap; /* флекс елементи заповнюють собою рядок (row) */ width: 75%; height: 450px; margin: auto; background-color: #333; } .blok { order: 1; flex: 1 1 30%; background-color: #ccc; margin: 5px; } article { order: 2; flex: 1 1 auto; background-color: #bbb; border: 5px solid #333; padding: 7px; } p { color: #fff; padding: 15px; font-size: 22px; }
І не забувайте, що якщо ви вирішите додати властивість min-width
flexbox`у або флекс елементам, це може привести до того, що flexbox не працюватиме належним чином. Також, для адаптивності дизайну, краще використовувати ширину основного контейнера з використанням відсотків. Якщо задати жорсткі значення в пікселях, для маленьких екранів адаптивність не спрацює.
Нижче представлено демо фінального результату:
Спробуйте погратися з різними стилями, щоб краще зрозуміти на практиці роботу flexbox.
Іншим варіантом досягти адаптивності є використання макету сіток Grid Layout в CSS стилях. Рекомендуємо ознайомитись!