web-dev-qa-db-fra.com

CSS: Change le parent sur le focus de l'enfant

Disons que vous avez quelque chose comme:

<div class="parent">
    <input class="childInput" type="text" />
    <div class="sibling"></div>
</div>

Je veux changer l'apparence du parent/de la fratrie lorsque l'enfant reçoit le focus. Existe-t-il des astuces CSS pour faire ce genre de choses?

Modifier:

La raison de ma question est la suivante:

Je crée une application angulaire qui nécessite des champs de texte modifiables. Cela devrait ressembler à une étiquette jusqu'à ce que vous cliquiez dessus, à quel point cela devrait ressembler à une entrée de texte normale. J'ai stylé le champ de texte en fonction de: focus pour obtenir cet effet, mais le texte est coupé par les limites de la saisie de texte. J'ai également utilisé ng-show, ng-hide, ng-blur, ng-keypress et ng-click pour basculer entre le libellé et la saisie de texte en fonction des flous, des pressions et des clics. Cela a bien fonctionné, sauf pour une chose: après que ng-click = "setEdit (this, $ event)" du label change le booléen de modification utilisé par ng-show et ng-hide à true, il utilise un appel jQuery en .select () la saisie de texte. Cependant, ce n'est qu'après l'achèvement du clic-ng que tout est assimilé, de sorte que la saisie de texte perd de nouveau le focus. Étant donné que la saisie de texte ne reçoit jamais le focus, l'utilisation de ng-blur pour revenir à l'affichage de l'étiquette est erronée: l'utilisateur doit cliquer dans l'entrée de texte, puis cliquer à nouveau pour afficher à nouveau l'étiquette.

Modifier:

Voici un exemple de problème: http://plnkr.co/edit/synSIP?p=preview

26
AaronF

Vous pouvez maintenant le faire en CSS pur, vous n'avez donc pas besoin de JavaScript.

La nouvelle pseudo-classe CSS :focus-within pourrait aider dans de tels cas et faciliterait l’accessibilité lorsque des personnes utilisaient la tabulation pour naviguer, commune à l’utilisation de lecteurs d’écran.

.parent:focus-within {
  border: 1px solid #000;
}

La pseudo-classe: focus-inside établit une correspondance entre les éléments eux-mêmes match: focus ou qui ont des descendants qui correspondent: focus.

Vous pouvez vérifier quels navigateurs le supportent http://caniuse.com/#search=focus-within


Démo

fieldset {
  padding: 0 24px 24px !important;
}

fieldset legend {
  opacity: 0;
  padding: 0 8px;
  width: auto;
}

fieldset:focus-within {
  border: 1px solid #000;
}

fieldset:focus-within legend {
  opacity: 1;
}
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" rel="stylesheet" />

<div class="container">
  <form>
    <fieldset>
      <legend>Parent Element</legend>
      <div class="form-group">
        <label for="name">Name:</label>
        <input type="email" class="form-control" id="name" placeholder="Enter name">
      </div>
      <div class="form-group">
        <label for="email">Email:</label>
        <input type="email" class="form-control" id="email" placeholder="Enter email">
      </div>
    </fieldset>
  </form>
</div>

68
J J B

Il n'y a aucune chance de savoir comment faire cela avec CSS. CSS ne peut appeler que les frères et sœurs, les enfants, etc., pas les parents.

Vous pouvez utiliser simplement JS comme ceci:

<style>
.parent {background: green}
.focused {background: red;}
</style>
<div class="parent">
    <input class="childInput" type="text" />
    <div class="sibling"></div>
</div>

<script>
$('.parent > *')
    .focus(function() {
        $('.parent').addClass('focused');
    })
    .blur(function() {
        $('.parent').removeClass('focused');
    });
</script>

http://jsfiddle.net/C4bZ6/

Ce code prend tous les enfants directs de .parent et si vous en focalisez un, la classe focused est ajoutée au parent. Sur flou, cette classe est supprimée.

5
panther

Vous pouvez utiliser du CSS pur pour donner l’impression que l’entrée de texte n’est pas une entrée de texte sauf si elle est active

http://jsfiddle.net/michaelburtonray/C4bZ6/13/

input[type="text"] {
    border-color: transparent;
    transition-duration: 600ms;
    cursor: pointer;
    outline-style: none;
    text-overflow: Ellipsis;
}

input[type="text"]:focus {
    border-color: initial;
    cursor: auto;
    transition-duration: 300ms;
}
1
Michael

Essayez l'attribut contenteditible. Cela peut toutefois nécessiter plus de travail pour le transformer en données utilisables.

http://jsfiddle.net/michaelburtonray/C4bZ6/20/

<span class="parent" contenteditable>Click me</span>
0
Michael