1

Is there anyway to do 'Either Or, one or the other validation in Angular Reactive Forms?

Currently, want form to be valid, (a) if City and State is inputted Or (b) Zip Code is inputted, either group, and form is valid. If both groups are empty, then form is invalid.

This is the base start form, currently both city and zip are optional, trying to incorporate this correct logic.

public editAddressForm: FormGroup;

this.editAddressForm = this.formBuilder.group({

      'name': [null, [Validators.maxLength(100)]],
      'phonenumber': [null, [Validators.maxLength(50)]],
      'city': [null, [Validators.maxLength(32)]],
      'state': [null,[Validators.maxLength(4)]],
      'zipcode': [null, [Validators.maxLength(16)]]
    })

Trying to use this resource, however it requires city and zip to be nested, which is not what is required.

Angular, How to set validation for either of two field should validate in reaction form approach

  • 1
    Does this answer your question? [Angular 2 custom validator to check when either one of the two fields is required](https://stackoverflow.com/questions/47661680/angular-2-custom-validator-to-check-when-either-one-of-the-two-fields-is-require) – Matt U Dec 05 '19 at 22:35

2 Answers2

3

You can write a custom validator for the form that has access to all the fields in the form. It can then check the value for either of those two fields and return true/false as needed.

The Angular docs call this cross field validation. You can read about it in the docs here.

pjlamb12
  • 2,300
  • 2
  • 32
  • 64
0

First create function, then apply this validator to the form.

export function atLeastOneLocationRequired(group : FormGroup) : {[s:string ]: boolean} {
  var cityCtrl = group.controls.city;
  var stateCtrl = group.controls.state;
  var postalCodeCtrl = group.controls.postalCode;

  if (cityCtrl != undefined && stateCtrl != undefined && postalCodeCtrl != undefined)
    if (!(((cityCtrl.value && cityCtrl.value.length) && (stateCtrl.value && stateCtrl.value.length)) || (postalCodeCtrl.value && postalCodeCtrl.value.length)))
      return { invalid: true };
}

this.editAddressForm = this.formBuilder.group({
      'name': [null, [Validators.maxLength(100)]],
      'phonenumber': [null, [Validators.maxLength(50)]],
      'city': [null, [Validators.maxLength(32)]],
      'state': [null,[Validators.maxLength(4)]],
      'zipcode': [null, [Validators.maxLength(16)]]
    }, { validator: atLeastOneLocationRequired })