Bref, voici comment écrire du CSS maintenable et évolutif. Comment nommer ses class CSS.

Loin de moi l’idée d’imposer ma vision à tout le monde, néanmoins, je vais te dire comment écrire, selon moi, du CSS maintenable et évolutif.

On pourrait commencer par se poser la question “pourquoi ?”.
Avant de t’exciter et de te dire des phrases du genre :

- Mais il veut quoi lui ? 
- Pourquoi y aurait-il des règles pour écrire du CSS ? 
- Je peux nommer mes class CSS comme bon me semble, YOLO

Calme-toi jeune intégrateur, développeur front-end ou développeur back-end qui voit le CSS comme du coloriage et non un vrai langage. Car si, le CSS, c’est un vrai langage (pas de programmation certes, mais de code).

Plus on écrit du code, plus il sera difficile de le maintenir et le faire évoluer si on n’applique pas des règles ou un cadre. Le CSS ne déroge pas à la règle.

Le plus gros problème du CSS, c’est le nommage et les conflits de sélecteurs.

Au début, on se dit qu’on va donner des noms sémantiques :
“navigation”, “contact”, “gallery”…
Puis arrive ce moment où tu dois donner une classe juste pour dire qu’un bouton est rouge, et là, c’est le drame, tu nommes ta class CSS “red”.

Quel est le problème ? À force de nommer des class CSS aussi courtes et sans aucun sens, quand notre code va grossir, on risque de nommer quelque chose du même nom ailleurs sans faire exprès. L’autre souci qui se pose, c’est que le jour où notre bouton devient bleu bah… Il faut changer cette class partout !

Comment faire ? Quelles sont les solutions ?

Atomic CSS vs Component CSS

/!\ Tout d’abord, l’Atomic CSS n’a rien à avoir avec l’Atomic Design, ce sont deux choses très différentes (clique sur les liens pour en savoir plus).

L’Atomic CSS et le Component CSS sont deux façons de faire du CSS avec une logique et une approche très différente. Elles ont toutes les deux de bons et de mauvais côtés car elles ne règlent pas le même souci.

L’Atomic CSS : C’est le principe de faire des class CSS qui n’appliquent qu’un seul style et qui fait du CSS au plus petit niveau, le niveau atomique.

Libs : Acss.io | Tachyon | Basscss

Le Component CSS : C’est le principe qui consiste à créer des composants en CSS et éventuellement des class CSS utilitaires.

Libs : Bootstrap | Foundation | Bulma | Semantic UI

Chacun d’entre eux a des implémentations diverses. Toujours flou par vrai ? Une image vaut mieux que mille mots alors voici :

Exemple Atomic CSS

Component CSS

En Atomic CSS, on préfère mettre plusieurs class dans le HTML, plutôt que de grouper des propriétés dans un seul sélecteur. C’est aux antipodes de tout ce qu’on apprend à la base mais ça a des avantages :

  • Pas de conflits de class car chaque class CSS ne fait qu’une seule chose
  • Pas de class non utilisée en théorie, car on ne chargera que celles dont on a besoin, mais surtout, pas de duplication de propriétés CSS
  • Pas de prise de tête pour les noms car, Elles font quelque chose de tellement petit (atomique) que le nom = ce qu’elles font

En Component CSS, il y a plusieurs implémentations :
- BEM (Block Element Modifier, premier screen)
- SMACSS (Scalable and Modular Architecture CSS, deuxième screen)
- et plus encore…

BEM propose de définir un composant en 3 parties, un block, une class parent, des éléments, des class enfants, des modifiers, les variations de style faites aux éléments.

SMACSS propose de définir le css en fonction de ce que représente le HTML, des modules, layouts, états, bases et un thème.

Le Component CSS est plus complexe mais a des avantages aussi :

  • Les class CSS sont plus faciles à lire qu’en Atomic CSS car plus descriptives
  • Quand on a plusieurs éléments avec le même style, c’est plus facile de le changer partout car on n’a qu’une seule classe où faire des modifications
  • C’est plus facile de gérer les pseudo class et pseudo éléments
  • C’est plus simple pour le JavaScript d’altérer un élément en n’ajoutant qu’une ou deux class plutôt qu’une dizaine comme en Atomic

Je te laisse lire plus en détail BEM, OOCSS ou SMACCSS.

Donc on doit faire du Component CSS alors ?

On pourrait conclure par ce que je dis, que le Component CSS via BEM, OOCSS ou SMACCSS est la solution ultime, mais en fait : non.

Bien que ce soit plus cadré que l’Atomic CSS, l’Atomic CSS règle des soucis que le Component CSS ne règle pas aujourd’hui et vice-versa.

La solution c’est d’arriver à un mélange des deux.

Nous sommes arrivé à un point où on parle d’architecture côté CSS. Si tu veux que ton CSS puisse évoluer et ne plus te prendre la tête sur les noms de class, il faut valider, selon moi, les points suivants :

  • Découpe ta maquette en composants à la BEM, donc une class = un composant, chaque enfant a une class .parent_enfant
  • Un composant ne doit que se nommer avec un nom propre ou commun lié à sa fonction et pas à son apparence
  • Chaque composant ne gère que son intérieur, donc il ne gère pas ses margins ni son placement par rapport à son parent, ce sera son parent qui décidera de le placer où il veut
  • Il faut des class utilitaires et des class d’états / de variations
  • Une class utilitaire ou d’état ne doit que se nommer avec un verbe en préfixe comme : is- ou has- ou can- etc
  • Remplace les couleurs et positions par des synonymes, par exemple, 
    au lieu de block-left met block-start, car ce qui est à gauche est le début de la lecture (en général), au lieu de is-red met is-danger car ce qui est rouge est une action dangereuse (en général) et ainsi de suite
  • Utilise les cumules de class pour les variations : .composant.is-etat
  • Utilise les id que pour les JavaScript et pas dans le CSS
  • Laisse le body ou le html gérer les styles génériques (font, chartes…)
  • N’hésite à créer de très petits composants quand ta charte graphique l’impose. Un composant bouton, un titre, un input… Ce n’est pas grave de créer un composant qui n’a pas d’enfant quand ça fait sens.

Cela parait énorme à retenir ? Mmmh pas tant que ça, essayons pour voir.

Un cas pratique pour illustrer

Voici une maquette d’un board Trello simple

On peut découper cette maquette en 4 composants : board, lists, list et card.

Les composants peuvent exister seul dans n’importe quel autre contexte. 
C’est pour cela qu’on considère que chaque carte est un composant car une carte peut être utilisée hors d’une liste.

Voici le code CSS et HTML

Comme on peut le voir, le composant lists a un composant list enfant, mais il lui ajoute ses marges et sa taille via une sous class. Le composant list n’a pas à gérer ses marges ou sa taille tout seul car, il ne sait pas dans quel contexte on peut l’utiliser (fullscreen, dans un container, en responsive…).

Prenons un autre exemple de composants beaucoup plus petits qui serait 
réutilisable souvent, un UI-kit / une charte graphique.

Ces principes fonctionnent pour moi dans la plupart des scénarios que j’ai, néanmoins, il y a toujours des cas extrêmes où tu iras à l’encontre d’une règle, et ce n’est pas grave tant que cela reste un cas extrême.

J’aurais pu appeler is-cancel “is-grey”, mais que se passe-t-il le jour où je veux changer de couleur ? Dans mon site, je sais que mes boutons gris ne servent qu’à annuler des actions, donc, is-cancel est plus clair car il n’est pas lié au style mais lié au comportement des boutons gris de mon site.

Le design doit aussi avoir une logique pour faciliter le nommage.

En espérant que cela t’aide à mieux construire ton CSS et nommer tes class.

XOXO. Gossip CSS.

PS : Je t’encourage fortement à utiliser un préprocesseur comme SASS pour t’aider à encore mieux appliquer ces règles et partager du CSS entre composants.

PS 2 : Je te conseil (si tu ne supportes pas IE 10 et inférieur) d’utiliser Bulma CSS, qui est le framework CSS qui se rapproche le plus de ce j’explique ici.

PS 3 : Un site qui m’a bien inspiré et conforté dans mes choix aussi après que j’ai trouvé mon style d’architecture CSS https://maintainablecss.com