Angular 表單2 響應式表單, 處理異步數據

上一節中咱們定義了一個響應式表單,其中表單數據是在定義的時候就初始化好的,可是不少時候數據須要異步獲取,好比打開一個編輯頁面,須要:css

  1. 請求HTTP拿到數據。
  2. 根據數據修改表單中字段的值,最終體如今頁面上。 咱們改造上一節的例子,成爲異步獲取數據。 咱們先建立service文件, 寫一個loadUser方法,模擬HTTP請求
import { Injectable } from '@angular/core';
import { of } from 'rxjs';
import { delay } from 'rxjs/operators';

// /api/users/1

export interface User {
  id: number;
  firstName: string;
  lastName: string;
  about: string;
}

const fakeData = {
  id: 0,
  firstName: 'Cory',
  lastName: 'Rylan',
  about: 'Web Developer'
};

@Injectable()
export class UserService {
  constructor() { }

  loadUser() {
    return of<User>(fakeData).pipe(
      delay(2000)
    );
  }
}

複製代碼

組件中,調用該方法html

import { Component } from '@angular/core';
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
import { Observable } from 'rxjs';
import { tap } from 'rxjs/operators';

import { UserService, User } from './user.service';

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  form: FormGroup;
  user$: Observable<User>;

  constructor(
    private formBuilder: FormBuilder,
    private userService: UserService) { }

  ngOnInit() {
    this.form = this.formBuilder.group({
      firstName: ['', Validators.required],
      lastName: ['', Validators.required],
      about: []
    });

    this.user$ = this.userService.loadUser().pipe(
      // tap 返回的仍是 Observable 這裏咱們不訂閱,咱們在模板中使用 async pipe 和 if else 語句實現有條件的顯示錶單
      tap(user => this.form.patchValue(user))
    );
    // .subscribe();
  }

  submit() {
    if (this.form.valid) {
      console.log(this.form.value);
    }
  }
}

複製代碼

修改模板api

<form *ngIf="user$ | async; else loading" [formGroup]="form" (ngSubmit)="submit()">
  <label for="firstname">First Name</label>
  <input id="firstname" formControlName="firstName" />
  <div *ngIf="form.controls.firstName.errors?.required && form.controls.firstName.touched" class="error">
    *Required
  </div>

  <label for="lastname">Last Name</label>
  <input id="lastname" formControlName="lastName" />
  <div *ngIf="form.controls.lastName.errors?.required && form.controls.lastName.touched" class="error">
    *Required
  </div>

  <label for="about">About</label>
  <textarea id="about" formControlName="about"></textarea>

  <button [disabled]="!form.valid">Save Profile</button>
</form>

<ng-template #loading>
  Loading User...
</ng-template>
複製代碼

你會發現頁面打開後一開始顯示Loading User...過了大概2s後文字消失並顯示錶單。bash

相關文章
相關標籤/搜索