Les sélecteurs CSS, partie 2 : on mélange tout

24 03 2010

Nous avons précédemment vus les sélecteurs CSS de base  (partie 1), ceci nous a permis de (re)découvrir des moyens efficaces d’identifier les éléments dans une page. On va à présent aborder le regroupement, les sélecteurs combinés et d’attribut. Prêt? C’est parti!

Le regroupement

Il vous est surement déjà arrivez de devoir répéter plusieurs fois les mêmes propriétés CSS pour des éléments différents, ce qui est très fastidieux, heureusement pour nous le regroupement est là. Ce dernier consiste à enchainer les sélecteurs en les séparant pas des virgules, les propriétés correspondantes s’appliqueront alors à tous ces sélecteurs.

<html>
  <head>
    <style>
      p, div{font-family:verdana;}
      p {color:#F00;}
      div{color:#00F;}
    </style>
  </head>
  <body>
    <p>élément P</p>
    <div>élément DIV</div>
  </body>
</html>

Comme vous pouvez le constater ici les éléments « P » et « DIV » ont la même police d’écriture mais on chacun une couleur différente. On peut donc définir des propriétés communes à de multiples sélecteurs en une fois, ce qui n’empêche pas pour autant de définir des propriétés spécifiques à un sélecteur.

Les combinateurs

On va aborder ici une notion intéressante qui permet d’appliquer des propriétés CSS à un même type d’élément sans lui indiquer de classe ou d’identifiant en utilisant l’arborescence des éléments de la page.

Sélecteur descendant

Pour changer je vous mets directement l’exemple et j’expliques après :

<html>
  <head>
    <style>
      p ul{list-style-type:circle;}
      div ul{list-style-type:square;}
    </style>
  </head>
  <body>
    <p>
      <ul>
        <li>puce1</li>
        <li>puce2</li>
        <li>puce3</li>
      </ul>
    </p>
    <div>
      <ul>
        <li>puce1</li>
        <li>puce2</li>
        <li>puce3</li>
      </ul>
    </div>
  </body>
</html>

On a ici deux listes à puce la première dans un élément « P », la seconde dans un élément « DIV », on n’a indiqué nulle part de classe ou d’identifiant et pourtant elles apparaissent différemment, pourquoi ?

Regardons la définition des styles, on a « p ul » avec des puces rondes et « div ul » avec des puces carrées, en fait on dit que les éléments « UL », auront des puces rondes quand ils sont inclus dans un élément « P » et qu’ils auront des puces carrées dans dans un « DIV ».

Sélecteur d’enfant

Celui-ci ressemble énormément au précédent, à un détail près, le sélecteur descendant doit être l’enfant, c’est-à-dire qu’il ne doit pas y avoir d’élément entre le sélecteur parent et l’enfant.

<html>
  <head>
    <style>
      p > strong{color:red;}
    </style>
  </head>
  <body>
    <p>
      <strong>l'enfant</strong>
      <div><strong>petit enfant</strong></div>
    </p>
  </body>
</html>

Seul l’enfant est en rouge, le petit enfant n’a aucun style d’appliqué.

Sélecteur adjacent

Il est construit en plaçant deux sélecteurs autour d’un « + », comme ceci « E1 + E2 », cela peut se traduire par tout élément E2 suivant un élément E1.

<html>
  <head>
    <style>
      p + p{color:red;}
    </style>
  </head>
  <body>
    <div>
      <p>E1</p>
      <p>E2</p>
    </div>
  </body>
</html>

Il va de soi que les deux éléments doivent avoir le même
parent.

(Petit) ajout pour le regroupement

Avec ce que vous venez d’apprendre sur les combinateurs vous seriez tentez de faire des regroupements « complexes », comme ceci :

<html>
  <head>
    <style>
      #bloc1 p, li{list-style-type:none;}
    </style>
  </head>
  <body>
    <ul id="liste1">
      <li>puce1</li>
      <li>puce2</li>
      <li>puce3</li>
    </ul>
    <div id="bloc1">
      <p>paragraphe</p>
      <ul>
        <li>puce1</li>
        <li>puce2</li>
        <li>puce3</li>
      </ul>
    </div>
  </body>
</html>

On définit nos style de sorte que la liste (« UL »)dans l’élément « DIV » n’est pas de puce, mais quand on regarde le résultat il n’y a de puce nulle part ! Que s’est il passé ? On a regroupé un sélecteur descendant « #bloc1 p » avec un sélecteur simple « li », il n’a pas été indiqué que ce dernier devait être un descendant de « #bloc1 », voici une autre notation possible pour ce que l’on a fait :

#bloc1 p {list-style-type:none;}
li {list-style-type:none;}

La bonne méthode était donc :

#bloc1 p, #bloc1 li {list-style-type:none;}

Les sélecteurs d’attributs

Ils permettent de sélectionner un élément en fonction de ces attributs. Un peu de syntaxe pour commencer :

  • E[att] : tout élément ayant l’attribut « att »
  • E[att=val] : tout élément ayant l’attribut « att » égale à « val »
  • E[att~=val] : tout élément dont l’attribut « att » contient une liste de valeur séparé par des espaces et dont une de celles-ci est égale à « val »
  • E[att|=val] : tout élément dont l’attribut « att » contient une liste de valeur séparé par des tirets et débutant par « val ».

Exemple :

<html>
  <head>
    <style>
      p[title] {color:red;}
      p[title=autre] {font-family:arial;}
      p[title~=titre2] {font-weight:bold;}
      p[lang|=fr] {color:#00f;}
    </style>
  </head>
  <body>
    <p title="titre"> paragraphe avec un attribut "title"</p>
    <p>paragraphe sans  attribut "title"</p>
    <p title="autre"> paragraphe avec un attribut "title" égale à "autre"</p>
    <p title="titre1 titre2 titre3">paragraphe avec un attribut "title" égale à "titre1 titre2 titre3"</p>
    <p lang="fr-be">paragraphe avec un attribut "lang" égale à "fr-be"</p>
    <p lang="fr-fr">paragraphe avec un attribut "lang" égale à "fr-fr"</p>
    <p lang="en-us">paragraphe avec un attribut "lang" égale à "en-us"</p>
  </body>
</html> 

Ce n’est qu’un au revoir

C’est fini pour le moment, j’espère que vous avez découvert plein de chose et les utiliserez à bon escient (et souvent 🙂 ). J’ai écrit ce tutoriel en suivant cet article Sélecteurs CSS 2.1.





Les sélecteurs CSS, partie 1 : les bases

19 03 2010

En tant que web développeur l’utilisation de feuille de style est un passage obligé et vous connaissez probablement toutes les propriétés mais utilisez vous a bon escient toutes les possibilités des sélécteurs ?

C’est quoi un sélecteur ?

Oh presque rien, c’est ce qui permet aux propriétés de s’appliquer à un endroit précis, par exemple:

p {font-size : 12px;}

Ici le sélecteur c’est l’élément (la balise) « p ».

ah! OK.

Les sélecteurs servent, comme leur nom l’indique, à sélectionner une partie de la page HTML et y appliquer un style.

Le sélecteur universel « * »

Celui là vous ne le voyez pas souvent (même si on s’en sert implicitement, vous verrez par la suite), en fait il représente tous les éléments de la page, donc toutes les propriétés rattachées a l’élément « * » seront appliqués partout. Dans la plupart des cas vous vous en servirez pour faire ça:

* {margin:0px;}

Le sélecteur de type

Ici c’est pour sélectionné un élément (ne me demander pas pourquoi on l’appel sélecteur de type et pas d’élément), comme ceci:

p {margin-left:5px;}

Le sélecteur ici c’est l’élément « p », donc tous les éléments « p » de la page auront une marge de gauche de 5px.

Les pseudo-éléments

On désigne par ce terme les éléments qu’on ne peut atteindre avec les autres sélecteurs, par exemple la première ligne d’un paragraphe.

  • :first-line : celui-ci permet d’atteindre la première ligne d’un élément de type block, inline-block, list-item, table-caption et table-cell (voir cet article pour plus d’infos)
  • :first-letter : identique au précédent mais ne s’appliquera qu’au premier caractère alphanumérique de l’élément.
  • :before et :after : ceux-ci  sont intéressants car il permettent d’ajouter du contenu avant et après l’élément.

Vous savez ce qui vous attends ? Un petit exemple pour expliquer tout ça:

<html>
  <head>
    <style>
      p:first-line {font-family:verdana;}
      p:first-letter{color:red;}
      p.court{width:150px;}
      p.long{width:300px;}
      #essai:before{content:"before"; padding-right:5px;font-family:arial; background-color:#aaF000;}
      #essai:after{content:"after"; padding-left:5px;font-family:arial; background-color:#aaF000;}
    </style>
  </head>
  <body>
    <p>Ce paragraphe contient beaucoup de texte, et n'est pas très large</p>
    <p>Ce paragraphe contient beaucoup de texte mais est plus large que le précédent</p>
    <p id="essai">test sur les pseudo-éléments :before et :after</p>
  </body>
</html>

Ce que vous devriez obtenir:

Le sélecteur de classe

Ce sélecteur fait référence à l’attribut classe d’un élément, on utilise « . » pour le désigner, un petit exemple pour voir ?

<html>
  <head>
    <style>
      p{margin-left:5px;}
      p.uneClasse{margin-right:5px;}
    </style>
  </head>
  <body>
    <p class="uneClasse">du texte</p>
    <div class="uneClasse">une div</div>
  </body>
</html>

Le premier élément , le « p », aura donc une marge à droite de 5px et une marge à gauche de 5px (et oui! On peut mixer les sélecteurs), l’élément « div » n’aura quant à lui qu’une marge de droite de 5px (car on n’a pas définit de marge autre ni sur la classe ni sur l’élément).

On peut utiliser un sélecteur de classe indépendement d’un sélecteur de type, comme ceci:

.uneClasse {font-size:16px;}

Ici tous les éléments ayant un attribut « class » égale à « uneClasse » auront une taille de caractère de 16px. Cette notation revient à faire:

*.uneClasse {font-size:16px;}

Je vous avais bien dit que vous utilisiez le sélecteur universel implicitement.

A notez également pour qu’il est possible d’indiquer plusieurs classe dans l’attribut comme ceci:

<p class="rouge bleu vert"> rouge, vert ou bleu ?</p>

Mais laquelle s’applique, quand elles modifient la même propriété?

Bizarrement ce n’est pas l’ordre dans lequel les classes sont écrites dans l’attribut mais celui dans la feuille de style, essayez avec ça:

<html>
  <head>
    <style>
      .vert {color:green;font-weight:bold;}
      .rouge {color:red;font-family:arial;}
      .bleu {color:blue;text-decoration:underline;}
    </style>
  </head>
  <body>
    <p class="rouge bleu vert"> rouge, vert ou bleu ?</p>
  </body>
</html>

Et changez l’ordre des classes vert, rouge et bleu dans la définition du style. Dans cet exemple le texte sera de couleur bleue, toutes les autres propriétés définis par les classes sont appliqués à l’élément car il n’y en à pas une commune à chaque classe.

avec la classe bleu en dernier:

puis la classe rouge en dernier:

En y réfléchissant bien ce n’est pas si bizarre que ça, la feuille de style est « lu » par le navigateur de haut en bas, c’est donc le sélecteur le plus « bas » qui est appliqué.

Les pseudo-classes

On peut les considérer comme des attributs aux sélecteurs, ce sont des notations spécifiques qui permettent de définir les propriétés d’un style en fonction de l’état d’un élément ou lorsqu’un évènement se produit sur l’élément (directement ou par une classe) lié au style.

Pseudo-classes d’ancres

On parle ici des pseudo-classes qui vont affectés un élément « a » disposant de l’attribut « href », il y en à 2:

  • :link : ce sera l’apparence du lien tant qu’il n’est pas visité (cliqué).
  • :visited : l’apparence du lien après avoir été visité.
a:link {color:green}
a:visited {color:red}

Notez bien que ces deux pseudo-classes sont exclusives, un lien est soit visité (:visited) soit non-visité (:link).

Pseudo-classes dynamiques

Celles-ci sont moins restrictives, elles peuvent s’appliquer à beaucoup plus d’éléments:

  • :hover : se déclenche lors du passage de la souris sur l’élément.
  • :active : se déclenche lorsque l’élément est activé, par exemple en pressant le bouton.
  • :focus : se déclenche lorsque l’élément accepte des saisies au clavier.

Un petit exemple pour mieux comprendre:

<html>
  <head>
    <style>
      input:hover {background-color:#000;color:#F00;}
      input:active {border:2px solid #0FF}
      input:focus {background-color:#000; color:#FFF;}
    </style>
  </head>
  <body>
    <input type="text">
  </body>
</html>

Ce qu’on obtient pour :hover

pour :active

et pour :focus (la bordure jaune est du au navigateur que j’utilise!)

Le sélecteur d’ID

Celui là vous permet de définir un style en ciblant un élément par son attribut « id », pour ce faire utilisez cette notation #monId.

<html>
  <head>
    <style>
      p {background-color : #00F; color:#FFF;}
      #monID {background-color:#c0c0c0;}
    </style>
  </head>
  <body>
    <p id="monId">avec identifiant</p>
    <p>sans identifiant</p>
  </body>
</html>

La propriété « color » s’applique bien au deux éléments « p » mais seul celui avec l’identifiant « monId » à un arrière-plan gris, l’élément « p » sans identifiant a l’arrière-plan défini par le sélecteur « p ». Le sélecteur d’ID est donc prioritaire sur le sélecteur de type.

Comme ceci:

Bientôt la suite

Et nous voici à la fin de cette première partie sur les sélecteurs CSS, nous verrons les sélecteurs un peu plus avancé dans la seconde partie que vous retrouverez prochainement.