【问题标题】:Angular 2+ Custom form validation breaks the form methodsAngular 2+ 自定义表单验证打破了表单方法
【发布时间】:2021-07-06 23:12:58
【问题描述】:

我有一个表格:

public buildUserForm(user: User = null): void {
    this.selectedUserForm = this.fb.group({
      id: 0,
      isActive: [true],
      isSuperUser: [null],
      firstName: ['', Validators.required],
      lastName: ['', Validators.required],
      username: ['', [Validators.required, UniqueNameValidator(this.userNamesList, user)]],
      password: ['',
        Validators.pattern('^(?=[^A-Z]*[A-Z])(?=[^a-z]*[a-z])(?=\\D*\\d)[A-Za-z\\d!$%@#£€*?&]{8,}$')],
      emailAddress: ['', Validators.email],
      businessEmailAddress: ['', Validators.email],
      address1: ['', Validators.maxLength(50)],
      address2: ['', Validators.maxLength(50)],
      city: ['', Validators.maxLength(30)],
      stateProvince: ['', Validators.maxLength(30)],
      postalCode: ['', Validators.maxLength(10)],
      phoneNumber1: ['', Validators.maxLength(10)],
      employeeId: [''],
      notes: ['']
    });
    this.onFormChanges();
  }

还有一个自定义表单验证器:

import { Directive } from '@angular/core';
import { AbstractControl, ValidationErrors, ValidatorFn } from '@angular/forms';

Directive({
  selector: '[uniqueName]'
});

export function UniqueNameValidator(array: any[], exception = null): ValidatorFn {
  const valObject = { nameDuplicate: true }
  return (control: AbstractControl): ValidationErrors | null => {
    if (exception) {
      if (control.value === exception.name || control.value === exception.username) {
        return array.findIndex(item => item.name === control.value || item.username === control.value) > 0 ? valObject : null;
      } else {
        return array.findIndex(item => item.name === control.value || item.username === control.value) > 0 ? valObject : null;
      }
    } else {
      return array.findIndex(item => item.name === control.value || item.username === control.value) > 0 ? valObject : null;
    }
  };
}

验证器工作并给我正确的消息。但是诸如 this.selectedUserForm.touched 或 this.selectedUserForm.valid 之类的方法不再起作用,并且现在总是显示 False。 如何在不丢失自定义表单验证的情况下恢复表单。

【问题讨论】:

    标签: angular typescript angular-forms angular-formbuilder angular2-form-validation


    【解决方案1】:

    如果不是唯一的,您的验证器函数需要返回错误。

    uniqueValidation(list: string[]): ValidatorFn {
        return (c: AbstractControl): { [key: string]: boolean } | null => {  
          if (c.value === null || c.pristine || c.value === '') {
            return null;
          } else if (c.dirty) {
            return (list.find(x => x === c.value)) ? { 'notunique': true } : null;
          }
          return null;
        }
      }
    

    用法:

    selectedUserForm: FormGroup;
      userNamesList: string[] = ['name1', 'name2']
    
      constructor(private fb: FormBuilder) {}
    
      ngOnInit() {
        this.buildForm();
      }
    
      uniqueValidation(list: string[]): ValidatorFn {
        return (c: AbstractControl): { [key: string]: boolean } | null => {  
          if (c.value === null || c.pristine || c.value === '') {
            return null;
          } else if (c.dirty) {
            return (list.find(x => x === c.value)) ? { 'notunique': true } : null;
          }
          return null;
        }
      }
    
      buildForm() {
        this.selectedUserForm = this.fb.group({
          userName: [null, [Validators.required, this.uniqueValidation(this.userNamesList)]]
        });
      }
    

    演示:https://stackblitz.com/edit/angular-unique-validator-akeje2?file=src%2Fapp%2Fapp.component.ts

    在此演示中,键入“name1”或“name2”,验证将失败,并显示一条消息,表明它不是唯一的。

    【讨论】:

    • 感谢您的示例。它有助于我的解决方案。我仍然必须添加: ngDoCheck(): void { this.selectedUserForm.updateValueAndValidity();否则当我对字段进行更改时它不会注册。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-08-28
    • 2011-03-08
    • 1970-01-01
    • 2012-12-05
    • 2016-12-17
    • 2017-03-26
    • 2020-01-13
    相关资源
    最近更新 更多