web-dev-qa-db-fra.com

Sélecteur CSS pour sélectionner un élément qui vient AVANT un autre élément?

Je travaille sur une page de connexion pour mon site Web et je veux mettre en gras l'étiquette qui vient avant la zone de saisie lorsque la zone de texte gagne le focus. En ce moment, j'ai le balisage suivant:

<label for="username">Username:</label>
<input type="textbox" id="username" />

<label for="password">Password:</label>
<input type="textbox" id="password" />

Je peux utiliser le sélecteur adjacent pour sélectionner l'étiquette après la zone de texte, mais je ne peux pas sélectionner l'élément avant. Je peux utiliser cette règle de sélection CSS, mais elle ne sélectionne que l'étiquette après, donc lorsque la zone de texte du nom d'utilisateur gagne le focus, l'étiquette du mot de passe devient en gras.

input:focus + label {font-weight: bold}

Puis-je faire quelque chose pour que cela fonctionne? Je sais que JavaScript pourrait être utilisé pour le faire facilement, mais j'aimerais utiliser une solution purement CSS si possible, je ne peux tout simplement pas trouver un moyen de le faire.

64
Dan Herbert

Il serait possible d'utiliser le "sélecteur de frère adjacent" si le input était avant le label. Placez simplement le input avant le label, puis modifiez la disposition pour mettre label avant le input. Voici un exemple:

<head runat="server">
    <title></title>
    <style type="text/css">
    input:focus + label {font-weight: bold}
    </style>
</head>
<body>
    <form id="form1" runat="server">
    <div style="direction:rtl">
        <input type="text" id="username" />
        <label for="username">Username:</label>
    </div>
    <div style="direction:rtl">
        <input type="password" id="password" />
        <label for="password">Password:</label>
    </div>
    </form>
</body>

(C'est une sorte de hack, j'utiliserais personnellement javascript pour ce faire)

input:focus + label {font-weight: bold}
<form id="form1" runat="server">
  <div style="direction:rtl">
    <input type="text" id="username" />
    <label for="username">Username:</label>
  </div>
  <div style="direction:rtl">
    <input type="password" id="password" />
    <label for="password">Password:</label>
  </div>
</form>
24
Matt Brunell

Le CSS Selectors 4 Spec fournit une syntaxe pour définir le "sujet" d'un sélecteur en utilisant un !. Au début de 2016, cela n'est disponible dans aucun navigateur. J'inclus cela parce que ce sera la bonne façon de le faire en utilisant du CSS pur une fois que les navigateurs auront implémenté cette syntaxe.

Compte tenu du balisage dans la question

<label for="username">Username:</label>
<input type="textbox" id="username" />

<label for="password">Password:</label>
<input type="textbox" id="password" />

Ce CSS ferait l'affaire.

label:has(+ input:focus) {font-weight: bold}

Bien sûr, cela suppose que les navigateurs implémentent réellement le sélecteur de sujet et qu'il n'y a aucun bogue lié au fonctionnement de cette syntaxe avec le :focus pseudo-classe.

36
Dan Herbert

Il n'y a pas de sélecteur qui vous donnera l'élément précédent en utilisant CSS ..

Vous devrez utiliser javascript pour gérer ce que vous recherchez.

8
JayTee

Utilisez ce sélecteur:

label[for=username]
{
font-weight: bold
}

cela sélectionnera le libellé qui a la valeur "nom d'utilisateur" dans l'attribut "pour"

5
user434917

Faire flotter l'élément d'entrée vers la droite permet d'obtenir un ordre d'élément correct sans changer l'ordre de "Username" et ":" dans le texte de l'étiquette que vous obtenez avec direction: rtl.

<style type="text/css">
    form {text-align: right;}
    input:focus + label {font-weight: bold}
    input {float:right; clear:right;}
</style>
<form>
    <div>
        <input type="text" id="username" />
        <label for="username">Username:</label>
    </div>
    <div>
        <input type="password" id="password" />
        <label for="password">Password:</label>
    </div>
</form>
5
Ole Helgesen