Métro full CSS chapitre 1 : The grid
Posté dans Développement le
  1. Analyse
  2. Les bases
  3. Les sections
  4. Les éléments
  5. Bonus

Bonjour aujourd’hui je vous propose une petite expérience. Nous allons réaliser un design inspiré du style Metro (de windows 8), pour la présentation des éléments certains me diront il suffit de prendre Masonry et le tour est joué, ils s’aligneront correctement sans s’embêter. Oui c’est vrai j’aurais pu le faire, mais c’est bien mal me connaitre et pour moi le JS est surtout fait pour les animations (bien qu’avec le CSS3 je me demande) et les interactions du coup je préfère chercher un peu et reproduire cette présentation uniquement en CSS comme cela aucun script à exécuter pour la mise en forme et le visiteur n’est pas obligé d’avoir JS activer pour visiter le site (bien que maintenant c’est pratiquement obligé de l’avoir mais bon c’est le principe), nous verrons aussi à la fin comment adapter la présentation au mobile.

Dans le souci d’utiliser les dernières technologies, le CSS3 et HTML5 seront utilisés pour cette expérience.
Nous utiliseront donc les nouvelles balises (Section, Article) ce qui peut poser des soucis de compatibilité avec certain navigateur, mais nous verrons comment les régler par la suite.

Aller c’est partit !

1) Analyser :

vignette

Sur cette capture d’écran on peut observer que les éléments sont présentés en section qui me font un peu pensé à des tableaux de deux colonnes et trois lignes et certains éléments peuvent faire deux colonnes de large.
Pour reproduire cette présentation la première solution pourrait être d’utiliser un tableau html, mais bon d’un ce n’est pas vraiment fait pour cela et de deux ça serait un peu bloquant pour rendre le design responsive par la suite, car le tableau garderait sa forme. J’ai donc préféré la solution d’utiliser des blocs et les positionner avec le CSS.

2) Les bases :

Nous allons commencer par poser les base de la structure html (je vous épargne le head)

<div id="container">
	<section>
		<article></article>
		<article></article>
		<article></article>
		<article></article>
	</section>
	<section>
		<article></article>
		<article></article>
		<article></article>
		<article></article>
	</section>
	<section>
		<article></article>
		<article></article>
		<article></article>
		<article></article>
	</section>
	<section>
		<article></article>
		<article></article>
		<article></article>
		<article></article>
	</section>
</div>
#container {
        width: 92%;
	margin-left: 4%;
	margin-right: 4%;
	background: #F3F3F3;
}

section {

}

article {
    height: 100px;
    background: #FF7979;
}

Bon jusqu’ici rien de bien particulier et ça ne ressemble à rien pour l’instant, mais pour expliquer rapidement on utilise une div conteneur pour la grille (vous verrez l’utilité par la suite), Section lui représente comme sur l’image de l’analyse un tableau de deux colonnes et article représente quant à lui les éléments.

3) Les sections :

Comme vous avez pu le remarquer pour l’instant section ne sert à rien, mais nous allons voir ça de suite.
En regardant l’exemple on voit que seulement trois colonnes sont entièrement affichées à l’écran et on aperçoit une partie des autres, pour obtenir ces trois grille il nous faudra donc 1/3 de l’écran par section le design étant responsive on va utiliser les pourcentages. Il nous faudra donc « 100/3 = 33,33% » auxquels on enlève 2% pour les marges nous obtenons donc 31,33% ce qui nous donne.

section {
    margin-left: 1%;
    margin-right: 1%;
    width:31.333%;
}

Maintenant il ne manque plus qu’à  les aligné, vous vous dites certainement qu’un « float: left » pourrait suffire, malheureusement non, certes trois blocs sont aligné, mais le 4eme sera forcément à la ligne. Une solution serais d’agrandir la largeur du conteneur, mais les sections seraient déformées, la seconde solution est de la faire déborder en désactivant le retour à la ligne automatique en utilisant « white-space: nowrap » sur le conteneur, mais cette propriété s’applique seulement aux éléments « inline » on ajoutera donc « display: inline-block » sur section, car « inline » ne garderais pas la largeur. Nous obtenons donc ce CSS et le résultat actuel.

#container {
    width: 92%;
    margin-left: 4%;
    margin-right: 4%;
    background: #F3F3F3;
    white-space: nowrap;
}

section {
    display: inline-block;
    margin-left: 1%;
    margin-right: 1%;
    width:31.333%;
}

article {
    height: 100px;
    background: #FF7979;
}

alignement-des-colonnes-metro

4) Les éléments :

Maintenant que les sections sont en place on va pouvoir s’occuper des éléments qui sont actuellement de couleur rouge et qu’on ne peut dissocier dans les sections.
Pour entrer dans le vif du sujet la problématique est la mêmes que pour les sections, il faut réussir à faire rentrer 2 éléments sur une même ligne avec 1% de marge de chaque coter. Ici le calcul est plus facile a faire de tête 100/2 = 50% auxquels on enlève 2% on obtient 48%. Contrairement aux sections ici on peut utiliser un « float: left » et on ajoutera 10px de marge vers le bas pour espacer les lignes de la grille. Ce qui nous donne ?

#container {
    width: 92%;
    margin-left: 4%;
    margin-right: 4%;
    background: #F3F3F3;
    white-space: nowrap;
}

section {
    display: inline-block;
    margin-left: 1%;
    margin-right: 1%;
    width:31.333%;
}

article {
    height: 100px;
    float: left;
    margin-left: 1%;
    margin-right: 1%;
    margin-bottom: 10px;
    width: 48%;
    background: #FF7979;
}

grille-metro

Il ne manque plus qu’un petit détail, le fait qu’un élément peut faire la largeur de deux colonnes. pour cela rien de plus simple il suffit de créer une class que je nommerais col2 qui devrait ressembler à ceci.

article.col2 {
    width: 98%;
}

bug-alignement

Si l’appliquer au premier élément vous risquez d’obtenir ce « bug » pour lequel je dois avouer que j’ai du mal à l’expliquer, mais pour faire simple la première section est plus grande et les suivante qui sont plus petites se colle en bas la solution la plus simple est d’ajouter un « vertical-align: top »  sur section et tout reviens dans l’ordre, personnellement je préfère une autre solution qui consiste à mettre un « position: absolute » sur le conteneur et définir (top, bottom, left …) ce qui demande un petit changement du conteneur et ensuite il suffit de définir un « height: 100% » sur section, ce qui aura pour effet de forcer les sections à avoir la même taille et au passage on pourra aussi y ajouter un « overflow: hidden » pour éviter que des éléments déborde.

#container {
    position: absolute;
    top: 20px;
    bottom: 20px;
    left: 4%;
    right: 4%;
    background: #F3F3F3;
    white-space: nowrap;
}

section {
    display: inline-block;
    margin-left: 1%;
    margin-right: 1%;
    width:31.333%;
    height: 100%;
    overflow: hidden
}

5) Bonus :

Bloc de 2 lignes :

article.row2 {
    height: 210px;
}

/*Permet de corriger l'alignement des bloc*/
article.align {
    margin-top: -110px;
}

Avoir un bloc de deux lignes est très simple comme pour un bloc de deux colonnes il suffit de multiplier sa taille par deux en ajoutant la marge (10px ici) ce qui nous donne (2 x 100)+10=210px
Malheureusement il se peut qu’il y aie des erreurs d’alignement surtout avec les éléments impair c’est pour ça que j’ai ajouté la class align

Propriété column CSS3 :

Le CSS3 apporte une propriété nommée column malheureusement elle n’est pas encore totalement supporté et des tests que j’ai réalisés on obtient un « bug » (qui n’en est pas vraiment un) enfaîte les div se retrouve couper, mais c’est le comportement normal de la fonction. Il y aura plus tard les propriété ‘break-before’, ‘break-after’, ‘break-inside’ mais ces dernières ne sont pas encore très bien supporté, j’essayerais de faire une mise à jour du tuto quand ces fonctions seront un peu mieux supporté.

End !

Voilà  c’est terminé pour le premier chapitre de cette expérience j’espère que ça vous a plu et qu’il vous sera utile, si vous le souhaitez vous pouvez partager cet article pour m’encourager à continuer

Tags