0

I have a reactive from, with two select dropdowns. Depending on the value selected in the first, the second may or may not be required.

This is the code that fires when the value changes on the first one. It basically searches an array to see if their are matching types and if there are it assigns them to the second dropdown, adds the required validator. If not, the control is disabled and the validator is removed.

However, the field remains required in the else part and the whole form is marked invalid. So what is missing?

  getCategoryTypes(value: string) {
    let types = this.categories.find(v => v.name === value);
    if (types) {
      this.categoryTypes = types.category_types;
      this.category_type.setValue("");
      this.category_type.setValidators([Validators.required]);
      this.category_type.updateValueAndValidity();
    }
    else {
      this.categoryTypes = [];
      this.category_type.setValidators(null);
      this.category_type.updateValueAndValidity();
    };
  }

Fyi:

category_type: FormControl;

UPDATE

In the Docs I discovered this:

"These statuses are mutually exclusive, so a control cannot be both valid AND invalid or invalid AND disabled."

and

"Disabled controls are exempt from validation checks and are not included in the aggregate value of their ancestor controls."

So disabling the control should automatically remove the validation and thus mark the control as being valid.

7
  • Not really enough information to reproduce the issue. Code here looks fine to me. Perhaps create a plunker that showcases the issue? Commented Aug 9, 2017 at 18:46
  • Is it definitely executing the appropriate branch of this logic? Commented Aug 9, 2017 at 19:02
  • Have you tried this: this.category_type.clearValidators(); Commented Aug 9, 2017 at 19:04
  • I believe it's because you set the validators first, and then the getCategoryTypes() is not ran again maybe? Not enough code, But I faced something similar with checkboxes. Essentially, you have to remove the validators when a value changes or fails to meet the requirement as DeborahK mentioned with this.control.clearValidators(); Commented Aug 9, 2017 at 19:14
  • @DeborahK Yes it is definitely executing the else branch, I tested that with logging to console. I also tried clearValidators(). Commented Aug 10, 2017 at 10:32

1 Answer 1

0

The if (types) check was not working but I also discovered it is not necessary to remove and re-add the validations, I can just disable and re-enable the control. So the solution is:

  getCategoryTypes(value: string) {
    let types = this.categories.find(v => v.name === value).category_types;
    if (types.length > 0) {
      this.categoryTypes = types;
      this.category_type.setValue("");
      this.category_type.enable();
      this.category_type.updateValueAndValidity();
    }
    else {
      this.categoryTypes = [];
      this.category_type.disable();
      this.category_type.updateValueAndValidity();
    };
  }
Sign up to request clarification or add additional context in comments.

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.