Les **flexbox** sont un dispositif de mise en page introduit avec le *CSS3* pour faciliter l'organisation des contenus. Ils remplacent avantageusement les mécanismes basés sur `float` utilisés en **CSS2**.
## préambule
Voice le code de base que nous allons faire évoluer tout au long de l'article :
```html
<!-- Code CSS -->
<divclass="conteneur">
<divclass="element orange">A</div>
<divclass="element jaune">B</div>
<divclass="element cyan">C</div>
<divclass="element rouge">D</div>
<divclass="element vert">E</div>
</div>
```
```css
/**** MISE en PAGE ****/
.conteneur{
/* Y'aura du code ici... */
}
.element{
/* ... et là */
}
/**** MISE en FORME ****/
/* Cette partie sert uniquement à gérer l'apparence afin
de rendre le résultat plus 'visuel' */
.conteneur{
background:purple;
padding:1em;
}
.elem{
font-size:2em;
}
.orange{background:orange;}
.jaune{background:yellow;}
.cyan{background:cyan;}
.rouge{background:red;}
.vert{background:green;}
```
Ce qui donne :

## Les bases
### flex et inline-flex
Le modèle de boîte doit s'activer **sur l'élément conteneur** (celui qui contient les éléments à mettre en page), en renseignant la valeur `display` avec les valeurs `flex` ou `inline-flex` .
```css
/**** MISE en PAGE ****/
.conteneur{
display:flex;
}
```

La valeur `inline-flex` ajoute un compotement **inline** au conteneur :
```css
/**** MISE en PAGE ****/
.conteneur{
display:inline-flex;
}
```

L'activation des *flexbox* se déclenche en utilisant les valeurs :
*`flex` : le conteneur se comporte comme un **block**
*`inline-flex` : le conteneur se comporte comme un élément **inline**
### Gérer la direction avec `flex-direction`
La propriété `flex-direction` permet de fixer le comportement général des éléments dans le conteneur. par défaut, les éléments s'affichent en ligne (valeur `row`).
```css
/**** MISE en PAGE ****/
.conteneur{
display:inline-flex;
flex-direction:row;
}
```
Les valeurs disponibles sont :
*`row`*(par défaut)* Le conteneur se comporte comme une ligne d'éléments alignés à gauche dans le sens de la lecture,
*`row-reverse` Les éléments sont alignés à droite et sont inversés
*`column` Le conteneur se comporte comme une colonne, les éléments sont affichés de haut en bas
*`column-reverse` Idem, mais les éléments sont inversés
A noter que la valeur `column-reverse` justify les éléments en bas du conteneur. Vous pouvez le vérifier en appliquant arbitrairement une hauteur à ce dernier : `height: 250px`
```css
/**** MISE en PAGE ****/
.conteneur{
display:flex;
flex-direction:column-reverse;
height:250px;
}
```

### Réorganiser les éléments avec `order`
La propriété `order` permet de modifier l'ordre d'affichage d'un élément spécifique. Par défaut, cette valeur est fixée à 0, mais elle peut être modifié sur chaque éléments pour réorganiser l'enchainement des éléments dans le conteneur.
```css
.conteneur{
display:flex;
}
.rouge{
order:-1;
}
```

Vous pouvez ainsi complètement modifier la disposition des éléments dans le conteneur.
### Emballage des éléments avec `flex-wrap`
Dans notre exemple, les éléments ont assez de place pour tenir dans le conteneur car ils comportent peu de contenu. Mais il faut garder à l'esprit que la règle **le contenu l'emporte** s'applique également aux flexbox :
Ajouter un peu de contenu dans les éléments HTML :
```html
<divclass="conteneur">
<divclass="element orange">ORANGE</div>
<divclass="element jaune">JAUNE</div>
<divclass="element cyan">CYAN</div>
<divclass="element rouge">ROUGE</div>
<divclass="element vert">VERT</div>
</div>
```
Puis réduisez la largeur de la fenêtre en largeur, vous verrez le contenu disparaître vers la droite :

La propriétés `flex-wrap` (*nowrap*, `wrap`, `wrap-reverse`) va forcer la *flexbox* à adapter l'embalage.
La valeur `wrap` va autoriser la flexbox à ajouter des lignes (ou des colonnes) pour garantir l'affichage du contenu :
```css
.conteneur{
display:flex;
flex-wrap:wrap;
}
```

La valeur wrap-reverse inverse la disposition des lignes.
A noter que `flex-wrap` ne semble pas donner de résultat si `flex-direction` est réglé sur `column`. Mais il a bien un effet, pour l'observer, ajouter une hauteur au conteneur :
```css
.conteneur{
display:flex;
flex-direction:column;
flex-wrap:wrap;
height:7em;
}
```
## Gérer la taille des éléments
La taille des éléments d'un flexbox s'ajuste avec 3 propriétés :
*`flex-grow` : Agrandissement
*`flex-shrink` : Contraction
*`flex-basis` : Taille optimale
*`flex` : Forme compacte de ces 3 propriétés
### Élargir les éléments avec `flex-grow`
La propriété `flex-grow` permet, au sein d'un item, de définir la façon dont la taille de l'élément peut être élargi. Par défaut, `flex-grow` est fixé à 0, donc les éléments ne s'élargissent, leurs taille maximum correspond à leur taille initiale.
En mettant la valeur 1 à tout les éléments, la *flexbox* va recalculer la largeur des éléments en équilibrant leur occupation (tous à la même taille) pour occuper toute la largeur disponible dans le conteneur :
```css
.conteneur{
display:flex;
}
.element{
flex-grow:1;
}
```

En jouant sur la largeur de la fenêtre, vous verrez la largeur des éléments s'adapter en fonction de l'espace disponible. Vous pouvez constater que la largeur est identique pour chaques éléments, peut importe son contenu.
Vous pouvez ensuite jouer avec la valeur de `flex-grow` (qui doit être un entier strictement positif) pour répartir la distribution de l'espace disponible différement en fonction de l'élément :
```css
.conteneur{
display:flex;
}
.element{
flex-grow:1;
}
.orange{
/* orange sera 3 fois plus grand que les autres */
flex-grow:3;
}
.vert{
/* Vert n'est pas autorisé à grandir */
flex-grow:0;
}
```

Pour observer le résultat avec un direction en colonne avec `flex-direction:column`, pensez à ajouter une hauteur au conteneur :
```css
.conteneur{
display:flex;
flex-direction:column;
height:350px;
}
.element{
flex-grow:1;
}
.orange{
flex-grow:3;
}
.vert{
flex-grow:0;
}
```

### Taille initale avec flex-basis
Par défaut, la taille des éléments est établie en fonction du contenu. la propriété `flex-basis` permet de définir la taille initiale d'un élément avant que l'espace disponible soit redistribué entre les éléments.
Par exemple, nous pouvons indiquer comme largeur optimale 200px, et interdire le bloc orange de grandir en fixant `flex-grow` à 0 :
```css
.conteneur{
display:flex;
}
.element{
flex-grow:1;
}
.orange{
flex-grow:0;
/* Taille initiale de 200 */
flex-basis:200px;
}
```

En jouant sur la largeur de la fenêtre, vous constaterez que la zone orange peut rétrécir, mais ne dépasse pas les 200 pixels en largeur lorsque l'on élargi la fenêtre.
### Contraction avec `flex-shrink`
La propriétés `flex-shrink`permet quand à elle de configurer le rétrécissement des éléments (C'est la même mécanique de `flex-grow`, mais ).
```css
.conteneur{
display:flex;
}
.element{
flex-grow:1;
}
/* Orange ne peut pas rétécir ou s'agrandir.
Sa taille est de 200px */
.orange{
flex-shrink:0;
flex-grow:0;
flex-basis:200px;
}
```

### Forme compacte avec `flex`
TODO
## Alignement et positionnement des éléments
### Justification et alignement
#### `Alignement dans l'axe principal : justify-content`
La propriété `justify-content` permet de définir la façon ton les éléments vont s'aligner le long de l'axe principal (Axe horizontal).
Petit récap des valeurs possibles :

##### flex-start
Les éléments sont alignés au début de la *flexbox* ; à gauche ou en haut selon la valeur de `flex-direction`. C'est le réglage par défaut.
```css
.conteneur{
display:flex;
justify-content:flex-start;
}
```
##### flex-end
Les éléments sont alignés à la fin de la *flexbox* ; à droite ou en bas selon la valeur de `flex-direction`
```css
.conteneur{
display:flex;
justify-content:flex-end;
}
```
##### center
Les éléments sont alignés à la fin de la *flexbox* ; à droite ou en bas selon la valeur de `flex-direction`
Certaines balises ne délimitent aucune information, elles sont utilisées pour indiquer la présence d'un contenu spécifique (présence d'une image par exemple).
Plutôt que de les ouvrir et de le refermer, sans qu'elles ne délimitent aucun contenu ex :`<balise></balise>`, on utilise une syntaxe raccourci : `<balise />`
Nous venons de voir que les balises sont utilisées pour **délimiter du contenu**, dans les exemples précédents, le contenu été uniquement du contenu texte, mais généralement, le contenu est souvent un aggrégat de texte contenant lui-même des balises, pouvant à son tour contenir des balises. (à la manière de poupées russes). Ce formalisme est appelé **l'imbrication**.
```html
<body>
<h1>Bonjour monde !</h1>
<p>
Ceci est ma première page<br/>
elle contient du
<strong>HTML</strong> !
</p>
</body>
```
L'imbrication respecte la règle : **Première ouverte, dernière fermée**. Less balises qui *se croisent* ou qui ne sont pas refermée peuvent provoquer des erreurs d'interprétation.
## Arbre DOM
De part sa nature, l'imbrication peut être représenté sous la forme d'un arbre, on parle de l'arbre DOM (Document Object Model).

## Commentaires
Un code source HTML peut devenir rapidement dense et atteindre plusieurs centaines de ligne(on écrit beaucoup de code).
Les **commentaires** sont très utilisés pour permettre aux intégrateurs d'annoter le code source sans que ce commentaire apparaisse dans le rendu final.
Un commentaire débute par la séquence `<!--` et se termine avec `-->`
La création de contenu pour le web est l'aggrégat d'un **ensemble de technologies** que l'usage profane regroupe généralement sous le terme **technologies HTML/Web**.
## HTML
Le HTML est une technologie utilisée pour :
- Créer des documents web (pages HTML)
- Structurer les interfaces web (Webapp)
Le HTML est un langage :
- Description de contenu par **balise**
- Conçu pour être facile à utiliser/partager
-**Sémantique** (Il sert à structurer une informations - pas à la mise en forme)
<divclass="info">
HTML n'est généralement pas considéré comme un **langage de programmation**. Il est en effet purement descriptif et ne propose aucun mécanisme logique.
</div>
## Petite histoire
### 1990
**Tim Berners** pose les bases du web :
- Premier navigateur,
- le protocole HTTP (pour l'accès aux document HTML),
- et le langage HTML
Le terme de **World Wide Web** est déjà consacré.

### 1993
Le **Web** s'étend à la communauté scientifique et se popularise grâce à **NCSA Mosaic**, un navigateur capable d'afficher... des images.
**Netscape navigator** popularise le web hors des universités en permettant de réaliser les premiers sites *visuels*.
- Fondation du **W3C** (World Wide Web Consortium)
- Apparition d'**Internet Explorer**
- 1995/96 : Spécification de HTML 2.0 est publiée.
Cette période voit également s'affronter les éditeurs de navigateur Netscape et Explorer dans ce qu'on appelle **Le guerre des navigateurs**. Ces derniers n'hesitant pas à prendre de grandes liberté quand au rendu et aux fonctionnalités HTML/CSS
**HTML 3.2** Syntètise les améliorations apportées par netscape et Internet explorer, en vu de normaliser les usages des 2 navigateurs.
**HTML 4** sort dans la foulée. Arrivée en force des **style CSS** et des scripts (Javascript). Le W3C arrive à imposer ce standard
La production de contenu Web se professionnalise

### 2000/2008 : Web 2.0
Le **XHTML** s'impose dans l'usage professionnel, il est la version **strict** de HTML 4. Il scèle une bonne fois pour toute la sacro-sainte séparation du contenu (XHTML) et de la forme (CSS).
La production de site web se professionnalise, les métiers d'**intégrateur web** / **Webdesigner** sont reconnus comme des disciplines hautement technique et plus seulement comme des activités complémentaires à des domaines plus générale (Designers / Informaticiens).
### Maintenant
**XHTML 2**, une nouvelle norme développée depuis plusieurs années a été définitivement abandonné ; rejetée par la communauté avant même d'être publié.
Le **HTML5** et le **CSS3**, encore en brouillon, sont déjà largement adoptés par les principaux navigateurs (Firefox, Chrome, Edge). Imposant définitivement l'aire du **Web Sémantique**.