Parfois, la première partie du HTML que nous écrivons dans un nouveau document est un élément qui enveloppe tout le reste de la page. Le terme wrapper est courant pour cela. Nous lui donnons une classe, et cette classe est responsable de l’encapsulation de tous les éléments visuels sur la page.
J’ai toujours lutté pour avec la meilleure façon de l’implémenter. J’ai trouvé un fil de discussion connexe sur StackOverflow qui a plus de 250 000 vues, donc évidemment je ne suis pas le seul à me poser la question ! Je vais résumer mes dernières réflexions dans cet article.
Avant de nous y plonger, examinons d’abord la différence entre le « wrapper » et le « container ».
« Wrapper » vs « Container »
Je crois qu’il y a une différence entre les éléments wrapper et container.
Dans les langages de programmation, le mot container est généralement utilisé pour les structures qui peuvent contenir plus d’un élément. Un wrapper, d’autre part, est quelque chose qui enveloppe un objet unique pour lui fournir plus de fonctionnalités et d’interface.
Donc, à mon avis, il est logique d’avoir deux noms différents parce qu’ils entendent des fonctions différentes.
En parlant du wrapper, il est courant de penser à un <div>
qui contient tout le reste du HTML du document. Je suis sûr que beaucoup d’entre nous ont vécu à une époque où nous avons réglé cela à 960px de largeur et aligné au centre tout notre contenu principal. Les wrappers sont également utilisés pour des choses comme l’application d’un pied de page collant.
Le conteneur, quant à lui, entend généralement un autre type de confinement. Celui qui est parfois nécessaire pour mettre en œuvre un comportement ou un style de plusieurs composants. Il sert à regrouper les éléments à la fois sémantiquement et visuellement. À titre d’exemple, Bootstrap dispose de « classes conteneurs » qui abritent leur système de grille ou contiennent divers autres composants.
Les termes wrapper et conteneur peuvent également signifier la même chose selon le développeur et son intention. Il pourrait y avoir d’autres conventions aussi, donc le meilleur conseil est généralement de mettre en œuvre ce qui a le plus de sens pour vous. Mais n’oubliez pas que le nommage est l’une des parties les plus fondamentales et les plus importantes des activités du développeur. Les conventions de nommage rendent notre code plus lisible et prévisible. Choisissez-les avec soin !
Voici un exemple de wrapper de page général :
/** * 1. Centers the content. Yes, it's a bit opinionated. * 2. See the "width vs max-width" section * 3. See the "Additional Padding" section */.wrapper { margin-right: auto; /* 1 */ margin-left: auto; /* 1 */ max-width: 960px; /* 2 */ padding-right: 10px; /* 3 */ padding-left: 10px; /* 3 */}
largeur vs largeur maximale
Définir la width
d’un élément de niveau bloc l’empêchera de s’étirer jusqu’aux bords de son conteneur (ce qui est bon pour des choses comme des longueurs de ligne lisibles). Par conséquent, l’élément d’habillage occupera la largeur spécifiée. Le problème se pose lorsque la fenêtre du navigateur est plus étroite que la largeur spécifique de l’élément enveloppant. Cela déclenchera une barre de défilement horizontale, ce qui est presque toujours indésirable.
L’utilisation de max-width
à la place, dans cette situation, est meilleure pour les fenêtres de navigateur plus étroites. C’est important lorsqu’il s’agit de rendre un site utilisable sur de petits appareils. Voici un bon exemple illustrant le problème.
Voir le Pen CSS-Tricks : La meilleure façon de mettre en œuvre un wrapper CSS par Kaloyan Kosev (@superKalo) sur CodePen.
En termes de réactivité, max-width
est le meilleur choix !
Rembourrage supplémentaire
J’ai vu beaucoup de développeurs oublier un cas limite particulier. Disons que nous avons un wrapper avec max-width
défini à 980px. Le cas limite apparaît lorsque la largeur d’écran de l’appareil de l’utilisateur est exactement de 980px. Le contenu va alors coller exactement aux bords de l’écran sans laisser de marge de manœuvre.
Nous voulons généralement un peu de rembourrage sur les bords. C’est pourquoi si je dois mettre en œuvre un wrapper avec une largeur totale de 980px, je le ferais comme suit :
.wrapper { max-width: 960px; /* 20px smaller, to fit the paddings on the sides */ padding-right: 10px; padding-left: 10px; /* ... */}
C’est pourquoi ajouter padding-left
et padding-right
à votre wrapper pourrait être une bonne idée, surtout sur mobile.
Ou, envisagez d’utiliser le box-sizing pour que le padding ne modifie pas du tout la largeur globale.
Quel élément HTML choisir
Un wrapper n’a aucune signification sémantique. Il contient simplement tous les éléments visuels et le contenu de la page. Il s’agit simplement d’un conteneur générique. En termes de sémantique, <div>
est le meilleur choix. Le <div>
n’a pas non plus de signification sémantique et c’est juste un conteneur générique.
On pourrait se demander si peut-être un élément <section>
ne pourrait pas répondre à cet objectif. Cependant, voici ce que dit la spécification du W3C:
L’élément
<section>
n’est pas un élément conteneur générique. Lorsqu’un élément n’est nécessaire qu’à des fins de style ou comme commodité pour les scripts, les auteurs sont encouragés à utiliser l’élément div à la place. Une règle générale veut que l’élément section ne soit approprié que si le contenu de l’élément doit être listé explicitement dans le plan du document.
L’élément <section>
porte sa propre sémantique. Il représente un regroupement thématique de contenu. Le thème de chaque section doit être identifié, généralement en incluant un titre (élément h1-h6) comme enfant de l’élément section.
Des exemples de sections seraient les chapitres, les différentes pages à onglets d’une boîte de dialogue à onglets ou les sections numérotées d’une thèse. La page d’accueil d’un site Web pourrait être divisée en sections pour une introduction, des articles d’actualité et des informations de contact.
Cela peut ne pas sembler très évident à première vue, mais oui ! La bonne vieille <div>
convient mieux à un wrapper!
Utiliser la balise <body> vs. Utilisation d’un <div>
Il convient de mentionner qu’il y aura des cas où l’on pourra utiliser l’élément <body>
comme enveloppe. L’implémentation suivante fonctionnera parfaitement bien :
body { margin-right: auto; margin-left: auto; max-width: 960px; padding-right: 10px; padding-left: 10px;}
Et il en résultera un élément de moins dans votre balisage, car vous pourrez abandonner cet élément wrapper inutile <div>
de cette façon.
Cependant, je ne le recommanderais pas, en raison de la flexibilité et de la résilience aux changements. Imaginez si, à un stade ultérieur du projet, l’un de ces scénarios se produit :
- Vous devez imposer un pied de page pour qu’il « colle » à la fin du document (bas du viewport lorsque le document est court). Même si vous pouvez utiliser la façon la plus moderne de le faire – avec flexbox, vous avez besoin d’un wrapper supplémentaire
<div>
. - Vous devez définir le
background-color
de toute la page. Normalement, quel que soit le fond que vous définissez sur la<body>
, il se comportera comme s’il était défini sur l’élément<html>
s’il n’avait pas déjà un fond. C’est juste un truc bizarre en CSS. Mais si votre élément<html>
a déjà un arrière-plan, et que vous définissez le corps sur quelque chose d’autre, et que le corps a une sorte de contrainte d’espacement, les arrière-plans seront bizarres. C’est une chose délicate.
Je conclurais que c’est toujours la meilleure pratique d’avoir un <div>
supplémentaire pour mettre en œuvre un wrapper CSS. De cette façon, si les exigences de la spécification changent plus tard, vous n’avez pas à ajouter le wrapper plus tard et à gérer le déplacement des styles. Après tout, nous ne parlons que d’un seul élément DOM supplémentaire.