Pseudo-classes

The CSS Podcast – 015 : Pseudo-classes

Imaginons que vous ayez un formulaire d'inscription par e-mail et que vous souhaitiez que le champ d'adresse e-mail soit entouré d'une bordure rouge s'il contient une adresse e-mail non valide. Comment procéder ? Vous pouvez utiliser une pseudo-classe CSS :invalid, qui fait partie des nombreuses pseudo-classes fournies par le navigateur.

Une pseudo-classe vous permet d'appliquer des styles en fonction des changements d'état et des facteurs externes. Cela signifie que votre conception peut réagir aux saisies de l'utilisateur, comme une adresse e-mail non valide. Ces sélecteurs sont abordés dans le module Sélecteurs. Ce module vous les présentera plus en détail.

Contrairement aux pseudo-éléments, dont vous pouvez en savoir plus dans le module précédent, les pseudo-classes s'accrochent à des états spécifiques dans lesquels un élément peut se trouver, plutôt que de styliser généralement des parties de cet élément.

États interactifs

Les pseudo-classes suivantes s'appliquent en raison d'une interaction d'un utilisateur avec votre page.

:hover

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 2.

Source

Si un utilisateur dispose d'un dispositif de pointage tel qu'une souris ou un pavé tactile et qu'il le place sur un élément, vous pouvez vous accrocher à cet état avec :hover pour appliquer des styles. C'est un moyen utile de suggérer qu'un élément peut être utilisé.

:active

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

Cet état est déclenché lorsqu'un élément est en cours d'interaction (par exemple, un clic) avant que le clic ne soit relâché. Si un dispositif de pointage tel qu'une souris est utilisé, cet état correspond au moment où le clic commence et n'a pas encore été relâché.

:focus, :focus-within et :focus-visible

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

Si un élément peut être sélectionné (comme un <button>), vous pouvez réagir à cet état avec la pseudo-classe :focus.

Vous pouvez également réagir si un élément enfant de votre élément est sélectionné avec :focus-within.

Les éléments pouvant être sélectionnés, comme les boutons, affichent un anneau de sélection lorsqu'ils sont sélectionnés, même lorsqu'ils sont cliqués. Dans ce type de situation, un développeur appliquera le CSS suivant :

button:focus {
    outline: none;
}

Ce CSS supprime l'anneau de sélection par défaut du navigateur lorsqu'un élément est sélectionné, ce qui pose un problème d'accessibilité pour les utilisateurs qui naviguent sur une page Web à l'aide d'un clavier. S'il n'y a pas de style de sélection, ils ne pourront pas savoir où se trouve actuellement la sélection lorsqu'ils utilisent la touche Tabulation. Avec :focus-visible, vous pouvez présenter un style de sélection lorsqu'un élément est sélectionné au clavier, tout en utilisant la règle outline: none pour l'empêcher lorsqu'un dispositif de pointage interagit avec lui.

button:focus {
    outline: none;
}

button:focus-visible {
    outline: 1px solid black;
}

:target

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.3.

Source

La pseudo-classe :target sélectionne un élément dont l'attribut id correspond à un fragment d'URL. Supposons que vous disposiez du code HTML suivant :

<article id="content">
    <!-- ... -->
</article>

Vous pouvez associer des styles à cet élément lorsque l'URL contient #content.

#content:target {
    background: yellow;
}

Cela permet de mettre en évidence les zones qui ont pu être spécifiquement associées, comme le contenu principal d'un site Web, à l'aide d'un lien d'accès rapide.

États historiques

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 1.

Source

La pseudo-classe :link peut être appliquée à n'importe quel élément <a> dont la valeur href n'a pas encore été visitée.

:visited

Vous pouvez styliser un lien déjà visité par l'utilisateur à l'aide de la pseudo-classe :visited. Il s'agit de l'état opposé à :link, mais vous disposez de moins de propriétés CSS pour des raisons de sécurité. Vous ne pouvez appliquer un style qu'à color, background-color, border-color, outline-color et à la couleur des éléments SVG fill et stroke.

De l'importance de l'ordre des modificateurs

Si vous définissez un style :visited, il peut être remplacé par une pseudo-classe de lien ayant au moins la même spécificité. Pour cette raison, il est recommandé d'utiliser la règle LVHA pour styliser les liens avec des pseudo-classes dans un ordre particulier : :link, :visited, :hover, :active.

a:link {}
a:visited {}
a:hover {}
a:active {}

États du formulaire

Les pseudo-classes suivantes peuvent sélectionner des éléments de formulaire, dans les différents états dans lesquels ces éléments peuvent se trouver lors de l'interaction avec eux.

:disabled et :enabled

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Si un élément de formulaire, tel qu'un <button>, est désactivé par le navigateur, vous pouvez vous raccrocher à cet état avec la pseudo-classe :disabled. La pseudo-classe :enabled est disponible pour l'état opposé, bien que les éléments de formulaire soient également :enabled par défaut. Vous n'aurez donc peut-être pas besoin de cette pseudo-classe.

:checked et :indeterminate

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

La pseudo-classe :checked est disponible lorsqu'un élément de formulaire compatible, tel qu'une case à cocher ou une case d'option, est coché.

L'état :checked est un état binaire (vrai ou faux), mais les cases à cocher ont un état intermédiaire lorsqu'elles ne sont ni cochées ni décochées. C'est ce qu'on appelle l'état :indeterminate.

Par exemple, lorsque vous disposez d'un contrôle "Tout sélectionner" qui coche toutes les cases d'un groupe. Si l'utilisateur décoche l'une de ces cases, la case racine ne représente plus "toutes" les cases cochées et doit donc être placée dans un état indéterminé.

L'élément <progress> possède également un état indéterminé qui peut être stylisé. Un cas d'utilisation courant consiste à lui donner un aspect rayé pour indiquer que la quantité supplémentaire nécessaire est inconnue.

:placeholder-shown

Browser Support

  • Chrome: 47.
  • Edge: 79.
  • Firefox: 51.
  • Safari: 9.

Source

Si un champ de formulaire comporte un attribut placeholder et aucune valeur, la pseudo-classe :placeholder-shown peut être utilisée pour associer des styles à cet état. Dès qu'il y a du contenu dans le champ, qu'il soit placeholder ou non, cet état ne s'applique plus.

États de validation

Browser Support

  • Chrome: 10.
  • Edge: 12.
  • Firefox: 4.
  • Safari: 5.

Source

Vous pouvez répondre à la validation de formulaire HTML avec des pseudo-classes telles que :valid, :invalid et :in-range. Les pseudo-classes :valid et :invalid sont utiles dans des contextes tels qu'un champ d'adresse e-mail qui comporte un pattern devant être mis en correspondance pour que le champ soit valide. Cet état de valeur valide peut être affiché à l'utilisateur, ce qui l'aide à comprendre qu'il peut passer au champ suivant en toute sécurité.

La pseudo-classe :in-range est disponible si une entrée comporte min et max, comme une entrée numérique and, et si la valeur se trouve dans ces limites.

Avec les formulaires HTML, vous pouvez déterminer qu'un champ est obligatoire avec l'attribut required. La pseudo-classe :required sera disponible pour les champs obligatoires. Les champs non obligatoires peuvent être sélectionnés avec la pseudo-classe :optional.

Sélectionner des éléments par leur index, leur ordre et leur occurrence

Il existe un groupe de pseudo-classes qui sélectionnent des éléments en fonction de leur emplacement dans le document.

:first-child et :last-child

Browser Support

  • Chrome: 4.
  • Edge: 12.
  • Firefox: 3.
  • Safari: 3.1.

Source

Si vous souhaitez trouver le premier ou le dernier élément, vous pouvez utiliser :first-child et :last-child. Ces pseudo-classes renvoient le premier ou le dernier élément d'un groupe d'éléments frères.

:only-child

Browser Support

  • Chrome: 2.
  • Edge: 12.
  • Firefox: 1.5.
  • Safari: 3.1.

Source

Vous pouvez également sélectionner les éléments qui n'ont pas de frères et sœurs avec la pseudo-classe :only-child.

:first-of-type et :last-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Vous pouvez sélectionner :first-of-type et :last-of-type, qui semblent faire la même chose que :first-child et :last-child, mais considérez ce code HTML :

<div class="my-parent">
    <p>A paragraph</p>
    <div>A div</div>
    <div>Another div</div>
</div>

Et ce CSS :

.my-parent div:first-child {
    color: red;
}

Aucun élément ne serait coloré en rouge, car le premier enfant est un paragraphe et non une div. La pseudo-classe :first-of-type est utile dans ce contexte.

.my-parent div:first-of-type {
    color: red;
}

Même si le premier <div> est le deuxième enfant, il est toujours le premier du type à l'intérieur de l'élément .my-parent. Par conséquent, avec cette règle, il sera coloré en rouge.

:nth-child et :nth-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Vous n'êtes pas non plus limité aux premiers et derniers enfants, ni aux types. Les pseudo-classes :nth-child et :nth-of-type vous permettent de spécifier un élément qui se trouve à un certain index. L'indexation dans les sélecteurs CSS commence à 1.

Les pseudo-classes :nth-last-child() et :nth-last-of-type() comptent à partir de la fin, et non du début.

Vous pouvez également transmettre plus qu'un index à ces pseudo-classes. Si vous souhaitez sélectionner tous les éléments pairs, vous pouvez utiliser :nth-child(even).

Vous pouvez également créer des sélecteurs plus complexes qui trouvent des éléments à intervalles réguliers à l'aide de la microsyntaxe An+B.

li:nth-child(3n+3) {
    background: yellow;
}

Ce sélecteur sélectionne un élément sur trois, en commençant par le troisième. Dans cette expression, n est l'index, qui commence à zéro, et 3 (3n) est le nombre par lequel vous multipliez cet index.

Imaginons que vous ayez sept éléments <li>. Le premier élément sélectionné est 3, car 3n+3 se traduit par (3 * 0) + 3. L'itération suivante sélectionnera l'élément 6, car n est maintenant incrémenté à 1, donc (3 * 1) + 3). Cette expression fonctionne à la fois pour :nth-child et :nth-of-type.

:nth-child() et :nth-last-child() acceptent également une syntaxe "of S" qui vous permet de filtrer les correspondances avec un sélecteur, comme :nth-of-type(). li:nth-of-type(even) équivaut à :nth-child(even of li). Alors que :nth-of-type ne vous permet de filtrer que par type d'élément (comme li ou p), la syntaxe "of S" vous permet de filtrer sur n'importe quel sélecteur.

Si vous avez un tableau, vous pouvez ajouter des bandes à une ligne sur deux. Bien que vous puissiez cibler une ligne sur deux avectr:nth-child(even), cela ne fonctionne pas si vous filtrez certaines lignes. Si vous implémentez le filtrage en appliquant l'attribut hidden, vous pouvez ajouter of :not([hidden]) au sélecteur pour préfiltrer les éléments masqués avant de sélectionner les lignes paires.

tr:nth-child(even of :not([hidden])){
  background: lightgrey;
}

Vous pouvez tester ce type de sélecteur sur cet outil de test nth-child ou cet outil de sélection de quantité.

:only-of-type

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 3.5.
  • Safari: 3.1.

Source

Enfin, vous pouvez trouver le seul élément d'un certain type dans un groupe de frères et sœurs avec :only-of-type. Cette option est utile si vous souhaitez sélectionner des listes ne comportant qu'un seul élément ou si vous souhaitez trouver le seul élément en gras d'un paragraphe.

Rechercher des éléments vides

Il peut parfois être utile d'identifier les éléments complètement vides. Il existe également une pseudo-classe pour cela.

:empty

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Si un élément n'a pas d'enfants, la pseudo-classe :empty s'applique à lui. Toutefois, les enfants ne sont pas uniquement des éléments HTML ou des nœuds de texte. Ils peuvent également être des espaces blancs, ce qui peut être déroutant lorsque vous déboguez le code HTML suivant et que vous vous demandez pourquoi il ne fonctionne pas avec :empty :

<div>
</div>

En effet, il y a des espaces entre les balises d'ouverture et de fermeture de <div>, ce qui empêche :empty de fonctionner.

La pseudo-classe :empty peut être utile si vous avez peu de contrôle sur le code HTML et que vous souhaitez masquer les éléments vides, comme un éditeur de contenu WYSIWYG. Ici, un éditeur a ajouté un paragraphe vide et isolé.

<article class="post">
 <p>Donec ullamcorper nulla non metus auctor fringilla.</p>
 <p></p>
 <p>Curabitur blandit tempus porttitor.</p>
</article>

Avec :empty, vous pouvez trouver et masquer ces informations.

.post :empty {
    display: none;
}

Rechercher et exclure plusieurs éléments

Certaines pseudo-classes vous aident à écrire un code CSS plus compact.

:is()

Browser Support

  • Chrome: 88.
  • Edge: 88.
  • Firefox: 78.
  • Safari: 14.

Source

Si vous souhaitez trouver tous les éléments enfants h2, li et img dans un élément .post, vous pouvez écrire une liste de sélecteurs comme celle-ci :

.post h2,
.post li,
.post img {
    
}

Avec la pseudo-classe :is(), vous pouvez écrire une version plus compacte :

.post :is(h2, li, img) {
    /* ... */
}

La pseudo-classe :is est non seulement plus compacte qu'une liste de sélecteurs, mais elle est également plus tolérante. Dans la plupart des cas, si une liste de sélecteurs contient une erreur ou un sélecteur non compatible, elle ne fonctionnera plus. Si une erreur se produit dans les sélecteurs transmis dans une pseudo-classe :is, le sélecteur non valide est ignoré, mais ceux qui sont valides sont utilisés.

:not()

Browser Support

  • Chrome: 1.
  • Edge: 12.
  • Firefox: 1.
  • Safari: 3.1.

Source

Vous pouvez également exclure des éléments avec la pseudo-classe :not(). Par exemple, vous pouvez l'utiliser pour styliser tous les liens qui n'ont pas d'attribut class.

a:not([class]) {
    color: blue;
}

Une pseudo-classe :not peut également vous aider à améliorer l'accessibilité. Par exemple, un <img> doit avoir un alt, même s'il s'agit d'une valeur vide. Vous pouvez donc écrire une règle CSS qui ajoute un contour rouge épais aux images non valides :

img:not([alt]) {
    outline: 10px red;
}

:has()

Que faire si vous souhaitez styliser des éléments en fonction de leur contenu ? Pour ce faire, vous pouvez utiliser la pseudo-classe :has(). Par exemple, vous pouvez appliquer des styles aux boutons qui incluent des icônes.

 button:has(svg) {
  /* ... */
}

Dans sa configuration la plus élémentaire, comme dans l'exemple précédent, vous pouvez considérer :has() comme un sélecteur parent. Vous pouvez également utiliser le sélecteur de parent correspondant avec d'autres sélecteurs pour cibler d'autres éléments.

form:has(input:valid) label {
  font-weight: bold;
}

form:has(input:valid) label::after {
  content: "✅";
}

Dans cet exemple, nous appliquons des styles à l'élément de libellé et au pseudo-élément label::after lorsque l'entrée de formulaire possède une pseudo-classe valid.

La pseudo-classe :has() ne peut pas être imbriquée dans une autre :has(), mais elle peut être combinée avec d'autres pseudo-classes.

:is(h1, h2, h3):has(a) {
   /* ... */
}

La liste des sélecteurs est impitoyable. Si l'un d'eux n'est pas valide, toutes les règles de style seront ignorées.

.my-element:has(img, ::before) {
  /* any styles here will be discarded since pseudo elements can't be included in the :has() selector list */
}

Vérifier que vous avez bien compris

Tester vos connaissances sur les pseudo-classes

Les pseudo-classes agissent comme si une classe avait été appliquée dynamiquement à un élément, tandis que les pseudo-éléments agissent sur un élément lui-même.

Vrai
Faites attention à l'utilisation d'un ou deux : comme caractère clé distinctif dans le sélecteur.
Faux
Les pseudo-éléments concernent les parties, tandis que les pseudo-classes concernent l'état.

Parmi les propositions suivantes, laquelle est une pseudo-classe fonctionnelle ?

:is()
🎉
:target
Les pseudo-classes fonctionnelles sont suivies de () pour indiquer qu'elles acceptent des paramètres.
:empty
Les pseudo-classes fonctionnelles sont suivies de () pour indiquer qu'elles acceptent des paramètres.
:not()
🎉

Parmi les pseudo-classes suivantes, lesquelles sont dues à une interaction de l'utilisateur ?

:hover
🎉
:press
Essayez encore.
:squeeze
Essayez encore.
:target
🎉
:focus-within
🎉

Parmi les propositions suivantes, lesquelles sont des pseudo-classes d'état <form> ?

:enabled
🎉
:fresh
Essayez encore.
:indeterminate
🎉
:checked
🎉
:in-range
🎉
:loading
Essayez encore.
:valid
🎉