7

I have a reactive form

 <form [formGroup]="secondFormGroup">
      <ng-template matStepLabel>enter items</ng-template>
      <div style="display: flex; flex-direction: column;">
        <mat-form-field>
          <input matInput type="text" placeholder="category"  [(ngModel)]="newItem.CategoryName" formControlName="category"
          />
        </mat-form-field>
        <mat-form-field>
          <input matInput type="text" placeholder="sub category"  [(ngModel)]="newItem.SubCategoryName" formControlName="subCategory"
          />
        </mat-form-field>
        <mat-form-field>
          <input matInput type="text" placeholder="product"  [(ngModel)]="newItem.ProductName" formControlName="name"/>
        </mat-form-field>
        <mat-form-field>
          <input matInput  [(ngModel)]="newItem.Amount" type="number" min="0" placeholder="amount" formControlName="amount"
          />
        </mat-form-field>
        <mat-form-field>
          <input matInput  [(ngModel)]="newItem.Price" type="number" min="0" placeholder="price" formControlName="price"
          />
        </mat-form-field>
        <button mat-raised-button color="primary" (click)="AddNewProduct(newItem)" style="float: left; align-self: flex-end;">submit</button>
      </div>
    </form>

I initialize it like this:

 this.secondFormGroup = this._formBuilder.group({
  category: ['', Validators.required],
  subCategory: ['', Validators.required],
  name: ['', Validators.required],
  amount: ['', Validators.required],
  price: ['', Validators.required]
});

Upon clicking sumbit I call this method:

AddNewProduct(newProduct) {
if (this.secondFormGroup.valid) {
  //add product
  this.secondFormGroup.reset();
 } 
}

After adding the product, I clear the form. However, once the form is cleared, it triggers the validation errors. I want the validation errors to show only when the user clicks submit and the form isn't valid, not when I clear the form after submitting.

How can I fix this?

4 Answers 4

26

The issue seems to be that the form is marked as submitted after reset is called. If the form is marked as submitted, regardless of whether or not its pristine, the errors will be highlighted.

You'll need to call resetForm instead, which is on the FormGroupDirective:

@ViewChild(FormGroupDirective) formGroupDirective: FormGroupDirective;

this.formGroupDirective.resetForm();

Secondly, you'll need to wrap it in a setTimeout with a timeout of 0, so that the form is submitted before it resets.

setTimeout(() => this.formGroupDirective.resetForm(), 0)

I've tested this in a StackBlitz, and it all seems to work:

https://stackblitz.com/edit/angular-l6xq1d?file=src%2Fapp%2Fapp.component.ts

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

8 Comments

Thanks. Although in my code, the form doesn't clear after calling resetForm. Why is this?
Hard to say without seeing it. Do you get any errors in the console?
Found the bug. I have another form. When I remove it, it works
How do I access only the formGroupDirective of the second form?
Give it an identifier, such as #myForm="ngForm", and then access it with @ViewChild('myForm') formGroupDirective: FormGroupDirective; instead
|
3

This works, try this you need to reset the formDirective otherwise it will not 100% resting the form

Template:

<form 
  ...
  #formDirective="ngForm" 
>

Component:

import { ViewChild, ... } from '@angular/core';
import { NgForm, ... } from '@angular/forms';

export class MyComponent {
 ...
 @ViewChild('formDirective') private formDirective: NgForm;

  constructor(... )

  private someFunction(): void { 
    ...
    formDirective.resetForm();
  }
}

Comments

0

You can easily clear the validators of form using clearValidators()

this.secondFormGroup .clearValidators();
this.secondFormGroup .updateValueAndValidity();

But this will remove the validators from the actual form group, and it will not show errors on form submit from the next time.

Better way to do is :

You could simply use flag on the error template, to display the errors based on form submit/reset. And set/reset the flag accordingly.

public formSubmitted = false;

onSubmit(){
   this.formSubmitted = true;
}

reset(){
   this.formSubmitted = false;
}

template file

<div *ngIf="formSubmitted">
 display errors
</div>

2 Comments

Thanks, but I don't want to just show or hide an element for the error. I want to mark the fields red like the default style does.
I have added more description onto what will happen, if you clear the validators. Please check that.
0

If you are using Angular Material inputs, then you can hide error state by setting inputs as untouched. Material input fields shows error status only if input is touched.

So

this.secondFormGroup.markAsUntouched();

should do the trick.

You may have to initiate change detection run after such operation (depends on scenario)

Here you have proof of concept. Input is initially in error state. Dedicated button clears this state untill future input.

https://stackblitz.com/edit/angular-tadkmb?file=src%2Fapp%2Fapp.component.ts

9 Comments

Actually, calling reset marks them as pristine anyway
@user184994 good to know, thanks for feedback. But wait, OP is stating that he resets form..
@amitairos ofc it work, its just you that dont know how to use it. Stating "not work" means nothing to me as there may be 10000 reasons why it is not working in your case. I can only guess that you need to run change detection like I have stated in last sentence.
@Antoniossss Tried using change detection, and it still shows the errors.
Please create stackblitz for us, it will be much more simpler
|

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.