0

我正在使用 formArray 创建动态表单。但是我遇到了“TypeError:无法读取未定义的属性'控件'”

enter code here
import { Component, OnInit } from '@angular/core';
import { FormGroup, FormBuilder, FormArray } from '@angular/forms';
@Component({
 selector: 'app-root',
 templateUrl: './app.component.html',
 styleUrls: ['./app.component.css']
})
 export class AppComponent implements OnInit {
 title = 'Trainner Registration Form ';
 registrationForm: FormGroup;

 get LanguagesForm() {
    return this.registrationForm.get('Languages') as FormArray;
 }

 addLanguage() {
  this.LanguagesForm.push(this.fb.control(''));
}


 constructor(private  fb : FormBuilder ) {}
   ngOnInit(){
     this.registrationForm = this.fb.group({
      personalDetails : this.fb.group({
      name: this.fb.group({
        firstName: [''],
        lastName: ['']
      }),
      aboutYours: [''],
      dob: [''],
      // lang: [''],
      Languages: this.fb.array([]),
      wTT: ['']
    })
  });

}


onSubmit() {
  console.log(this.registrationForm.value);
  // this._registerationservice.register(this.registrationForm.value).subscribe(
  //   response => console.log('Success', response),
  //   error => console.log('Error',error)
  // );
}

}

预期结果:如果用户单击“添加语言”按钮,则应创建一个新的输入字段。

实际结果:我收到“TypeError:无法读取未定义的属性‘控件’”

app.component.html 文件

<div style="text-align:center">
<h1>Welcome to {{ title }}!</h1>
</div>

<mat-horizontal-stepper >

  <mat-step  [stepControl]="personalDetails">
    <ng-template matStepLabel>Enter Personal Details</ng-template>
    <div formGroupName="personalDetails">
      <div formGroupName="name">
          <div class="form-group">
            <label>First Name : </label>
            <input type="text"  formControlName="firstName" class="form-control"  >
          </div>

          <div class="form-group">
            <label>Last Name : </label>
            <input type="text" formControlName="lastName" class="form-control">
          </div>
      </div>    
      <div class="form-group">
          <label>DOB : </label>
          <input type="date" formControlName="dob" class="form-control">
        </div>

        <div class="form-group">
          <label>About Yourself : </label>
          <textarea formControlName="aboutYours" class="form-control"></textarea>
        </div>

        <div class="form-group">
            <label>Language(s) : </label>
            <button type="button" class="btn btn-secondary btn-sm m-2" (click)="addLanguage()">Add Language</button>
            <!-- <input type="text" formControlName="lang" class="form-control"> -->

            <div formArrayName="Languages">
                <div *ngFor="let lang of langsform.controls; let i =index;">
                    <input type="text" class="form-control" [formControlName]="i">
                </div>
              </div>

          </div>


</mat-horizontal-stepper>
</form>
</div>
4

4 回答 4

2

发生这种情况是因为您没有设置上层表单组,personalDetails所以要在控件中使用名称查看控件,其中表单组Languages中的控件是一个控件,与您的错字相关的另一件事必须是“Languages.controls”registrationFormLanguagespersonalDetailsLanguagesForm.controls

<div class="form-group">
  <label>Language(s) : </label>
  <button type="button" class="btn btn-secondary btn-sm m-2" (click)="addLanguage()">Add Language</button>

  <div [formGroup]="registrationForm"> <!--  -->
    <div [formGroupName]="'personalDetails'"> <!--  -->

      <div formArrayName="Languages">
        <div *ngFor="let lag of registrationForm.get('personalDetails').get('Languages').controls; let i =index;">
          <input type="text" class="form-control" [formControlName]="i">
        </div>

      </div>
    </div>
  </div>
</div>

您可以使用 get 属性来访问这样的语言表单

  langsform() :FormArray { 
    return this.registrationForm.get('personalDetails').get('Languages') as FormArray 
  }

模板

<div [formGroup]="registrationForm">
  <div [formGroupName]="'personalDetails'">

    <div formArrayName="Languages">
      <div *ngFor="let lang of langsform.controls; let i =index;">
          <input type="text" class="form-control" [formControlName]="i">
      </div>
    </div>
  </div>
</div>

演示

于 2019-09-13T08:04:10.223 回答
1

我认为问题在于您在 onInit 中初始化了 registrationForm 对象,此时模板已经被解析,所以您应该*ngIf="this.registrationForm"在这个 div 上添加一个<div formArrayName="Languages">

于 2019-09-13T08:00:00.230 回答
1

您将 FormArray 命名为“Languages”而不是 LanguagesForm。

<div *ngFor="let Languages of registrationForm.controls.personalDetails.controls.Languages.controls; let i =index;">
      <input type="text" class="form-control" [formControlName]="i">
</div>

编辑:我更改了 getLangsform 和<mat-step>and<form>标签。 https://stackblitz.com/edit/angular-lc8mu1

于 2019-09-13T08:07:24.627 回答
1

试试这个方法:

在您的 HTML 中:

 <div class="form-group">
      <div formArrayName="languages">
        <label>Languages</label>

        <div class="row">
          <div class="col-8">
            <input type="text" class="form-control" id="languages">
          </div>
          <div class="col-4">
            <button type="button" class="btn btn-primary" (click)="onAddLanguages()">Add</button>
          </div>
        </div>

        <div class="form-group row" *ngFor="let languages of registrationForm.get('languages').controls; let i = index">
          <div class="col-8">
            <input type="text" class="form-control" [formControlName]="i">
          </div>
          <div class="col-4">
            <button type="button" class="btn btn-danger" (click)="onDeleteLanguages(i)">Delete</button>
          </div>
        </div>
      </div>
    </div>

在您的 TS 中:

this.registrationForm = new FormGroup({
       'languages': new FormArray([])
});
onAddLanguages() {
const control = new FormControl(null, Validators.required);
(<FormArray>this.registrationForm.get('languages')).push(control)
}
onDeleteLanguages(index) {
(<FormArray>this.registrationForm.get('languages')).removeAt(index)
}
于 2019-09-13T09:34:43.583 回答