Chapitre 7 : Fondamentaux du modèle Flexbox : Axes et Alignements
Concepts clés : flex-direction, justify-content, align-items
Le modèle Flexbox (Flexible Box Layout) a révolutionné la manière dont nous concevons les interfaces web. Avant son arrivée, nous devions jongler avec des float, des display: table ou des calculs de marges complexes pour aligner des éléments. Flexbox a été conçu pour résoudre un problème précis : distribuer l'espace et aligner des éléments au sein d'un conteneur, même lorsque leurs dimensions sont inconnues ou dynamiques.
Le Concept d'Axes et le Conteneur Flex
1. Quoi
Pour comprendre Flexbox, il faut oublier la notion de "haut", "bas", "gauche" et "droite". Flexbox fonctionne avec un système de deux axes perpendiculaires :
- L'Axe Principal (Main Axis) : C'est l'axe le long duquel les éléments sont disposés. Par défaut, il est horizontal (de gauche à droite).
- L'Axe Secondaire (Cross Axis) : C'est l'axe perpendiculaire à l'axe principal. Par défaut, il est vertical (de haut en bas).
Le déclencheur de tout ce système est la propriété display: flex (ou inline-flex) appliquée à l'élément parent. Cet élément devient alors le Flex Container, et ses enfants directs deviennent des Flex Items.
2. Pourquoi
Dans un projet professionnel, vous rencontrerez constamment des besoins de mise en page dynamiques :
- Une barre de navigation où le logo est à gauche et les liens à droite.
- Un bloc de contenu dont le bouton doit toujours rester en bas, quelle que soit la longueur du texte.
- Une grille de cartes qui doit s'adapter à la taille de l'écran sans casser la mise en page.
L'approche par axes permet de définir des règles d'alignement qui restent valides, même si vous décidez de passer votre mise en page d'une ligne (horizontale) à une colonne (verticale) pour le mobile.
3. Comment
A. Syntaxe de base
La propriété flex-direction définit l'orientation de l'axe principal, c'est-à-dire la direction dans laquelle les flex items sont disposés les uns après les autres. Elle accepte quatre valeurs :
row(par défaut) : Les éléments s'alignent de gauche à droite.row-reverse: Les éléments s'alignent de droite à gauche.column: Les éléments s'empilent de haut en bas.column-reverse: Les éléments s'empilent de bas en haut.
Choisir la bonne direction est le premier geste à poser avant de régler l'alignement, car elle détermine quel axe est "principal" et donc le comportement de justify-content et align-items.
.container {
display: flex; /* Active le contexte flex */
flex-direction: row; /* Axe principal = horizontal (par défaut) */
}
B. Cas concret : Le changement de direction
Imaginons un composant de profil utilisateur. Sur ordinateur, les informations sont côte à côte. Sur mobile, elles s'empilent.
/* Style du conteneur parent */
.profile-card {
display: flex;
padding: 1.25rem;
gap: 1.25rem; /* Espace moderne entre les items */
border: 1px solid #ddd;
border-radius: 8px;
/* Par défaut : Axe principal horizontal */
flex-direction: row;
}
/* Adaptation mobile via Media Query */
@media (max-width: 600px) {
.profile-card {
/* L'axe principal devient vertical */
/* L'axe secondaire devient horizontal */
flex-direction: column;
}
}
C. Limitations
- Portée directe : Flexbox ne s'applique qu'aux enfants directs du conteneur. Si vous avez un élément imbriqué dans un enfant, il ne sera pas "flex" à moins que cet enfant ne devienne lui-même un
display: flex. - Dimensionnalité : Flexbox est conçu pour des mises en page unidimensionnelles (soit une ligne, soit une colonne). Pour des grilles complexes en deux dimensions, CSS Grid est l'outil approprié.
4. Zone de Danger
❌ L'erreur classique : Penser que justify-content aligne toujours horizontalement.
✅ La bonne pratique : Se rappeler que justify-content aligne toujours sur l'Axe Principal. Si flex-direction est column, justify-content alignera vos éléments verticalement.
Relation entre flex-direction et les Axes
L'Alignement sur l'Axe Principal : justify-content
1. Quoi
La propriété justify-content définit comment les éléments sont distribués le long de l'axe principal lorsque cet axe dispose de plus d'espace que la somme des tailles des éléments.
2. Pourquoi
C'est l'outil indispensable pour créer des espacements proportionnels et propres sans utiliser de margin-left: 20px ou de text-align: center qui ne fonctionnent pas toujours sur les blocs.
3. Comment
A. Syntaxe de base
.container {
display: flex;
justify-content: center; /* Centre les éléments sur l'axe principal */
}
B. Les valeurs essentielles en production
| Valeur | Effet | Cas d'usage type |
|---|---|---|
flex-start | Aligne au début de l'axe | Menu aligné à gauche |
flex-end | Aligne à la fin de l'axe | Boutons d'action alignés à droite |
center | Centre les éléments | Titre de section ou loader |
space-between | Espace maximum entre les éléments | Logo à gauche, Menu à droite |
space-around | Espace égal autour de chaque élément | Galerie de photos simple |
space-evenly | Espace strictement identique partout | Barre d'outils équilibrée |
C. Exemple robuste : La barre de navigation
.navbar {
display: flex;
justify-content: space-between; /* Pousse le logo et le menu aux extrémités */
align-items: center; /* Aligne verticalement (voir section suivante) */
padding: 0 2rem;
height: 60px;
background-color: #2c3e50;
color: white;
}
.nav-links {
display: flex;
gap: 1.5rem;
list-style: none;
}
4. Zone de Danger
❌ L'erreur classique : Utiliser justify-content: center et s'étonner que les éléments ne soient pas centrés verticalement.
✅ La bonne pratique : Vérifiez votre flex-direction. Si vous voulez centrer verticalement avec justify-content, vous devez être en flex-direction: column.
L'Alignement sur l'Axe Secondaire : align-items
1. Quoi
La propriété align-items définit l'alignement des éléments sur l'axe secondaire (Cross Axis). Elle contrôle comment les items se positionnent par rapport à la ligne de Flexbox.
2. Pourquoi
C'est la solution définitive au problème historique du "centrage vertical en CSS". Elle permet d'aligner des éléments de hauteurs différentes sur une même ligne de manière harmonieuse.
3. Comment
A. Syntaxe de base
.container {
display: flex;
align-items: center; /* Centre les éléments sur l'axe secondaire */
}
B. Les valeurs essentielles
stretch(par défaut) : Les éléments s'étirent pour remplir toute la hauteur du conteneur (si aucune hauteur fixe n'est définie sur l'item).center: Les éléments sont centrés sur l'axe secondaire.flex-start: Les éléments sont collés au début de l'axe secondaire.flex-end: Les éléments sont collés à la fin de l'axe secondaire.baseline: Les éléments s'alignent sur la ligne de base de leur texte (très utile pour des polices de tailles différentes).
C. Cas concret : L'alignement d'icônes et de texte
.input-group {
display: flex;
align-items: center; /* Assure que l'icône et l'input sont parfaitement alignés */
border: 1px solid #ccc;
border-radius: 4px;
padding: 0.5rem;
}
.search-icon {
width: 1.25rem;
height: 1.25rem;
margin-right: 0.5rem;
}
.search-input {
border: none;
outline: none;
flex-grow: 1; /* L'input prend tout l'espace restant */
}
4. Zone de Danger
❌ L'erreur classique : Appliquer align-items: center sur un conteneur qui a la même hauteur que son contenu.
✅ La bonne pratique : Pour que align-items soit visible, le conteneur doit avoir une hauteur (ou une largeur en mode column) supérieure à celle de ses enfants. Si le conteneur "colle" à ses enfants, vous ne verrez aucun mouvement.
Questions clés
1. Quelle est la différence fondamentale entre justify-content et align-items ?
Découvrir la réponse
justify-content gère l'alignement sur l'axe principal (Main Axis), tandis que align-items gère l'alignement sur l'axe secondaire (Cross Axis). Leur comportement change donc selon la valeur de flex-direction.
2. Si je définis flex-direction: column, comment puis-je centrer mes éléments horizontalement ?
Découvrir la réponse
Puisque l'axe principal est maintenant vertical, l'axe secondaire devient horizontal. Il faut donc utiliser align-items: center.
3. Que se passe-t-il si je n'utilise aucune propriété d'alignement ?
Découvrir la réponse
Par défaut, justify-content est à flex-start (les éléments sont collés au début) et align-items est à stretch (les éléments s'étirent pour remplir la hauteur du conteneur).
4. Pourquoi mes éléments ne se centrent-ils pas verticalement avec align-items: center ?
Découvrir la réponse
C'est généralement parce que le conteneur flex n'a pas de hauteur définie. S'il fait la même taille que son contenu, le centrage est mathématiquement invisible. Ajoutez un height ou un min-height au conteneur.
Mise en pratique
Exercice 1 : Reproduction guidée
Objectif : Créer une barre d'outils simple.
- Un conteneur avec un fond gris clair.
- Trois boutons à l'intérieur.
- Les boutons doivent être parfaitement centrés horizontalement et verticalement.
- Le conteneur doit avoir une hauteur de
80px.
Découvrir la solution commentée
.toolbar {
display: flex;
/* Axe principal = horizontal par défaut, on centre */
justify-content: center;
/* Axe secondaire = vertical, on centre */
align-items: center;
height: 5rem;
background-color: #f0f0f0;
gap: 0.5rem;
}
Exercice 2 : Adaptation
Objectif : Transformer une liste de liens en menu "Split".
- Vous avez un conteneur
.nav. - À l'intérieur, un élément
.logoet un élément.menu-links. - Le logo doit être collé à gauche, et le groupe de liens doit être collé à droite.
- Sur mobile (max-width: 480px), tout doit être centré verticalement et empilé.
Découvrir la solution commentée
.nav {
display: flex;
/* Pousse les enfants aux extrémités opposées */
justify-content: space-between;
align-items: center;
padding: 1rem;
}
.menu-links {
display: flex;
gap: 1rem;
}
@media (max-width: 480px) {
.nav {
/* On change l'axe principal en vertical */
flex-direction: column;
/* On centre maintenant sur l'axe principal (vertical) */
justify-content: center;
/* On centre sur l'axe secondaire (horizontal) */
align-items: center;
gap: 1.25rem;
}
}
Exercice 3 : Conception
Objectif : Créer un composant "Card Footer".
- Une carte avec un contenu variable.
- Le footer de la carte doit contenir un texte "Publié le 12 Octobre" à gauche et un bouton "Lire la suite" à droite.
- Le texte et le bouton doivent être parfaitement alignés sur leur ligne de base (baseline) pour éviter les décalages visuels si les tailles de police diffèrent.
Découvrir la solution commentée
.card-footer {
display: flex;
/* Distribution aux extrémités */
justify-content: space-between;
/* align-items: baseline est crucial ici pour que le texte
et le bouton soient alignés sur le bas des lettres,
peu importe leur taille */
align-items: baseline;
padding: 1rem 0;
border-top: 1px solid #eee;
}
.footer-date {
font-size: 0.85rem;
color: #666;
}
.footer-btn {
font-size: 1rem;
font-weight: bold;
cursor: pointer; /* Affiche une main au survol pour signaler un élément cliquable */
}