1

In my Angualar application I have a form with several text fields like order ID and order date. My form also has a FormArray where each element is a FormGroup representing a row of fields. This form array has 1 FormGroup at startup and more can be addedby clicking on a button. After I submit my form I want to reset the form after getting a succesful response from posting data to a REST service. My reset code form is as follows.:

resetItems(): void {
  this.orderForm.reset();
  this.clearErrorsFromFormGroup(this.orderForm);
  let items = this.orderForm.get('items') as FormArray;
  items.controls = [];
  this.addItem();
  this.clearErrorsFromFormGroup(items.at(0) as FormGroup);


}

  private clearErrorsFromFormGroup(formGroup: FormGroup): void {
    Object.keys(formGroup.controls).forEach(key => {
      formGroup.controls[key].setErrors(null);
    });
  }


When executing the above the top level fields like order Id and Order date are reset and are not highlighted red as I have removed the errors. I want to set my form array to be the same way it was at start up with 1 element. My code clears the form array and adds a rowData Element. I then clear the errors for the rowData FormGroup. On the UI The fields for this rowData are all cleared but theys are highlighted red even though I have cleared the errors. Can anyone help please?

I have included a StackBlitz link to demonstrate this at https://stackblitz.com/edit/angular-8qjphu

2
  • your stackblitz demo doesn't have the code you have above Commented May 9, 2020 at 2:28
  • Sorry about that @brijmcq. I have now. updated the link with the correct one. Commented May 9, 2020 at 3:07

2 Answers 2

4

The items is a FormArray and the way you clear your controls won't work.

Check this code

 Object.keys(formGroup.controls).forEach(key => {
      formGroup.controls[key].setErrors(null);
    });

Imagine that you hit the items key here

formGroup.controls['item'] // this is a FormArray and 
// not FormControl so setErrors(null) won't work here

One way to fix this is to check for the instance of FormArray then iterate on the controls field and you can use the clearValidators and updateValueAndValidty functions.

   if (formGroup.controls[key] instanceof FormArray) {
         const control = formGroup.get(key) as FormArray;
        for (let i = 0; i < control.controls.length; i++) {
          const formGroup = control.controls[i] as FormGroup;
          Object.keys(formGroup.controls).forEach(field => {
            const control = formGroup.get(field);
            control.clearValidators();
            control.updateValueAndValidity();
          });
        }
      }

Here's a stackblitz demo: https://stackblitz.com/edit/angular-f7pflm?file=src%2Fapp%2Fapp.component.ts

Here's how your clearErrorsFromFormGroup woud look like now

private clearErrorsFromFormGroup(formGroup: FormGroup): void {
    Object.keys(formGroup.controls).forEach(key => {
      formGroup.controls[key].setErrors(null);
       if (formGroup.controls[key] instanceof FormArray) {
         const control = formGroup.get(key) as FormArray;
        for (let i = 0; i < control.controls.length; i++) {
          const formGroup = control.controls[i] as FormGroup;
          console.log('control', control);
          Object.keys(formGroup.controls).forEach(field => {
            const control = formGroup.get(field);
            control.clearValidators();
            control.updateValueAndValidity();
          });
        }
      }

    });
  }

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

Comments

0

Try using formGroup.updateValueAndValidity() method after reset

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.