Skip to content

Instantly share code, notes, and snippets.

@MarcusResell
Last active February 5, 2024 08:53
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save MarcusResell/e68a502f2105563a8ff9c2dd25c5870c to your computer and use it in GitHub Desktop.
Save MarcusResell/e68a502f2105563a8ff9c2dd25c5870c to your computer and use it in GitHub Desktop.
Dynamic checkboxes in Angular tutorial
<form [formGroup]="musicForm" (ngSubmit)="submit()">
<label>
<input type="checkbox" formControlName="selectAll">
Select/Unselect all
</label>
<label formArrayName="musicPreferences" *ngFor="let genre of musicForm.controls['musicPreferences'].controls; let i = index">
<input type="checkbox" [formControlName]="i">
{{musicPreferences[i].genre}}
</label>
<button>submit</button>
</form>
import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, FormArray, FormControl } from '@angular/forms';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit {
musicForm: FormGroup;
musicPreferences = [
{ id: 1, genre: 'Pop' },
{ id: 2, genre: 'Rock' },
{ id: 3, genre: 'Techno' },
{ id: 4, genre: 'Hiphop' }
];
constructor(private fb: FormBuilder) {
// Create a FormControl for each available music preference, initialize them as unchecked, and put them in an array
const formControls = this.musicPreferences.map(control => new FormControl(false));
// Create a FormControl for the select/unselect all checkbox
const selectAllControl = new FormControl(false);
// Simply add the list of FormControls to the FormGroup as a FormArray, add the selectAllControl separetely
this.musicForm = this.fb.group({
musicPreferences: new FormArray(formControls),
selectAll: selectAllControl
});
}
ngOnInit() {
this.onChanges();
}
onChanges(): void {
// Subscribe to changes on the selectAll checkbox
this.musicForm.get('selectAll').valueChanges.subscribe(bool => {
this.musicForm
.get('musicPreferences')
.patchValue(Array(this.musicPreferences.length).fill(bool), { emitEvent: false });
});
// Subscribe to changes on the music preference checkboxes
this.musicForm.get('musicPreferences').valueChanges.subscribe(val => {
const allSelected = val.every(bool => bool);
if (this.musicForm.get('selectAll').value !== allSelected) {
this.musicForm.get('selectAll').patchValue(allSelected, { emitEvent: false });
}
});
}
submit() {
// Filter out the unselected ids
const selectedPreferences = this.musicForm.value.musicPreferences
.map((checked, index) => checked ? this.musicPreferences[index].id : null)
.filter(value => value !== null);
// Do something with the result
}
}
<form [formGroup]="musicForm" (ngSubmit)="submit()">
<label formArrayName="musicPreferences" *ngFor="let genre of musicForm.controls.musicPreferences.controls; let i = index">
<input type="checkbox" [formControlName]="i">
{{musicPreferences[i].genre}}
</label>
<button>submit</button>
</form>
import { Component } from '@angular/core';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
musicPreferences = [
{ id: 1, genre: 'Pop' },
{ id: 2, genre: 'Rock' },
{ id: 3, genre: 'Techno' },
{ id: 4, genre: 'Hiphop' }
];
}
import { Component } from '@angular/core';
import { FormBuilder, FormGroup, FormArray, FormControl } from '@angular/forms';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
musicForm: FormGroup;
musicPreferences = [
{ id: 1, genre: 'Pop' },
{ id: 2, genre: 'Rock' },
{ id: 3, genre: 'Techno' },
{ id: 4, genre: 'Hiphop' }
];
constructor(private fb: FormBuilder) {
// Create a FormControl for each available music preference, initialize them as unchecked, and put them in an array
const formControls = this.musicPreferences.map(control => new FormControl(false));
// Simply add the list of FormControls to the FormGroup as a FormArray
this.musicForm = this.fb.group({
musicPreferences: new FormArray(formControls)
});
}
submit() {
// do something
}
}
submit() {
// Filter out the unselected ids
const selectedPreferences = this.musicForm.value.musicPreferences
.map((checked, index) => checked ? this.musicPreferences[index].id : null)
.filter(value => value !== null);
// Do something with the result
...
}
constructor(private fb: FormBuilder) {
const formControls = this.musicPreferences.map(control => new FormControl(false));
// Create a FormControl for the select/unselect all checkbox
const selectAllControl = new FormControl(false);
// Add the selectAllControl separetely
this.musicForm = this.fb.group({
musicPreferences: new FormArray(formControls),
selectAll: selectAllControl
});
}
// Import and implement OnInit from the '@angular/core' library, and implement the onChanges function
ngOnInit() {
this.onChanges();
}
onChanges(): void {
// Subscribe to changes on the selectAll checkbox
this.musicForm.get('selectAll').valueChanges.subscribe(bool => {
this.form
.get('musicPreferences')
.patchValue(Array(this.musicPreferences.length).fill(bool), { emitEvent: false });
});
// Subscribe to changes on the music preference checkboxes
this.musicForm.get('musicPreferences').valueChanges.subscribe(val => {
const allSelected = val.every(bool => bool);
if (this.musicForm.get('selectAll').value !== allSelected) {
this.musicForm.get('selectAll').patchValue(allSelected, { emitEvent: false });
}
});
}
@cpeddieTC
Copy link

I have spent days trying to figure out how to use reactive forms to do something similar to this- dynamic checkboxes. Thanks to this post I was finally able to figure out how they work and get mine implmented after days of trying ! Great post, well written and easy to understand. Thanks!

@Danielitouci96
Copy link

hi, how I can validate that?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment