Angular: Select checkbox on another checkbox selection ( dynamic form control )

261 views Asked by At

I'm new to angular.
enter image description here

I have this UI. I wanted to make Bill To checkbox checked if any one (Address, Email or Phone) of the checkbox is checked. I'm using dynamic form control for checkbox.

code snippet: This solution didnt work , as combineLatest is emitting only when all the three checkboxes get selected

combineLatest([this.form.customerInfo.address.valueChanges(),
  this.form.customerInfo.email.valueChanges(),
  this.form.customerInfo.phone.valueChanges()])
  .subscribe((formValues)=>{
    if (formValues.every((value) => value === false || value === undefined)) {
      this.form.customerInfo.billTo.setValue(false)
    }
    else {
      this.form.customerInfo.billTo.setValue(true)
    }
});

this.form.customerInfo.billTo.valueChanges().pipe(distinctUntilChanged()).subscribe(value =>{
// if billTo is false or unchecked- unchecked all
  if(!value){
    this.form.customerInfo.address.setValue(value);
    this.form.customerInfo.phone.setValue(value);
    this.form.customerInfo.email.setValue(value);
  }

})

another solution: it's a bit complicated

combineLatest([
  this.form.customer.address.valueChanges().pipe(startWith(false)),
  this.form.customer.phone.valueChanges().pipe(startWith(false)),
  this.form.customer.email.valueChanges().pipe(startWith(false)),
])
  // adding debounce until we can listen for form changes and patch multiple form values simultaneously
  .pipe(debounceTime(100))
  .subscribe(([address, phone, email]) => {
    if ((address || phone || email) && !this.form.customerInfo.billTo.value) {
      // one of the nested values is true, and billTo is false, make billTo true
      this.form.customer.billTo.setValue(true);
    }
  });

// when customer toggle billTo to false, we set all children to false
this.form.customer.billTo
  .valueChanges()
  .pipe(filter((value) => value !== true))
  .subscribe(() => {
    const address = this.form.customer.address.value;
    const phone = this.form.customer.phone.value;
    const email = this.form.customer.email.value;
    // if any of the nested values are true, set them to false
    if (address) {
      this.form.customer.address.setValue(false);
    }
    if (phone) {
      this.form.customer.phone.setValue(false);
    }
    if (email) {
      this.form.customer.email.setValue(false);
    }
  });

Can anyone tell how to improve this? Thanks in advance.

1

There are 1 answers

0
Ashrik Ahamed On

I did it like this,

Assume that i have a parent check that can select itself and its child one :

<mat-checkbox(change)="onCheckBoxChange('parent', $event)"
                                        [checked]="selection.isSelected('parent')">
                          </mat-checkbox>
<mat-checkbox"(change)="onCheckBoxChange('child', $event)"
                                                  [checked]="selection.isSelected('child')"></mat-checkbox>`

And then when the onChange method triggers do like this:

onCheckBoxChange(attr: string, event: MatCheckboxChange) {
    this.selection.toggle(attr);

    if (this.selection.isSelected('parent') && event.checked){
    this.selection.select('child')   //Here you can pass all the check box names that you need to select
}}