【问题标题】:How to add dynamic custom validations in angular2 (ReactiveForms)?如何在 angular2 (ReactiveForms) 中添加动态自定义验证?
【发布时间】:2017-08-13 14:49:49
【问题描述】:

我有一个要求,我想实现逻辑以动态地将对象数组数据分配给输入控件,并且基于更新我想更新我的数组以及我想触发验证以检查控件中输入的名称/数据是否有重复条目。 为了验证,我使用了 ReactiveForm 模块。但我面临以下 2 个问题 –

  1. 我如何创建相同的数组结构以便成功 验证我可以直接将更新后的结构传递给api吗?
  2. 我如何将数组对象中的 id 分配给 formControlName,目前我用循环索引分配它。
    plunkar 参考这里 - https://plnkr.co/edit/RSBpT0sFSI1GDCp6K7VR?p=preview

组件:

@Component({
  selector: 'my-app',
  template: `
    <div>
      <h3> Custom Group Validation</h3>
      <form [formGroup]="myForm">
          <div class="left">
              names: <br>
              <div formArrayName="names">
                  <div *ngFor="let item of namesArray.controls; let i = index">
                      <input type="text" [formControlName]="i">
                      <button (click)="removeAt(i)">X</button><br>
                  </div>
              </div>

              <div *ngIf="namesArray.hasError('duplicate')">
                  duplicate entries
              </div>
              <pre>Array value: <br>{{namesArray.value | json}}</pre>
          </div>
      </form>
</div>
  `
})

类(摘要):

namesArray:FormArray =  new FormArray([], this.customGroupValidation  );
    dataArray: { custId: number, customerName: string }[] = [
{ custId: 101, customerName: 'John' },
{ custId: 102, customerName: 'Mike' },
{ custId: 103, customerName: 'Julia' }];

    ngOnInit():void{
      for(let ele of this.dataArray){
          this.namesArray.push(
            new FormControl(ele.customerName)
        );
      }
    }

感谢任何帮助!

【问题讨论】:

    标签: angular angular2-forms reactive-forms


    【解决方案1】:

    处理这两个问题的一种方法是订阅 FormGroup 的 .valueChanges 事件并放入 check in 方法来验证 FormControl 值是否存在重复条件。

    在 ngOnInit() 中创建 FormControl 并将其添加到 FormGroup 时也分配 custId 属性

    代码片段 -

    import { Component, NgModule, OnInit } from '@angular/core'
    import { BrowserModule } from '@angular/platform-browser'
    import { FormBuilder, FormGroup, FormArray, AbstractControl, Validators, FormControl, ReactiveFormsModule } from '@angular/forms'
    
    @Component({
      selector: 'my-app',
      template: `
        <div>
          <h3> Custom Group Validation</h3>
          <form [formGroup]="customerFormGroup">
              <div class="left">
                  names: <br>
                  <div>
                      <div *ngFor="let item of dataArray">
                          <input type="text" [formControlName]="item.custId" [(ngModel)]="item.customerName">
                          <div *ngIf="customerFormGroup.controls[item.custId] && customerFormGroup.controls[item.custId].errors">
                            duplicate                       
                          </div>
                      </div>
                  </div>
                  <pre>Array value: <br>{{dataArray | json}}</pre>
              </div>
          </form>
    </div>
      `
    })
    export class App implements OnInit {
      customerFormGroup: FormGroup = new FormGroup({});
      dataArray: { custId: number, customerName: string }[] = [
        { custId: 101, customerName: 'John' },
        { custId: 102, customerName: 'Mike' },
        { custId: 103, customerName: 'Julia' }];
    
      ngOnInit(): void {
    
        for (let ele of this.dataArray) {
          let control: FromControl = new FormControl(ele.customerName);
          this.customerFormGroup.addControl(ele.custId, control);
        }
    
        this.customerFormGroup.valueChanges.subscribe(
          data => this.onValueChanged(data)
        );
      }
    
      onValueChanged(data?: any) {
        if (!this.customerFormGroup) return;
        let formGroup = this.customerFormGroup;
        var result = _.groupBy(formGroup.controls, c => {
          if (c.value) return c.value.toLowerCase();
          else c.value;
        });
        for (let prop in result) {
          if (result[prop].length > 1) {
            _.forEach(result[prop], function (item: any) {
              if (item.dirty && item.value) {
                item.setErrors({
                  'duplicate': true
                });
              }
            })
          }
        }
      }
    }
    
    @NgModule({
      imports: [BrowserModule, ReactiveFormsModule],
      declarations: [App],
      bootstrap: [App]
    })
    export class AppModule { }
    

    【讨论】:

      猜你喜欢
      • 2012-09-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-10-03
      • 1970-01-01
      • 2018-12-20
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多