Simplifying Form Management in Angular with FormGroupDirective

aminkarimi_sis

Amin-Karimi

Posted on August 7, 2024

Simplifying Form Management in Angular with FormGroupDirective

As an Angular developer, managing forms can sometimes be a daunting task, especially when using ngValueAccessor. While ngValueAccessor is powerful, it often requires implementing numerous functions to handle value retrieval and updates for our form elements. Recently, I transitioned to using FormGroupDirective, and it has significantly streamlined the process. Here’s why this switch was a game-changer for me and my team:

Why FormGroupDirective?

  1. Simplicity in Implementation
    With FormGroupDirective, much of the boilerplate code required by ngValueAccessor is eliminated. This means less time writing repetitive code and more time focusing on business logic.

  2. Better Synchronization of Values
    FormGroupDirective automatically synchronizes values, so there’s no need to write additional functions for value retrieval and setting. This makes the code cleaner and easier to maintain.

  3. Improved Code Readability
    Code written with FormGroupDirective is significantly more readable and understandable. This is especially beneficial for the entire development team, including newcomers.

  4. Greater Flexibility
    Using FormGroupDirective provides more flexibility in managing forms, allowing us to easily handle more complex forms.

Let's dive into a practical example to illustrate how FormGroupDirective can simplify form management.

Before: Using ngValueAccessor

import { Component, forwardRef } from '@angular/core';
import { NG_VALUE_ACCESSOR, ControlValueAccessor } from '@angular/forms';

@Component({
  selector: 'app-custom-input',
  template: `
    <input type="text" [value]="value" (input)="onInput($event.target.value)" />
  `,
  providers: [
    {
      provide: NG_VALUE_ACCESSOR,
      useExisting: forwardRef(() => CustomInputComponent),
      multi: true,
    },
  ],
})
export class CustomInputComponent implements ControlValueAccessor {
  value: string;

  onChange: any = () => {};
  onTouched: any = () => {};

  writeValue(value: any): void {
    this.value = value;
  }

  registerOnChange(fn: any): void {
    this.onChange = fn;
  }

  registerOnTouched(fn: any): void {
    this.onTouched = fn;
  }

  onInput(value: string) {
    this.value = value;
    this.onChange(value);
  }
}
Enter fullscreen mode Exit fullscreen mode

After: Using FormGroupDirective

import { Component, Input } from '@angular/core';
import { FormGroup, FormGroupDirective, ReactiveFormsModule } from '@angular/forms';

@Component({
  selector: 'app-custom-form',
  template: `
    <form [formGroup]="form">
      <input [formControlName]="controlName" />
    </form>
  `,
  standalone:true,
  imports:[ReactiveFormsModule]
})
export class CustomFormComponent {
  form!: FormGroup;
  @Input({ required: true }) controlName!: string

  constructor(private _rootFormGroup: FormGroupDirective,) {
    this.form = this._rootFormGroup.control as FormGroup;
  }

}
Enter fullscreen mode Exit fullscreen mode
💖 💪 🙅 🚩
aminkarimi_sis
Amin-Karimi

Posted on August 7, 2024

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related