iT邦幫忙

2022 iThome 鐵人賽

DAY 15
0
Modern Web

angular專案開發指南系列 第 15

Angular 表單驗證

  • 分享至 

  • xImage
  •  

前言

驗證使用者輸入的準確性和完整性,可提高資料品質。該頁面顯示瞭如何從 UI 驗證使用者輸入,Angular 提供 範本驅動表單中驗證響應式表單中驗證 一般來說,結構簡單的表單我會使用 範本驅動表單中驗證 方式,複雜的大型表單我會使用 響應式表單中驗證
以下示範如何在 範本驅動表單響應式表單 中進行驗證並顯示有用的驗證訊息。


實作範本驅動表單

First Name 加入驗證 src\app\tenant\tenant.component.html

<div>
    <label>First Name   </label>

    <!-- 檢查 minlength="3" 與 required -->
    <input type="text" nbInput [(ngModel)]="addTenant.fname" #fname="ngModel" minlength="3" required />
</div>
<div *ngIf="fname.invalid && (fname.dirty || fname.touched)" class="alert">
    <span *ngIf="fname.errors?.['required']">此欄位必填</span>
    <span *ngIf="fname.errors?.['minlength']">至少輸入 3 個字</span>
</div>

驗證項目

  1. 此欄位必填
  2. 至少輸入 3 個字

美化驗證樣式 src\app\tenant\tenant.component.scss

nb-card-body {
    div {
        ...

        // 驗證欄位
        &.alert {
            margin: 0;
            color: red;
        }
    }

    // 錯誤訊息
    span {
        display: inline-block;
        width: 100%;
        text-align: center;
    }
}

範本驅動表單驗證結果

g8

範例解釋

  1. #fname="ngModel" NgModel 匯出一個名叫 fname 的區域性變數。NgModel 把自己控制的 FormControl 實例的屬性映射出去,讓你能在範本中檢查控制元件的狀態。

  2. *ngIf="fname.invalid && (fname.dirty || fname.touched)" 檢查控制元件的 dirty 狀態或 touched 狀態,避免一開始還沒操作的情況下就被驗證為錯誤輸入。

    • 當用戶在被監視的欄位中修改該值時,控制元件就會被標記為 dirty
    • 當用戶的表單控制元件失去焦點時,該控制元件就會被標記為 touched

打開 console 檢視元素會發現 Angular 有幫你加入 ng-dirty ng-invalid ng-touched 的樣式名。

<input type="text" nbinput="" minlength="3" required="" class="size-medium status-basic shape-rectangle nb-transition ng-dirty ng-invalid ng-touched">

響應式表單

要使用響應式表單需要載入 ReactiveFormsModule 模組

src\app\app.module.ts

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

imports: [
    FormsModule,
    ReactiveFormsModule,
    ...
]

加入 formGroupsrc\app\tenant\tenant.component.html

<form [formGroup]="helloForm">
    ...
    <div>
        <label>Last Name   </label>
        <input type="text" nbInput class="form-control" formControlName="lname" required />
    </div>
    <div *ngIf="lname.invalid && (lname.dirty || lname.touched)" class="alert">
        <span *ngIf="lname.errors?.['required']">此欄位必填</span>
        <span *ngIf="lname.errors?.['minlength']">至少輸入 3 個字</span>
    </div>
    ...
</form>

載入模組 src\app\tenant\tenant.component.ts

import { FormControl, FormGroup, Validators, FormBuilder } from '@angular/forms';

...

helloForm: any;

editItem(dialog: TemplateRef<any>, idx: number) {
    // 被選擇項目資料寫入對話框
    this.addTenant.fname = targetObj.first_name;
    this.addTenant.lname = targetObj.last_name;
    this.addTenant.phone = targetObj.phone;
    this.addTenant.address = targetObj.address;

    ...
}

get lname() {
    return this.helloForm.get('lname');
}

async ngOnInit(): Promise<void> {
    ...

    this.helloForm = new FormGroup({
        lname: new FormControl(
            this.addTenant.lname,
            [Validators.required,Validators.minLength(3)
        ]),
    });
}

這些驗證器都是同步的,所以它們作為第二個引數傳遞。注意,你可以透過把這些函式放到一個數組中傳入來支援多個驗證器。

響應式表單驗證結果

g9


結論

編輯租戶表單原本就使用了雙向綁定特性,因此比較適用 範本驅動表單中驗證 的方式,但是為求完整展示範例,在 First name 是使用 範本驅動表單 中驗證,而在 Last name 是使用 響應式表單驗證

租戶管理元件功能都做好了,下一篇回到 Angular 基本概念整理跟大家分享一下生命週期鉤子。


參考

Validating form input


上一篇
實作租戶管理頁面(2)
下一篇
Angular 元件的生命週期
系列文
angular專案開發指南30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言