2

I have a reactive form as following:

this.form = this.formBuilder.group({
  name: ['', Validators.required],
  email: ['', this.customValidator()]
});

I also have a "submit" button with a [disabled] condition:

<button [disabled]="form.invalid" (click)="create()">Create</button>

If email input is untouched and I modify name input, customValidator is not fired and Create button enables despite the customValidator() would return an error.

On the other hand, the name control has a Validators.required validation that is fired even if the input is untouched, which is the desired behaviour.

Example on stackblitz: I want the email input to be required (and the create button to be disabled) when name has value on it even if email is untouched.

7
  • It should work as it is. Post an MRE or a demo for us to be able to debug. Here is something to begin with: stackblitz.com/edit/… Commented May 25, 2022 at 9:00
  • 1
    Can you add some stackblitz to this, since Vega is right, this should work Commented May 25, 2022 at 9:02
  • Can you share the code of your custom validator? Commented May 25, 2022 at 9:02
  • MRE is minimal reproducible example , FYI Commented May 25, 2022 at 9:05
  • @Bozhinovski stackblitz added Commented May 25, 2022 at 9:42

4 Answers 4

1

Please check this solution. Instead of abstratcontrol I've used FormControl which is much easier to handle. Also you can pass the parent-child param to the custom validator as seen on this example:

 ngOnInit() {
    this.form = this.formBuilder.group({
      name: ['', Validators.required],
      email: ['', this.customVal('name')], -> you can pass the value here
    });
  }

Please check the stackblitz for complete solution.

https://stackblitz.com/edit/angular-custom-validator-uhhicz?file=src/app/app.component.ts

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

3 Comments

Still enabling Create button when only filling name input
@Iñigo its fixed now. Please check it out
what was the solution? its still not working as you can see here: stackblitz.com/edit/… if you try to save the form its valid even if the fields are not the same (I've changed the validator)
1

Found a couple ways for solving the problem:

1 Angular cross-validation.

The custom validator is applied to the FormGroup and not to the FormControl. The validation is executed every time the form is modified.

this.form = this.formBuilder.group({
  name: ['', Validators.required],
  email: ['']
}, { validators: this.customValidator});

2 Subscribe to form valueChanges + updateValueAndValidity.

this.form = this.formBuilder.group({
  name: ['', Validators.required],
  email: ['', this.customValidator()]
});

And on ngOnInit, whenever the form changes, the validation is executed:

this.form.valueChanges.subscribe(x => {
    this.form.get('email').updateValueAndValidity();
})

1 Comment

That is indeed the case, cross-validation solves the behavior problem, but that should not mark email input in red if you just click on it and then focus out. From user's perspective that only work if email is never required. It does not make much sense to disable button if email input is empty but not mark it as invalid, how are u supposed to understand that button is disabled because you have not introduced email?
0

Can you try this :

  ngOnInit() {
    this.form = this.formBuilder.group({
      name: ['', Validators.required],
      email: ['', [Validators.required, this.customVal()]],
    });
  }

1 Comment

I don't want it to be required always, the custom validator logic is just an example to demonstrate that the validation is only fired when touched.
0

As Iñigo say, a FormControl only is "validate" if is modify the input or if you call manually to "updateValueAndValidity".

So another way is subscribe to form.get('name').valueChange (not forget unsubscribe)

this.form.get('name').valueChange.subscribe(_=>{
  this.form.get('email').updateValueAndValidity()
})

Or we can use input event in .html

<input formControlName="name" class="form-control" placeholder="Name" 
      (input)="form.get('email').updateValueAndValidity()" />

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.