Skip to content

Comment créer un formulaire avec ngForm dans Angular ?

Pensez à ajouter FormsModule

FormsModule est un module Angular qui contient une série de directives et de services qui vous permettent de créer et de gérer des formulaires dans votre application Angular. Il contient notamment les directives suivantes :

  • ngModel : permet de lier la valeur d'un champ de formulaire à une propriété d'un composant.
  • ngModelGroup : permet de grouper des champs de formulaire de manière à ce qu'ils partagent une validation et une gestion de l'état communs.
  • ngForm : permet de créer un formulaire Angular à partir d'un formulaire HTML.
  • formControlName : permet de lier un champ de formulaire à un FormControl dans un FormGroup.

Pour utiliser FormsModule dans votre application Angular, vous devez l'importer dans votre module principal ou dans un module dédié aux formulaires, et l'ajouter à la liste des imports du décorateur @NgModule.

ts
import { FormsModule } from '@angular/forms';

@NgModule({
  declarations: [
     // Ici contient les composants qui profitent de FormsModule
  ],
  imports: [
    FormsModule,
    // d'autres imports ici
  ]
})
export class MonModule { }
import { FormsModule } from '@angular/forms';

@NgModule({
  declarations: [
     // Ici contient les composants qui profitent de FormsModule
  ],
  imports: [
    FormsModule,
    // d'autres imports ici
  ]
})
export class MonModule { }

ngForm ?

ngForm est un module d'Angular qui fournit des directives et des classes pour travailler avec des formulaires HTML. Il permet de créer des formulaires dynamiques et de valider les données saisies par l'utilisateur. Il est utilisé ici pour accéder aux données saisies par l'utilisateur et pour vérifier si le formulaire est valide avant de soumettre les données.

Solution 1. Passer ngForm dans ngSubmit dans le template

ts
import { Component } from '@angular/core';

@Component({
  selector: 'app-login',
  template: `
    <form (ngSubmit)="onSubmit(loginForm)">
      <input type="text" name="username" ngModel required>
      <input type="password" name="password" ngModel required>
      <button type="submit" [disabled]="!loginForm.valid">Login</button>
    </form>
  `
})
export class LoginComponent {
  onSubmit(form: NgForm) {
    console.log(form.value);
    // Do login here
  }
}
import { Component } from '@angular/core';

@Component({
  selector: 'app-login',
  template: `
    <form (ngSubmit)="onSubmit(loginForm)">
      <input type="text" name="username" ngModel required>
      <input type="password" name="password" ngModel required>
      <button type="submit" [disabled]="!loginForm.valid">Login</button>
    </form>
  `
})
export class LoginComponent {
  onSubmit(form: NgForm) {
    console.log(form.value);
    // Do login here
  }
}

Le second exemple montre comment utiliser ngForm dans Angular en passant ngForm dans ngSubmit dans le template.

On utilise ngModel pour associer les champs de saisie à des propriétés de notre composant. Ces propriétés contiendront les valeurs saisies par l'utilisateur.

html
<input type="text" name="username" ngModel required>
<input type="password" name="password" ngModel required>
<input type="text" name="username" ngModel required>
<input type="password" name="password" ngModel required>

On utilise la propriété valid de ngForm pour désactiver le bouton de soumission si le formulaire n'est pas valide :

html
<button type="submit" [disabled]="!loginForm.valid">Login</button>
<button type="submit" [disabled]="!loginForm.valid">Login</button>
  1. Enfin, on utilise ngSubmit pour gérer l'événement de soumission du formulaire, et on passe ngForm en argument de la méthode onSubmit :
html
<form (ngSubmit)="onSubmit(loginForm)">
<form (ngSubmit)="onSubmit(loginForm)">

Quelle est la différence entre la ngSubmit et submit ?

La directive ngSubmit est une directive d'événement Angular qui est utilisée pour détecter la soumission d'un formulaire. Elle est déclenchée lorsque l'utilisateur clique sur le bouton de soumission du formulaire ou appuie sur la touche "Entrée" lorsqu'un champ de formulaire a le focus.

Voici comment utiliser la directive ngSubmit dans un template HTML :

html
<form (ngSubmit)="onSubmit()">
  <!-- Champs de formulaire ici -->
  <button type="submit">Envoyer</button>
</form>
<form (ngSubmit)="onSubmit()">
  <!-- Champs de formulaire ici -->
  <button type="submit">Envoyer</button>
</form>

La propriété submit est une propriété de l'objet HTMLFormElement qui représente le formulaire dans le DOM (Document Object Model). Elle peut être utilisée pour soumettre le formulaire de manière programmatique en utilisant JavaScript.

Voici comment utiliser la propriété submit dans du code JavaScript :

js
const form = document.querySelector('form');
form.submit();
const form = document.querySelector('form');
form.submit();

Dans un projet Angular, il est recommandé d'utiliser la directive ngSubmit plutôt que la propriété submit. En effet, la directive ngSubmit est spécifique à Angular et est conçue pour fonctionner de manière intégrée avec les autres composants et fonctionnalités d'Angular, tels que les formulaires avec ngForm et la gestion des données avec ngModel.

Utiliser la directive ngSubmit vous permet de déclarer une méthode de soumission de formulaire dans votre composant Angular, ce qui vous permet de traiter les données du formulaire de manière centralisée et structurée. Cela vous évite également d'avoir à manipuler le DOM ou à écrire du code JavaScript "brut" pour gérer la soumission du formulaire.

  1. Enfin, dans la méthode onSubmit, on utilise la propriété value de ngForm pour accéder aux données du formulaire :
ts
onSubmit(form: NgForm) {
    console.log(form.value);
    // Do login here
}
onSubmit(form: NgForm) {
    console.log(form.value);
    // Do login here
}

Solution 2. Utiliser @ViewChild :

ts
import { Component, ViewChild } from '@angular/core';
import { NgForm } from '@angular/forms';

@Component({
  selector: 'app-login',
  template: `
    <form #loginForm="ngForm" (ngSubmit)="onSubmit()">
      <input type="text" name="username" ngModel required>
      <input type="password" name="password" ngModel required>
      <button type="submit" [disabled]="!loginForm.valid">Login</button>
    </form>
  `
})
export class LoginComponent {
  @ViewChild('loginForm') loginForm!: NgForm;

  onSubmit() {
    console.log(this.loginForm.value);
    // Do login here
  }
}
import { Component, ViewChild } from '@angular/core';
import { NgForm } from '@angular/forms';

@Component({
  selector: 'app-login',
  template: `
    <form #loginForm="ngForm" (ngSubmit)="onSubmit()">
      <input type="text" name="username" ngModel required>
      <input type="password" name="password" ngModel required>
      <button type="submit" [disabled]="!loginForm.valid">Login</button>
    </form>
  `
})
export class LoginComponent {
  @ViewChild('loginForm') loginForm!: NgForm;

  onSubmit() {
    console.log(this.loginForm.value);
    // Do login here
  }
}
  1. On utilise la décorateur @ViewChild pour récupérer une référence à notre formulaire dans le composant en utilisant la propriété #loginForm="ngForm" dans la balise form.
html
<form #loginForm="ngForm" (ngSubmit)="onSubmit()">
<form #loginForm="ngForm" (ngSubmit)="onSubmit()">
  1. Enfin, dans la méthode onSubmit, on utilise la propriété value de notre référence pour accéder aux données du formulaire :
ts
onSubmit() {
    console.log(this.loginForm.value);
    // Do login here
}
onSubmit() {
    console.log(this.loginForm.value);
    // Do login here
}

Solution 1 ou 2 ?

Il n'y a pas vraiment de "meilleure" solution entre les deux exemples car cela dépend des besoins spécifiques de l'application. Les deux solutions sont valides et peuvent être utilisées en fonction des besoins de l'application.

L'utilisation de @ViewChild dans le premier exemple est utile lorsque vous avez besoin d'accéder à des propriétés spécifiques de ngForm dans le composant. Cela permet de simplifier l'accès aux données du formulaire et de vérifier la validité du formulaire directement à partir de la référence de ngForm.

D'autre part, Passer ngForm dans ngSubmit dans le template est plus simple à utiliser dans les scénarios où vous avez besoin d'accéder aux données du formulaire uniquement lors de la soumission. Cela permet de passer des données supplémentaires avec le formulaire lors de la soumission.