ReactJS ajoute une classe dynamique aux noms de classe manuels


158

J'ai besoin d'ajouter une classe dynamique à une liste de classes régulières, mais je n'ai aucune idée de comment (j'utilise babel), quelque chose comme ceci:

<div className="wrapper searchDiv {this.state.something}">
...
</div>

Des idées?


Réponses utiles pour les meilleures pratiques de style reactjs sur lien
Rahil Ahmad

Réponses:


241

Vous pouvez soit faire ceci, JavaScript normal:

className={'wrapper searchDiv ' + this.state.something}

ou la version du modèle de chaîne, avec des backticks:

className={`wrapper searchDiv ${this.state.something}`}

Les deux types sont bien sûr juste du JavaScript, mais le premier modèle est le type traditionnel.

Quoi qu'il en soit, dans JSX, tout ce qui est entre accolades est exécuté en JavaScript, vous pouvez donc faire ce que vous voulez. Mais combiner des chaînes JSX et des accolades n'est pas une option pour les attributs.


et que faire en cas de classes multiples?
Pardeep Jain

5
Dans le cas de plusieurs classes dynamiques, toutes les classes dynamiques doivent provenir de l'état, c'est-à-dire qu'il n'est pas possible d'utiliser element.classList.add("my-class"); permettant donc:className={`wrapper searchDiv ${this.state.something ? "my-class " : ""} ${this.state.somethingElse ? "my-other-class " : ""}`}
Kevin Farrugia

className={'wrapper searchDiv} + this.state.isTrue ? 'my-class' : ' 'Cela ne marche pas. Quelqu'un peut-il dire pourquoi?
kryptokinght

54

En fonction du nombre de classes dynamiques que vous devez ajouter au fur et à mesure de la croissance de votre projet, il vaut probablement la peine de consulter l' utilitaire de noms de classe de JedWatson sur GitHub. Il vous permet de représenter vos classes conditionnelles en tant qu'objet et renvoie celles dont la valeur est vraie.

Donc, à titre d'exemple tiré de sa documentation React:

render () {

var btnClass = classNames({
  'btn': true,
  'btn-pressed': this.state.isPressed,
  'btn-over': !this.state.isPressed && this.state.isHovered
});

return <button className={btnClass}>I'm a button!</button>;

} 

Étant donné que React déclenche un nouveau rendu en cas de changement d'état, vos noms de classes dynamiques sont gérés naturellement et tenus à jour avec l'état de votre composant.


5
L'utilisation de classNames pour une chose aussi simple est une exagération. Évitez de l'utiliser et optez pour la réponse simple de dannyjolie
checklist

2
Êtes-vous sûr que c'est une chose simple? Presque toujours, vous voulez avoir un contrôle total fin sur les classes appliquées aux éléments.
Dragas

5
@checklist Je dirais le contraire, le package des noms de classes fait 1,1 Ko avant Gzipping (et un demi-Ko après Gzipping), n'a pas de dépendances et fournit une API beaucoup plus propre pour la manipulation des noms de classes. Il n'est pas nécessaire d'optimiser prématurément quelque chose d'aussi petit, lorsque l'API est beaucoup plus expressive. Lorsque vous utilisez la manipulation de chaînes standard, vous devez vous rappeler de tenir compte de l'espacement, soit avant chaque nom de classe conditionnel, soit après chaque nom de classe standard.
tomhughes

classNames est génial, j'ai trouvé que la lecture, l'ajout et la correction d'accessoires étaient plus faciles que la manipulation manuelle car le composant devenait de plus en plus complexe.
MiFiHiBye

37

Une syntaxe simple possible sera:

<div className={`wrapper searchDiv ${this.state.something}`}>

26

Voici la meilleure option pour Dynamic className, faites simplement une concaténation comme nous le faisons en Javascript.

     className={
        "badge " +
        (this.state.value ? "badge-primary " : "badge-danger ") +
        " m-4"
      }

C'est la meilleure solution sans aucun problème de peluchage. A travaillé comme un charme. Je vous remercie.
Royal.O

3

Si vous avez besoin de noms de style qui doivent apparaître selon la condition d'état, je préfère utiliser cette construction:

<div className={'wrapper searchDiv' + (this.state.something === "a" ? " anotherClass" : "")'}>

2

essayez ceci en utilisant des crochets:

        const [dynamicClasses, setDynamicClasses] = React.useState([
    "dynamicClass1", "dynamicClass2
]);

et ajoutez ceci dans l'attribut className:

<div className=`wrapper searchDiv ${[...dynamicClasses]}`>
...
</div>

pour ajouter une classe:

    const addClass = newClass => {
       setDynamicClasses([...dynamicClasses, newClass])
    }

pour supprimer la classe:

        const deleteClass= classToDelete => {

           setDynamicClasses(dynamicClasses.filter(class = > {
             class !== classToDelete
           }));

        }

1

Vous pouvez utiliser ce package npm. Il gère tout et propose des options pour les classes statiques et dynamiques basées sur une variable ou une fonction.

// Support for string arguments
getClassNames('class1', 'class2');

// support for Object
getClassNames({class1: true, class2 : false});

// support for all type of data
getClassNames('class1', 'class2', ['class3', 'class4'], { 
    class5 : function() { return false; },
    class6 : function() { return true; }
});

<div className={getClassNames({class1: true, class2 : false})} />

1
getBadgeClasses() {
    let classes = "badge m-2 ";
    classes += (this.state.count === 0) ? "badge-warning" : "badge-primary";
    return classes;
}

<span className={this.getBadgeClasses()}>Total Count</span>

-1
className={css(styles.mainDiv, 'subContainer')}

Cette solution a fait ses preuves dans React SPFx.

Ajoutez également une instruction d'importation:

import { css } from 'office-ui-fabric-react/lib/Utilities';
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.