Kurs HTML i CSS · Moduł 4: Flexbox
Tworzenie Siatki za pomocą Flexbox
W tej lekcji10
Masz do pokazania zdjęcia skarbów z grobowca: na komputerze po kilka w rzędzie, na telefonie jedno pod drugim. Starożytni Egipcjanie byli mistrzami planowania przestrzeni, od symetrycznych kolumn w świątyniach po precyzyjne podziały pól uprawnych wzdłuż Nilu. Tworzenie siatki (grid) za pomocą Flexbox to nowoczesny odpowiednik tej umiejętności. Przeanalizujemy krok po kroku, jak zbudować responsywny układ z elastycznymi kolumnami o szerokościach w procentach, podobnie jak robią to frameworki Bootstrap czy Tailwind CSS.
Krótka historia układów stron
W latach 90. układy stron budowano z tabel HTML, choć <table> służy do danych. W latach 2000. królowały float i clear, które znasz z lokacji o CSS. Flexbox, którego specyfikacja w obecnej postaci powstała w 2012 roku, pozwolił wreszcie ustawiać elementy w rzędzie bez sztuczek, a w 2017 roku przeglądarki wprowadziły CSS Grid, stworzony specjalnie do siatek dwuwymiarowych. Siatka na Flexboksie wciąż żyje, na przykład w Bootstrapie od wersji 4.
Dwie właściwości, na których stoi siatka
Siatkę budują dwie właściwości kontenera: display: flex ustawia elementy w rzędzie, a flex-wrap: wrap pozwala im przechodzić do nowej linii. Reszta to cztery kroki w stałej kolejności: włącz display: flex, dodaj flex-wrap: wrap, określ szerokość kolumn, na przykład flex-basis: 33%, a na koniec dodaj gap dla odstępów.
Krok 1: Stwórz podstawową strukturę dokumentu HTML
Najpierw stwórz nowy plik HTML i dodaj podstawową strukturę dokumentu. Dodaj element <div> z klasą .flex-grid i kilka elementów <div> z klasą .col, które będą reprezentować kolumny w siatce:
<!DOCTYPE html>
<html lang="pl">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="styles.css"> <!-- Podłącz plik CSS -->
<title>Tworzenie Siatki za pomocą Flexbox</title>
</head>
<body>
<div class="flex-grid">
<div class="col col-6">Kolumna 1</div>
<div class="col col-6">Kolumna 2</div>
</div>
<div class="flex-grid">
<div class="col col-4">Kolumna 1</div>
<div class="col col-4">Kolumna 2</div>
<div class="col col-4">Kolumna 3</div>
</div>
<div class="flex-grid">
<div class="col col-3">Kolumna 1</div>
<div class="col col-3">Kolumna 2</div>
<div class="col col-3">Kolumna 3</div>
<div class="col col-3">Kolumna 4</div>
</div>
</body>
</html>Każdy wiersz to osobny .flex-grid. Kolumny mają wspólną klasę col i klasę liczbową, na przykład col-6, która mówi, ile z dwunastu części szerokości zajmie kolumna. W każdym wierszu liczby sumują się do 12.
Krok 2: Stwórz plik CSS
Otwórz lub utwórz nowy plik CSS i zapisz go jako styles.css. To do niego prowadzi znacznik <link> z kroku 1.
Krok 3: Stylizacja podstawowa
Dodaj podstawowe style dla elementów .flex-grid i .col, aby były widoczne na stronie. Tutaj siatka dostaje swoje dwie kluczowe właściwości:
body {
font-family: Arial, sans-serif;
margin: 0;
padding: 0;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
gap: 20px;
min-height: 100vh;
background-color: #f0f0f0;
}
.flex-grid {
display: flex;
flex-wrap: wrap;
width: 80%;
background-color: #fff;
border: 1px solid #ddd;
padding: 10px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
gap: 10px;
}
.col {
background-color: lightblue;
padding: 20px;
text-align: center;
border: 1px solid #ccc;
}body jest kontenerem flex w kolumnie i układa wiersze jeden pod drugim. Każdy .flex-grid ma display: flex, flex-wrap: wrap i gap: 10px, a .col dostaje tło, wypełnienie i ramkę, żeby było ją widać.
Krok 4: Tworzenie klas kolumn z wartościami procentowymi
Dodaj style dla klas od .col-1 do .col-12, które określą szerokość kolumn w procentach. Wzór jest prosty: liczba z nazwy klasy podzielona przez 12:
.col-1 {
flex-basis: 8.33333333%;
max-width: 8.33333333%;
}
.col-2 {
flex-basis: 16.66666667%;
max-width: 16.66666667%;
}
.col-3 {
flex-basis: 25%;
max-width: 25%;
}
.col-4 {
flex-basis: 33.33333333%;
max-width: 33.33333333%;
}
.col-5 {
flex-basis: 41.66666667%;
max-width: 41.66666667%;
}
.col-6 {
flex-basis: 50%;
max-width: 50%;
}
.col-7 {
flex-basis: 58.33333333%;
max-width: 58.33333333%;
}
.col-8 {
flex-basis: 66.66666667%;
max-width: 66.66666667%;
}
.col-9 {
flex-basis: 75%;
max-width: 75%;
}
.col-10 {
flex-basis: 83.33333333%;
max-width: 83.33333333%;
}
.col-11 {
flex-basis: 91.66666667%;
max-width: 91.66666667%;
}
.col-12 {
flex-basis: 100%;
max-width: 100%;
}flex-basis ustawia startową szerokość kolumny, a max-width działa jak bezpiecznik, gdyby ktoś dopisał kolumnie flex-grow. Dwanaście części wybrano celowo, bo 12 dzieli się przez 2, 3, 4 i 6. Jeśli nie chcesz liczyć, zostaw zapas: trzy kolumny z flex-basis: 30% przy typowych odstępach zmieszczą się w rzędzie.
Krok 5: Responsywne kolumny
Aby siatka była responsywna, możemy użyć media queries i zmieniać właściwości Flexbox w zależności od szerokości ekranu:
@media (max-width: 768px) {
.flex-grid {
flex-direction: column;
}
.col {
flex: none;
width: 100%;
}
}Na ekranach do 768 pikseli wiersz układa kolumny jedna pod drugą, a flex: none i width: 100% mają rozciągnąć je na całą szerokość.
Pułapka: padding, ramki i odstępy
Gdy otworzysz stronę, czeka cię niespodzianka: dwie kolumny col-6 nie staną obok siebie. Domyślnie flex-basis i max-width liczą samą treść kolumny, więc wypełnienie i ramka doliczają się do 50%, a do tego dochodzi odstęp. Suma przekracza 100% i druga kolumna spada do nowej linii. Na telefonie z kolei max-width z klas kolumn dalej obowiązuje. Naprawiają to trzy zmiany dopisane na końcu styles.css:
*,
*::before,
*::after {
box-sizing: border-box;
}
.col-3 { flex-basis: calc(25% - 7.5px); max-width: calc(25% - 7.5px); }
.col-4 { flex-basis: calc(33.333% - 6.667px); max-width: calc(33.333% - 6.667px); }
.col-6 { flex-basis: calc(50% - 5px); max-width: calc(50% - 5px); }
@media (max-width: 768px) {
.col {
max-width: 100%;
}
}box-sizing: border-box, znane z lekcji o modelu pudełkowym, wlicza wypełnienie i ramkę do szerokości. Od każdej kolumny odejmujemy jej udział w odstępach, na przykład dwie kolumny col-6 dzielą jeden odstęp, więc każda oddaje 5 pikseli. Na telefonie max-width: 100% zdejmuje ograniczenie. Wzór na takie obliczenia poznasz w lekcji o gap.
Wynik
Po wykonaniu kroków od 1 do 5 twoje pliki powinny wyglądać następująco. Poprawki z poprzedniej sekcji dopisz na samym końcu arkusza, żeby nadpisały wcześniejsze reguły.
Plik HTML (index.html)
Plik HTML pozostaje bez zmian, to wciąż trzy wiersze z kolumnami:
<!DOCTYPE html>
<html lang="pl">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="styles.css"> <!-- Podłącz plik CSS -->
<title>Tworzenie Siatki za pomocą Flexbox</title>
</head>
<body>
<div class="flex-grid">
<div class="col col-6">Kolumna 1</div>
<div class="col col-6">Kolumna 2</div>
</div>
<div class="flex-grid">
<div class="col col-4">Kolumna 1</div>
<div class="col col-4">Kolumna 2</div>
<div class="col col-4">Kolumna 3</div>
</div>
<div class="flex-grid">
<div class="col col-3">Kolumna 1</div>
<div class="col col-3">Kolumna 2</div>
<div class="col col-3">Kolumna 3</div>
<div class="col col-3">Kolumna 4</div>
</div>
</body>
</html>Plik CSS (styles.css)
Arkusz zbiera wszystkie reguły z kroków 3, 4 i 5 w jednym miejscu, w tej samej kolejności, w jakiej je pisałeś:
body {
font-family: Arial, sans-serif;
margin: 0;
padding: 0;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
gap: 20px;
min-height: 100vh;
background-color: #f0f0f0;
}
.flex-grid {
display: flex;
flex-wrap: wrap;
width: 80%;
background-color: #fff;
border: 1px solid #ddd;
padding: 10px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
gap: 10px;
}
.col {
background-color: lightblue;
padding: 20px;
text-align: center;
border: 1px solid #ccc;
}
.col-1 {
flex-basis: 8.33333333%;
max-width: 8.33333333%;
}
.col-2 {
flex-basis: 16.66666667%;
max-width: 16.66666667%;
}
.col-3 {
flex-basis: 25%;
max-width: 25%;
}
.col-4 {
flex-basis: 33.33333333%;
max-width: 33.33333333%;
}
.col-5 {
flex-basis: 41.66666667%;
max-width: 41.66666667%;
}
.col-6 {
flex-basis: 50%;
max-width: 50%;
}
.col-7 {
flex-basis: 58.33333333%;
max-width: 58.33333333%;
}
.col-8 {
flex-basis: 66.66666667%;
max-width: 66.66666667%;
}
.col-9 {
flex-basis: 75%;
max-width: 75%;
}
.col-10 {
flex-basis: 83.33333333%;
max-width: 83.33333333%;
}
.col-11 {
flex-basis: 91.66666667%;
max-width: 91.66666667%;
}
.col-12 {
flex-basis: 100%;
max-width: 100%;
}
@media (max-width: 768px) {
.flex-grid {
flex-direction: column;
}
.col {
flex: none;
width: 100%;
}
}Kolejność reguł ma znaczenie: media query stoi na końcu, więc na telefonie nadpisuje wcześniejsze ustawienia kolumn. Z tego samego powodu poprawki trafiają za nią. Moja rada: gdy układ potrzebuje wierszy i kolumn naraz, sięgnij po CSS Grid, a siatkę na Flexboksie zostaw dla prostych rzędów.
Zadanie dodatkowe
- Dodaj więcej kolumn i eksperymentuj z różnymi wartościami
flex-basisimax-width, aby zobaczyć, jak zmienia się układ siatki. - Przetestuj swoje umiejętności, tworząc bardziej złożone układy z użyciem różnych kombinacji właściwości Flexbox.
- Dodaj różne style do swojej siatki, np. zmieniając kolory, rozmiary czcionek i inne właściwości elementów, aby lepiej zrozumieć, jak działają różne opcje Flexboxa.
Wypróbuj siatkę w edytorze poniżej. Zobaczysz ją od innej strony: kontenery mają flex-wrap: wrap i stałą wysokość, więc elementy układają się w kilka linii, a align-content decyduje, jak te linie rozłożą się w pionie.
Kod do tej lekcji: index.html
<!DOCTYPE html>
<html lang="pl">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flexbox - Align Content</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<div class="container">
<h1>Align Content - Rozmieszczanie linii</h1>
<p class="subtitle">Kontroluj rozkład LINII elementów w kontenerze z flex-wrap</p>
<section class="demo-section">
<h2>align-content: flex-start</h2>
<div class="flex-container align-start">
<div class="flex-item">1</div>
<div class="flex-item">2</div>
<div class="flex-item">3</div>
<div class="flex-item">4</div>
<div class="flex-item">5</div>
<div class="flex-item">6</div>
</div>
<p class="description">Linie są grupowane na początku kontenera</p>
</section>
<section class="demo-section">
<h2>align-content: center</h2>
<div class="flex-container align-center">
<div class="flex-item">1</div>
<div class="flex-item">2</div>
<div class="flex-item">3</div>
<div class="flex-item">4</div>
<div class="flex-item">5</div>
<div class="flex-item">6</div>
</div>
<p class="description">Linie są wycentrowane w kontenerze</p>
</section>
<section class="demo-section">
<h2>align-content: space-between</h2>
<div class="flex-container align-between">
<div class="flex-item">1</div>
<div class="flex-item">2</div>
<div class="flex-item">3</div>
<div class="flex-item">4</div>
<div class="flex-item">5</div>
<div class="flex-item">6</div>
</div>
<p class="description">Pierwsza linia na górze, ostatnia na dole, równe odstępy między</p>
</section>
<section class="demo-section">
<h2>align-content: space-around</h2>
<div class="flex-container align-around">
<div class="flex-item">1</div>
<div class="flex-item">2</div>
<div class="flex-item">3</div>
<div class="flex-item">4</div>
<div class="flex-item">5</div>
<div class="flex-item">6</div>
</div>
<p class="description">Równe odstępy wokół każdej linii</p>
</section>
<section class="demo-section practice">
<h2>Praktyka: Egipska półka ze skarbami</h2>
<p class="practice-description">Rozmieszczamy skarby faraona na półkach</p>
<div class="shelf-container">
<div class="shelf">
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
<div class="treasure">◆</div>
</div>
</div>
<div class="controls">
<button onclick="changeAlign('flex-start')">Start</button>
<button onclick="changeAlign('center')">Center</button>
<button onclick="changeAlign('space-between')">Between</button>
<button onclick="changeAlign('space-around')">Around</button>
</div>
</section>
</div>
<script>
function changeAlign(value) {
document.querySelector('.shelf').style.alignContent = value;
}
</script>
</body>
</html>Pamiętaj: siatka na Flexboksie to pole nad Nilem podzielone na dwanaście równych części, gdzie flex-wrap: wrap pozwala zaczynać nowe rzędy, a procenty mówią, ile ziemi dostaje każda kolumna.
Hasła z dokumentacji w tej lekcji
Widzisz błąd w tej lekcji?
Sprawdź się
Odpowiedz na pytania z tej lekcji. Wybierz odpowiedź, a od razu zobaczysz, czy jest poprawna.
1. Jakie dwie właściwości są niezbędne do stworzenia siatki (gridu) za pomocą Flexbox?
Zadania praktyczne w grze
- Układanie w pionie
Ułóż kroki tworzenia responsywnej siatki za pomocą Flexbox:
- Edytor kodu
Stwórz siatkę 3 kolumn z 6 elementami używając display: flex, flex-wrap: wrap i flex-basis: 30% na elementach potomnych.
- Klikanie w kolejności
Ułóż skrótową deklarację flex (grow: 1, shrink: 0, basis: 200px):
- Układanie w pionie
Ułóż metody tworzenia układu strony w CSS w kolejności chronologicznej: