Reactive forms in Angular provide a code-driven way to build and manage forms. Instead of defining form logic only in the template, you configure form structure, validation, and state in the TypeScript class using FormGroup and FormControl. This makes reactive forms ideal for complex, dynamic, and highly validated form scenarios.
? Best for complex & dynamic forms
Validators.required or Validators.email that enforce rules.[formGroup] and formControlName directives.To use reactive forms, you must first import ReactiveFormsModule into your Angular root or feature module. Then, in your component, you define a FormGroup instance with one or more FormControl objects.
In the template, you bind the FormGroup instance to the form element using [formGroup], and each field is bound using formControlName. Angular automatically keeps the form model and the view in sync.
First, enable reactive forms support in your Angular module:
// app.module.ts - register ReactiveFormsModule
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { ReactiveFormsModule } from '@angular/forms';
import { AppComponent } from './app.component';
@NgModule({
declarations: [AppComponent],
imports: [BrowserModule, ReactiveFormsModule],
bootstrap: [AppComponent]
})
export class AppModule {}
This example creates a simple user form with name and email fields and basic validation.
// app.component.ts - reactive user form definition
import { Component } from '@angular/core';
import { FormGroup, FormControl, Validators } from '@angular/forms';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
userForm = new FormGroup({
name: new FormControl('', [Validators.required, Validators.minLength(3)]),
email: new FormControl('', [Validators.required, Validators.email])
});
submitForm() {
console.log('Form Submitted', this.userForm.value); // Log the form values when the form is valid
}
}
<!-- app.component.html - bind the FormGroup to the template -->
<form [formGroup]="userForm" (ngSubmit)="submitForm()">
<label>Name:</label>
<input type="text" formControlName="name">
<div class="error" *ngIf="userForm.get('name')?.errors && userForm.get('name')?.touched">
<span *ngIf="userForm.get('name')?.errors?.required">Name is required.</span>
<span *ngIf="userForm.get('name')?.errors?.minlength">Name must be at least 3 characters.</span>
</div>
<br><br>
<label>Email:</label>
<input type="email" formControlName="email">
<div class="error" *ngIf="userForm.get('email')?.errors && userForm.get('email')?.touched">
<span *ngIf="userForm.get('email')?.errors?.required">Email is required.</span>
<span *ngIf="userForm.get('email')?.errors?.email">Invalid email format.</span>
</div>
<br><br>
<button type="submit" [disabled]="userForm.invalid">Submit</button>
</form>
submitForm(), logging the form values in the browser console.ReactiveFormsModule in the appropriate module (e.g., app.module.ts).userForm.get('controlName') to read values, check validity, or subscribe to value changes.touched and dirty states to avoid showing error messages before the user interacts with a field.email and password controls.required and minLength(6) validators.rememberMe checkbox as a FormControl and log its value when the form is submitted.[disabled]="loginForm.invalid".