角材料:使用反应形式从服务中垫式选择设定值数据

时间:2020-07-12 10:52:43

标签: angular angular-material angular-reactive-forms

我已经在这个问题上苦苦挣扎了几天,希望有人可以帮助我解决这个问题。

我有一项从后端检索用户的服务。用户模型如下所示:

declare interface IUser {
  id?: string;
  name?: string;
  email?: string;
  firebaseID?: string;
  firebaseEmail?: string;
  role?: string;
  phoneNumber?: string;
}

并且我有一项从后端检索工作订单的服务。

在我的工作订单表格中,我想显示一个用户列表以及已经分配给该工作订单的用户列表(默认值)。 表单是响应式表单(create-work-order-dialog),我想在其中显示用户选择的工作订单或显示列表,以选择工作项目的其他用户。

我与用户formControl一起使用的表单是(Monteur):

<div #container>
  <form
    [formGroup]="form"
    (ngSubmit)="save()"
    data-test="createFollowUpDialog"
    autocomplete="off"
  >
    <h1 mat-dialog-title>Maak een nieuwe werkorder aan</h1>
    <mat-dialog-content>
      <div class="row mt-3">
        <div class="col-md-12">
          <h2>Werkorder informatie</h2>
          <mat-form-field class="input">
            <mat-label>Omschrijving van het probleem</mat-label>
            <input
              formControlName="leakageReason"
              tabindex="1"
              autocomplete="off"
              matInput
              placeholder="Omschrijving van probleem"
              matTooltip="Omschrijving van het probleem"
            />
            <mat-error
              *ngIf="form.controls['leakageReason'].hasError('required')"
              >Verplicht
            </mat-error>
          </mat-form-field>
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Projectnummer</mat-label>
            <input
              formControlName="projectNumber"
              tabindex="2"
              autocomplete="off"
              matInput
              placeholder="Projectnummer"
            />
            <mat-error
              *ngIf="form.controls['projectNumber'].hasError('required')"
              >Verplicht
            </mat-error>
          </mat-form-field>
        </div>
      </div>
      <div formGroupName="client">
        <h3>Gegevens van de opdrachtgever</h3>
        <div class="row mt-3">
          <div class="col-md-12">
            <mat-form-field class="input">
              <mat-label>Naam opdrachtgever</mat-label>
              <input
                formControlName="name"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Naam van de opdrachtgever"
                placeholder="Naam opdrachtgever"
              />
              <mat-error *ngIf="form.get('client.name')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
        </div>
        <div class="row mt-3">
          <div class="col-md-12">
            <mat-form-field class="input">
              <mat-label>Telnr. van opdrachtgever</mat-label>
              <input
                formControlName="phoneNumber"
                tabindex="2"
                autocomplete="off"
                matInput
                required
                matTooltip="Telnr. van de opdrachtgever"
                placeholder="Telnr. opdrachtgever"
              />
              <mat-error
                *ngIf="form.get('client.phoneNumber')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
        </div>
        <div class="row mt-3">
          <div class="col-md-12">
            <mat-form-field class="input">
              <mat-label>Mobielnr. van opdrachtgever</mat-label>
              <input
                formControlName="mobilePhoneNumber"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Mobielnr. van de opdrachtgever"
                placeholder="Mobielnr. opdrachtgever"
              />
            </mat-form-field>
          </div>
        </div>
      </div>
      <div formGroupName="customer">
        <h3>Gegevens van de klant</h3>
        <div class="row mt-3">
          <div class="col-md-12">
            <mat-form-field class="input">
              <mat-label>Naam Klant</mat-label>
              <input
                formControlName="name"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Naam van de klant"
                placeholder="Naam klant"
              />
              <mat-error *ngIf="form.get('customer.name')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
        </div>
        <div class="row mt-3">
          <div class="col-md-8">
            <mat-form-field class="input">
              <mat-label>Adres van klant</mat-label>
              <input
                formControlName="street"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Straat van de klant"
                placeholder="straat klant"
              />
              <mat-error
                *ngIf="form.get('customer.street')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
          <div class="col-md-2">
            <mat-form-field class="input addressWidth">
              <mat-label>Huisnr.</mat-label>
              <input
                formControlName="houseNumber"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Huisnummer"
                placeholder="Huisnr."
              />
              <mat-error
                *ngIf="form.get('customer.houseNumber')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
          <div class="col-md-2">
            <mat-form-field class="input addressWidth">
              <mat-label>toevoeging</mat-label>
              <input
                formControlName="houseNumberExt"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Huisnummer toevoeging"
                placeholder="toevoeging"
              />
            </mat-form-field>
          </div>
        </div>
        <div class="row mt-3">
          <div class="col-md-4">
            <mat-form-field class="input zipCodeWidth">
              <mat-label>Postcode</mat-label>
              <input
                formControlName="zipCode"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Postcode"
                placeholder="Postcode"
              />
              <mat-error
                *ngIf="form.get('customer.zipCode')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
          <div class="col-md-4">
            <mat-form-field class="input">
              <mat-label>Plaats</mat-label>
              <input
                formControlName="city"
                tabindex="2"
                autocomplete="off"
                matInput
                matTooltip="Plaats"
                placeholder="Plaats"
              />
              <mat-error *ngIf="form.get('customer.city')?.hasError('required')"
                >Verplicht
              </mat-error>
            </mat-form-field>
          </div>
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="datepicker">
            <mat-label>Inspectiedatum </mat-label>
            <input
              matInput
              formControlName="dateInspection"
              tabindex="3"
              [matDatepicker]="pickerIn"
            />
            <mat-datepicker-toggle
              tabindex="-1"
              matSuffix
              [for]="pickerIn"
            ></mat-datepicker-toggle>
            <mat-datepicker #pickerIn></mat-datepicker>
          </mat-form-field>
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Status werkorder</mat-label>
            <mat-select formControlName="status" name="status" tabindex="4">
              <mat-option
                *ngFor="let status of statusWerkOrder"
                [value]="status"
              >
                {{ status }}
              </mat-option>
            </mat-select></mat-form-field
          >
        </div>
      </div>
      <div formGroupName="user" class="mt-4 mb-3">
        <div class="row mt-3">
          <div class="col-md-12">
            <mat-form-field class="input">
              <mat-label>Monteur</mat-label>
              <mat-select
                formControlName="name"
                name="name"
                tabindex="5"
                [(value)]="data.user.name"
              >
                <mat-option
                  *ngFor="let mechanic of mechanics"
                  [value]="mechanic"
                >
                  {{ mechanic.name }}
                </mat-option>
              </mat-select>
            </mat-form-field>
          </div>
        </div>
      </div>
      <pre>{{ data.user.name }}</pre>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-slide-toggle
            color="primary"
            formControlName="followupInspection"
            tabindex="5"
            >Opvolgmelding?</mat-slide-toggle
          >
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-slide-toggle
            color="primary"
            formControlName="clientPresent"
            tabindex="6"
            >Is de klant aanwezig?</mat-slide-toggle
          >
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-slide-toggle
            color="primary"
            formControlName="visibleWaterDamage"
            tabindex="7"
            >Zichtbare waterschade?</mat-slide-toggle
          >
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Duur waterschade</mat-label>
            <input
              formControlName="visibleWaterDamagePeriod"
              tabindex="8"
              autocomplete="off"
              matInput
              matTooltip="Duur waterschade (dag, week, etc.)"
              placeholder="Duur waterschade"
            />
          </mat-form-field>
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Soort gebouw</mat-label>
            <mat-select
              formControlName="buildingType"
              name="buildingType"
              tabindex="9"
            >
              <mat-option
                *ngFor="let buildingType of buildingTypes"
                [value]="buildingType"
              >
                {{ buildingType }}
              </mat-option>
            </mat-select></mat-form-field
          >
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Bouwjaar</mat-label>
            <input
              formControlName="buildingEstablished"
              tabindex="10"
              autocomplete="off"
              matInput
              placeholder="Bouwjaar"
              matTooltip="Bouwjaar van het object"
            />
          </mat-form-field>
        </div>
      </div>
      <div class="row mt-3">
        <div class="col-md-12">
          <mat-form-field class="input">
            <mat-label>Renovatie jaar</mat-label>
            <input
              formControlName="renovatedYear"
              tabindex="11"
              autocomplete="off"
              matInput
              placeholder="Renovatie jaar"
              matTooltip="Renovatie jaar van het object"
            />
          </mat-form-field>
        </div>
      </div>
    </mat-dialog-content>
    <mat-dialog-actions class="d-flex">
      <button
        mat-raised-button
        type="submit"
        color="primary"
        tabindex="29"
        class="align-items-end"
        [disabled]="!form.valid"
        matTooltip="Na opslaan worden de openstaande meldingen ververst zodat de melding direct ingepland kan worden"
      >
        Opslaan
      </button>
      <button
        mat-raised-button
        tabindex="30"
        [mat-dialog-close]="true"
        data-test="cancelCloseDialog"
        class="align-items-end"
      >
        Annuleren
      </button>
    </mat-dialog-actions>
  </form>
</div>

我的ts文件

import { Component, Inject, OnDestroy, OnInit } from '@angular/core';
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
import {
  FormBuilder,
  FormControl,
  FormGroup,
  Validators,
} from '@angular/forms';
import { WorkOrderService } from '../services/work-order.service';
import { takeUntil } from 'rxjs/operators';
import { Observable, Subject } from 'rxjs';
import { CustomSnackbarService } from '../../shared/services/custom-snackbar.service';
import { Router } from '@angular/router';
import { v4 as uuidv4 } from 'uuid';
import { UserService } from '../../shared/services/user.service';

@Component({
  selector: 'app-create-work-order-dialog',
  templateUrl: './create-work-order-dialog.component.html',
  styleUrls: ['./create-work-order-dialog.component.css'],
})
export class CreateWorkOrderDialogComponent implements OnInit, OnDestroy {
  form: FormGroup;
  data: IWorkOrder;
  alreadySetDescriptionUpdated = false;
  showEditDescription = false;
  isLoading = false;
  buildingTypes: string[] = [
    'Hoekwoning',
    'Appartement',
    'Woonhuis',
    'Vrijstaand',
  ];
  statusWerkOrder: string[] = ['Open', 'In behandeling', 'Gesloten'];
  panelOpenState = false;
  onDestroy$ = new Subject();
  mechanics: any;

  constructor(
    public dialogRef: MatDialogRef<CreateWorkOrderDialogComponent>,
    @Inject(MAT_DIALOG_DATA)
    public passedData: { workOrder: IWorkOrder; mechanics: IUser },
    private formBuilder: FormBuilder,
    private workOrderService: WorkOrderService,
    private customSnackbarService: CustomSnackbarService,
    private userService: UserService,
    private router: Router
  ) {}

  ngOnInit(): void {
    // this.getMechanics();
    console.log('####--passedData', this.passedData);
    this.mechanics = this.passedData.mechanics;
    this.data = this.passedData.workOrder;
    this.buildForm();
  }

  ngOnDestroy() {
    this.onDestroy$.next();
    this.onDestroy$.complete();
  }

  private getMechanics() {
    this.userService
      .getUsers()
      .pipe(takeUntil(this.onDestroy$))
      .subscribe((users: IUser[]) => {
        this.mechanics = users.filter(
          (user: IUser) => user.role === 'technician'
        );
      });
  }

  save() {
    this.isLoading = true;
    const workOrder: IWorkOrder = { ...this.data, ...this.form.value };

    if (this.data && this.data !== null && this.data !== undefined) {
      this.workOrderService
        .updateWorkOrderForPlanning(workOrder)
        .pipe(takeUntil(this.onDestroy$))
        .subscribe(
          (data: IWorkOrder) => {
            this.isLoading = false;
            this.customSnackbarService.notification$.next({
              message: `Werkorder is ge-update`,
              type: 'info',
            });
            this.dialogRef.close();
            this.router.navigate(['planning']);
            this.workOrderService.refreshWorkOrders.next(true);
          },
          (error: any) => {
            this.customSnackbarService.notification$.next({
              message: `Fout bij aanmaken van werkorder: ${error}`,
              type: 'error',
            });
            console.log('Create Follow-up failure', error);
            this.isLoading = false;
          }
        );
    } else {
      this.workOrderService
        .createWorkOrderForPlanning(workOrder)
        .pipe(takeUntil(this.onDestroy$))
        .subscribe(
          (data: IWorkOrder) => {
            this.isLoading = false;
            this.customSnackbarService.notification$.next({
              message: `Werkorder is aangemaakt`,
              type: 'info',
            });
            this.dialogRef.close();
            this.workOrderService.refreshWorkOrders.next(true);
            this.router.navigate(['planning']);
          },
          (error: any) => {
            this.customSnackbarService.notification$.next({
              message: `Fout bij aanmaken van werkorder: ${error}`,
              type: 'error',
            });
            console.log('Create Follow-up failure', error);
            this.isLoading = false;
          }
        );
    }
  }

  private buildForm() {

    console.log('####--the data', this.data);
    this.form = this.formBuilder.group({
      id: [this.data?.id ? this.data.id : uuidv4()],
      projectNumber: new FormControl(this.data?.projectNumber, [
        Validators.required,
      ]),
      leakageReason: new FormControl(this.data?.leakageReason, [
        Validators.required,
      ]),
      dateInspection: new FormControl(this.data?.dateInspection, []),
      followupInspection: new FormControl(this.data?.followupInspection, []),
      clientPresent: new FormControl(this.data?.clientPresent, []),
      visibleWaterDamage: new FormControl(this.data?.visibleWaterDamage, []),
      visibleWaterDamagePeriod: new FormControl(
        this.data?.visibleWaterDamagePeriod,
        []
      ),
      buildingType: new FormControl(this.data?.buildingType, []),
      renovatedYear: new FormControl(this.data?.renovatedYear, []),
      buildingEstablished: new FormControl(this.data?.buildingEstablished, []),
      status: new FormControl(this.data?.status, []),
      user: this.formBuilder.group({
        id: [this.data?.user?.id],
        name: new FormControl(this.data?.user?.name),
        email: new FormControl(this.data?.user?.email),
        firebaseID: new FormControl(this.data?.user?.firebaseID),
        firebaseEmail: new FormControl(this.data?.user?.firebaseEmail),
        role: new FormControl(this.data?.user?.role),
        phoneNumber: new FormControl(this.data?.user?.phoneNumber),
      }),
      client: this.formBuilder.group({
        id: [this.data?.client?.id ? this.data.client.id : uuidv4()],
        name: new FormControl(this.data?.client?.name),
        contactPerson: new FormControl(this.data?.client?.contactPerson),
        email: new FormControl(this.data?.client?.email),
        phoneNumber: new FormControl(this.data?.client?.phoneNumber),
        mobilePhoneNumber: new FormControl(
          this.data?.client?.mobilePhoneNumber
        ),
        street: new FormControl(this.data?.client?.street),
        houseNumber: new FormControl(this.data?.client?.houseNumber),
        houseNumberExt: new FormControl(this.data?.client?.houseNumberExt),
        zipCode: new FormControl(this.data?.client?.zipCode),
        city: new FormControl(this.data?.client?.city),
        attribute: new FormControl(this.data?.client?.attribute),
      }),
      customer: this.formBuilder.group({
        id: [this.data?.customer?.id ? this.data.customer.id : uuidv4()],
        name: new FormControl(this.data?.customer?.name, [Validators.required]),
        contactPerson: new FormControl(this.data?.customer?.contactPerson),
        street: new FormControl(this.data?.customer?.street, [
          Validators.required,
        ]),
        houseNumber: new FormControl(this.data?.customer?.houseNumber, [
          Validators.required,
        ]),
        houseNumberExt: new FormControl(this.data?.customer?.houseNumberExt),
        zipCode: new FormControl(this.data?.customer?.zipCode, [
          Validators.required,
        ]),
        city: new FormControl(this.data?.customer?.city, [Validators.required]),
        phoneNumber: new FormControl(this.data?.customer?.phoneNumber, []),
        mobilePhoneNumber: new FormControl(
          this.data?.customer?.mobilePhoneNumber,
          []
        ),
      }),
      expertiseOffice: this.formBuilder.group({
        id: [
          this.data?.expertiseOffice?.id
            ? this.data.expertiseOffice.id
            : uuidv4(),
        ],
        expertiseOfficeName: new FormControl(this.data?.expertiseOffice?.name),
        fileNumber: new FormControl(this.data?.expertiseOffice?.fileNumber),
        nameOfAgent: new FormControl(this.data?.expertiseOffice?.nameOfAgent),
        phoneNumberAgent: new FormControl(
          this.data?.expertiseOffice?.phoneNumberAgent
        ),
        emailAgent: new FormControl(this.data?.expertiseOffice?.emailAgent),
        insuranceCompanyName: new FormControl(this.data?.expertiseOffice?.id),
        damageNumber: new FormControl(this.data?.expertiseOffice?.damageNumber),
        policyNumber: new FormControl(this.data?.expertiseOffice?.policyNumber),
      }),
    });
  }
}

正确显示了用户列表(机械),但是已经分配给工作订单的用户不会在“ monteur”字段中显示其姓名。

如何显示已分配给该workOrder的用户(机械)的默认值?

非常感谢您的帮助 皮特

1 个答案:

答案 0 :(得分:1)

我认为您只是在以错误的方式提供值,您必须在列表中提供整个对象,仅提供名称是行不通的。如果要使下拉菜单为多选,则需要编写 multiple

请使用以下几行替换html中的代码:

<div class="col-md-12">
        <mat-form-field class="input">
          <mat-label>Monteur</mat-label>
          <mat-select
            formControlName="name"
            name="name"
            tabindex="5" multiple
            [value]="data.user"
          >
            <mat-option
              *ngFor="let mechanic of mechanics"
              [value]="mechanic"
            >
              {{ mechanic.name }}
            </mat-option>
          </mat-select>
        </mat-form-field>
      </div>