J'ai un composant LoginForm. Je veux vérifier avant de soumettre, que loginName
et password
sont définis. J'ai essayé avec ce code (beaucoup de trucs omis):
class LoginForm extends Component {
constructor() {
super();
this.state = {
error: "",
loginName: "",
password: "",
remember: true
};
}
submit(e) {
e.preventDefault();
if(!this.state.loginName || !this.state.password) { //this is null
this.setState({ error: "Fill in both fields" });
} else {
console.log("submitting form");
}
}
render() {
return (
<div className="col-xs-12 col-sm-6 col-md-4">
<form className="login" onSubmit={this.submit}>
<button type="submit" className="btn btn-default">Sign in</button>
</form>
</div>
);
}
}
export default LoginForm;
cependant, j'obtiens un TypeError
dans le gestionnaire d'événements, disant que this
est nul.
Que dois-je faire?
Vous devez définir this
pour la méthode submit
car maintenant this
est undefined
, pour cette opération, vous pouvez utiliser .bind
onSubmit={ this.submit.bind(this) }
ou vous pouvez utiliser fonction flèche
onSubmit={ (e) => this.submit(e) }
React vous a déjà lié des rappels. Mais maintenant, il a disparu, et vous devez le lier vous-même ou faire un emballage comme
onSubmit={() => this.submit()}
Pour ceux qui utilisent Babel, vous pouvez utiliser opérateur de liaison avec transform-function-bind plugin:
onSubmit={::this.submit}
qui est un sucre syntaxique pour:
onSubmit={this.submit.bind(this)}
Vous n'avez pas lié le this
à votre classe; Vous pouvez utiliser la fonction de propriétés de classe ES6 pour contourner le problème de la manière la plus propre; Il vous suffit donc de:
submit = (e) => {
// some code here
}
La fonction flèche le liera automatiquement; Bien plus agréable que de le lier dans un constructeur; la chose la plus importante est de ne jamais le faire de cette façon:
onSubmit={() => this.submit()}
Cela va créer une fonction qui est un objet en javascript et cela prendra de la mémoire et réside maintenant dans votre fonction redner! ce qui le rend si cher. La fonction render
fait partie du code qui s'exécute tant de fois et chaque fois que votre fonction submit
est également créée et vous vous retrouverez avec des problèmes de performances. Votre code devrait donc être comme:
class LoginForm extends Component {
submit = (e) => {
// some code here
}
render() {
return (
<form className="login" onSubmit={ this.submit }>
<button type="submit" className="btn btn-default">Sign in</button>
</form>
);
}
}
export default LoginForm;
Ici, vous n'aurez pas de problème de performances, vous n'aurez pas non plus de problème de liaison et votre code sera beaucoup plus agréable.