6

I have an array of languages for a user to select and a default language to pick. When a default language is selected, I want to make sure the checkbox for that language is also selected programmatically.

I'm not sure how to use patchValue on the FormArray of languages.

component.ts

import { FormGroup, FormControl, FormArray, Validators } from '@angular/forms';
...

constructor(...) {
    this.languages = ['English', 'Spanish', 'Mandarin', 'Klingon'];

    this.myForm = new FormGroup({
        languages: this.createLanguagesControl(),
        defaultLanguage: new FormControl('', Validators.required)
    });
}

createLanguagesControl() {
    const controls = this.languages.map(language => {
        return new FormControl(false);
    });
    return new FormArray(controls);
}

defaultLanguageSelection() {
    let formValues = this.myForm.value;
    console.log('defaultLanguageSelection', formValues.defaultLanguage);

    let i = 0;
    for (let language of this.languages) {
        if (language == formValues.defaultLanguage) {              // find the index of our newly-selected default language in the languages array
            this.myForm.patchValue({languages: {i: true}});        // make sure the language is checked
        }
        i++;
    }
}

component.html

<mat-card-content>

    <div formArrayName="languages" *ngFor="let language of languages; index as i">
        <mat-checkbox formControlName="{{ i }}">
            {{ language }}
        </mat-checkbox>
    </div>

    <mat-form-field>
        <mat-label>Default Language</mat-label>
        <mat-select formControlName="defaultLanguage">
            <mat-option *ngFor="let language of languages" [value]="language" (click)="defaultLanguageSelection()">
                {{ language }}
            </mat-option>
        </mat-select>
    </mat-form-field>

</mat-card-content>
3
  • 1
    Could you please create stackblitz working project for this problem. Commented Jan 9, 2020 at 3:44
  • @Ryan, why you use a FormArray if you really only want to store an unique variable -defaultLanguage-?, check my answer Commented Jan 9, 2020 at 8:46
  • Hi @Eliseo, this is a very simplified example of the full code I'm trying to build :) Commented Jan 10, 2020 at 0:05

2 Answers 2

13

Get language formArray first and then use patchValue on the matching control

let langArr = <FormArray>this.myForm.controls["languages"];
langArr.controls[i].patchValue(true);     // i is the matching index

Stackblitz demo

Sign up to request clarification or add additional context in comments.

Comments

0

You don't need use a FormArray to show the selected language or a complex formGroup to store a simple value. If you has an unique variable use a FormControl

defaultLanguage:FormControl=new FormControl('')

//and the .html

<mat-form-field>
    <mat-label>Default Language</mat-label>
    <mat-select [formControl]="defaultLanguage">
        <mat-option *ngFor="let language of languages" [value]="language">
            {{ language }}
        </mat-option>
    </mat-select>
</mat-form-field>

If you want to show if is checked in a list just use defaultLanguage.value, some like (*)

<div *ngFor="let language of languages; index as i">
    <mat-checkbox [checked]="language==defaultLanguage.value"
                  (change)="defaultLanguage.setValue($event.checked?language:null)">
        {{ language }}
    </mat-checkbox>
</div>

(*) I write the code if you want to change the defaultLanguage checking some checkbox, If you only whant to show even it's innecesary a input, just a

<div *ngFor="let language of languages; index as i">
       {{language==defaultLanguage.value?'ok':''}}{{ language }}
</div>

See the stackblitz

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.