Fork me on GitHub

angular:响应式表单(Reactive Forms)和模板驱动表单(Template-Driven Forms)分别进行验证

2022-01-18

响应式表单

响应式表单是围绕Observable的流构建的。

使用响应式表单时,FormControl类是最基本的构造类。

在使用响应式表单前,需要先导入 ReactiveFormsModule 并添加到 NgModule里。

html:

<!-- 响应式表单 -->
            <form [formGroup]="reactiveForm">
                <p>
                    <mat-form-field>
                        <mat-label>Name</mat-label>
                        <input matInput placeholder="Name" formControlName="name" [matTooltip]="name.errors?.['msg']">
                    </mat-form-field>
                </p>
                <button mat-stroked-button color="primary" [disabled]="reactiveForm.valid"
                    (click)="onSubmit()">Primary</button>
            </form>

 

 ts:

import { Component, OnInit } from '@angular/core';
//  响应式表单
import { FormGroup, FormControl, FormBuilder, Validators } from '@angular/forms';
import { nameValidator } from './form.directive';

@Component({
  selector: 'app-form',
  templateUrl: './form.component.html',
  styleUrls: ['./form.component.less']
})
export class FormComponent implements OnInit {
  reactiveForm!: FormGroup;
  constructor(
    private fb: FormBuilder
  ) { }
  ngOnInit(): void {
    // 响应式表单
    this.reactiveForm = this.fb.group({
      name: ['', [Validators.required, nameValidator()]]
    });
  }

  get name() { return this.reactiveForm.get('name'); }

  onSubmit() {
    console.log(this.reactiveForm);
    console.log(this.reactiveForm.value);
  }
}

 

directive.ts

import { AbstractControl, ValidationErrors, ValidatorFn } from "@angular/forms";

export function nameValidator(): ValidatorFn {
    return (control: AbstractControl): ValidationErrors | null => {
        // 验证由数字、英文字母或者下划线组成的字符串:^\w+$ 
        let nameRe = /^\w+$/;
        const isTrue = nameRe.test(control.value);
        return !isTrue ? { msg: "仅支持数字、英文字母或者下划线" } : null;
    };
}

 

 

模板驱动表单

使用表单指令和技术来进行构建表单。

使用ngModel创建双向数据的绑定,进行读取和写入控件值。

在表单输入控件上添加name属性,用途是有效性验证和追踪表单元素的变更。

可以在form中可以使用ngForm声明一个模板变量,例如#heroForm="ngForm"。NgForm可以用来控制带有NgModel指令和name属性的元素。

在使用模板驱动表单钱,需要先导入FormsModule

 

响应式表单和模板驱动表单的不同点:    

响应式表单使用 Observable 流进行数据追踪;

模板驱动表单依赖嵌入模板中的指令并借助数据进行异步追踪;

使用模板绑定语法,把该表单控件注册给了模板中名为name的输入元素。

 

html:

 

 <!-- 模板表单 -->
            <form #ReactiveForm="ngForm">
                <mat-form-field appearance="fill">
                    <mat-label>Name</mat-label>
                    <input matInput placeholder="Name" name="name" ngModel #name="ngModel" nameValidator
                        appForbiddenName="admin" [matTooltip]="name.errors?.['msg']">
                </mat-form-field>
            </form>

 

 

directive.ts

// 自定义指令
@Directive({
    selector: '[nameValidator]',
    providers: [{
        provide: NG_VALIDATORS, // 带有可扩展验证器集合的预定义提供者
        useExisting: nameValidatorDirective,
        multi: true //想让一个控件同时支持多个验证器
    }]
})
export class nameValidatorDirective implements Validator {
    @Input('appForbiddenName') forbiddenName = '';
    validate(control: AbstractControl): ValidationErrors | null {
        let nameRe = /^\w+$/;
        const isTrue = nameRe.test(control.value);
        console.log(isTrue);
        console.log(this.forbiddenName);
        // console.log(control);
        return !isTrue ? { msg: "仅支持数字、英文字母或者下划线" } : null;
    }
}

 

module.ts

import { NgModule } from '@angular/core';

import { CommonModuleModule } from "../common-module/common-module.module";
import { FormRoutingModule } from './form-routing.module';

import { FormsModule, ReactiveFormsModule } from '@angular/forms';

import { FormComponent } from './form.component';

import { nameValidatorDirective } from './form.directive'


@NgModule({
    imports: [
        CommonModuleModule,
        FormRoutingModule,
        ReactiveFormsModule,
        FormsModule
    ],
    declarations: [
        FormComponent,
        nameValidatorDirective
    ],
    entryComponents: [

    ],

    providers: [

    ]
})
export class FormModule { }

 

posted @ 2022-01-18 14:00  元芳啊  阅读(393)  评论(0编辑  收藏  举报