Angular 2:在valueChanges之后更新FormControl验证器

Angular 2: Update FormControl validator after valueChanges

本文关键字:更新 FormControl 验证 之后 valueChanges Angular      更新时间:2023-09-26

是否有办法更新一个FormControl对象的Validtors ?我有FormGroup,其中一个输入是一个选择字段,当选择字段的值发生变化时,我希望我的FormGroup中的另一个FormControl改变验证器。

这是我的subscribeToFormChanges()方法从我的FormGroup组件:
private appIdRegexes = {
    ios: /^[a-zA-Z][a-zA-Z0-9]*('.[a-zA-Z0-9'-]+){2,}$/,
    android: /^([a-zA-Z])[a-zA-Z0-9_]*('.[a-zA-Z][a-zA-Z0-9'-]*){2,}$/,
    any: /^any$/
  };
private subscribeToFormChanges(): void {
    const myFormValueChanges$ = this.appsForm.valueChanges;
    myFormValueChanges$.subscribe(x => {
      const platform = this.appsForm.controls['platform'].value;
      const appId = this.appsForm.controls['appId'].value;
      if (this.appIdRegexes[platform]) {
        this.appsForm.controls['appId'] = new FormControl(appId, Validators.pattern(this.appIdRegexes[platform].source));
      }
    });
  }

这是html模板:

<div class="row" [formGroup]="appsForm">
  <div class="form-group col-xs-6">
    <label>Platform</label>
    <select id="licensePlatform" class="form-control"
            formControlName="platform">
      <option *ngFor="let platform of licensePlatforms" [value]="platform">
        {{platform}}
      </option>
    </select>
    <small [hidden]="appsForm.controls.platform.valid">
      Platform is required
    </small>
  </div>
  <div class="form-goup col-xs-6">
    <label>App ID</label>
    <input type="text" class="form-control" formControlName="appId">
    <small [hidden]="appsForm.controls.appId.valid">
      Please use the right ID format
    </small>
  </div>
</div>

当我像这里所示的那样实现subscribeToFormChanges()方法时,appsForm.controls.appId.value在写入输入字段时不再更新。初始值正在更新

我通过在我的平台选择字段上收听valueChanges来解决这个问题,然后我在appId输入字段上使用setValidators()方法。这篇文章很有用。

这是我的解决方案:

 private subscribePlatformChanges() {
    const platformCtrl = this.appsForm.controls['platform'];
    const changes$ = platformCtrl.valueChanges;
    changes$.subscribe(platform => {
      this.appsForm.controls['appId'].setValidators([Validators.pattern(this.appIdRegexes[platform].source),
                                                    Validators.required]);
      this.appsForm.controls['appId'].updateValueAndValidity();
    });
  }

要重新检查FormGroup中的控件,您可以使用FormControl updateValueAndValidity 做一些事情。

如果this.appsForm确实是FormGroup:

this.appsForm.controls.forEach(control => control.updateValueAndValidity());

您可以从select中触发一个更改事件,如下所示

<select id="licensePlatform" class="form-control"
            formControlName="platform"  (change)="update($event.target.value)" >
      <option selected="selected" disabled="disabled" value="">Select Card Type</option>
      <option *ngFor="let platform of licensePlatforms" [value]="platform" >
        {{platform}}
      </option>
    </select>

在组件中,您可以编写如下的更新函数

update(value){
      if(value){
        (<FormControl>this.appsForm.controls['platform']).setValue(value, {onlySelf: false});
        const appId = this.appsForm.controls['appId'].value;
        if (this.appIdRegexes[value]) {
        this.appsForm.controls['appId'] = new FormControl(appId, Validators.pattern(this.appIdRegexes[value].source));
      }
    };
  }

这将根据您在下拉菜单中所做的选择更新验证器。我相信这会解决你的问题。