无法将数据修补到FormArray

San*_*adi 14 html javascript typescript angular formarray

无法将值修补为FormArray resultList.

有人可以解释我,我错过了什么?

TS档案:

import { Component, OnInit } from '@angular/core';
import { Student } from '../student';
import { FormGroup, FormControl, Validators, FormArray } from '@angular/forms';

@Component({
  selector: 'app-container',
  templateUrl: './container.component.html',
  styleUrls: ['./container.component.css']
})

export class ContainerComponent implements OnInit {

  studList: Student[] = [];
  myform: FormGroup = new FormGroup({
    firstName: new FormControl('', [Validators.required, Validators.minLength(4)]),
    lastName: new FormControl(),
    gender: new FormControl('male'),
    dob: new FormControl(),
    qualification: new FormControl(),
    resultList: new FormArray([])
  });    

  onSave() {
    let stud: Student = new Student();
    stud.firstName = this.myform.get('firstName').value;
    stud.lastName = this.myform.get('lastName').value;
    stud.gender = this.myform.get('gender').value;
    stud.dob = this.myform.get('dob').value;
    stud.qualification = this.myform.get('qualification').value;
    this.studList.push(stud);
    this.myform.controls.resultList.patchValue(this.studList);
    console.log(JSON.stringify(this.studList));
  }

  ngOnInit() {
  }
}
Run Code Online (Sandbox Code Playgroud)

模型:

export class Student {
    public firstName: String;
    public lastName: string;
    public gender: string;
    public dob: string;
    public qualification: string;
}
Run Code Online (Sandbox Code Playgroud)

HTML:

    <div class="container">
        <h3>Striped Rows</h3>
        <table class="table table-striped" formArrayName="resultList">
            <thead>
                <tr>
                    <th>Firstname</th>
                </tr>
            </thead>
            <tbody>
                <tr *ngFor="let item of myform.controls.resultList.controls; let i = index" [formGroupName]="i">
                    <td><p formControlName="firstName"></p></td>
                </tr>
            </tbody>
        </table>
    </div>
Run Code Online (Sandbox Code Playgroud)

this.studList JSON:

[  
   {  
      "firstName":"santosh",
      "lastName":"jadi",
      "gender":"male",
      "dob":"2018-03-31T18:30:00.000Z",
      "qualification":"BE"
   },
   {  
      "firstName":"santosh",
      "lastName":"jadi",
      "gender":"male",
      "dob":"2018-03-31T18:30:00.000Z",
      "qualification":"BE"
   }
]
Run Code Online (Sandbox Code Playgroud)

Yer*_*kon 12

通过你的问题,你想新添加StudentresultList.首先,您需要知道的FormArray是一个AbstractControl数组 .您可以只添加数组类型的AbstractControl而不是其他类型.为了简化任务,更喜欢使用FormBuilder:

 constructor(private fb: FormBuilder) {}

  createForm() {

    this.myform = this.fb.group({
      firstName: ['', [Validators.required, Validators.minLength(4)]],
      lastName: [],
      gender: ['male'],
      dob: [],
      qualification: [],
      resultList: new FormArray([])
    });
  }
Run Code Online (Sandbox Code Playgroud)

正如您在填充resultList 之前所看到的 FormArray,它已映射到FormGroup:

onSave() {
    let stud: Student = new Student();
    stud.firstName = 'Hello';
    stud.lastName = 'World';
    stud.qualification = 'SD';
    this.studList.push(stud);

    let studFg = this.fb.group({
      firstName: [stud.firstName, [Validators.required, Validators.minLength(4)]],
      lastName: [stud.lastName],
      gender: [stud.gender],
      dob: [stud.dob],
      qualification: [stud.qualification],
    })
     let formArray = this.myform.controls['resultList'] as FormArray;
    formArray.push(studFg);
    console.log(formArray.value)
  }
Run Code Online (Sandbox Code Playgroud)

FormBuilder - 从用户指定的配置创建AbstractControl.

它本质上是语法糖,缩短了新的FormGroup(), 新的FormControl()新的FormArray()样板,它们可以以更大的形式构建.

另外,在绑定到元素的html formControlName中<p>,它不是输入,你不能绑定到不像div/p/span ... 这样的表单元素:

 <tbody>
                <tr *ngFor="let item of myform.controls.resultList.controls; let i = index" [formGroupName]="i">
                    <td><p formControlName="firstName"></p></td> <==== Wrong element 
                </tr>
</tbody>
Run Code Online (Sandbox Code Playgroud)

所以,我想你只想在表格中显示添加的学生.然后遍历studList并在表中显示它的值:

<tbody>
                <tr *ngFor="let item of studList; let i = index" [formGroupName]=i>
                    <td>
                        <p> {{item.firstName}} </p>
                    </td>
                </tr>
</tbody>
Run Code Online (Sandbox Code Playgroud)

修补价值

修补阵列时要小心.因为FormArraypatchValue索引修补值:

 patchValue(value: any[], options: {onlySelf?: boolean, emitEvent?: boolean} = {}): void {
    value.forEach((newValue: any, index: number) => {
      if (this.at(index)) {
        this.at(index).patchValue(newValue, {onlySelf: true, emitEvent: options.emitEvent});
      }
    });
    this.updateValueAndValidity(options);
  }
Run Code Online (Sandbox Code Playgroud)

因此,它下面的代码会修复index = 0处的元素:第一个索引值this.myform.controls['resultList'] as FormArray将替换为:

let stud1 = new Student();

stud1.firstName = 'FirstName';
stud1.lastName = 'LastName';
stud1.qualification = 'FFF';
formArray.patchValue([stud1]);
Run Code Online (Sandbox Code Playgroud)

你的情况不起作用,因为patchValue 需要数组中的一些控件.在您的情况下,数组中没有控件.看源代码.

StackBlitz演示


Omk*_*hav 6

首先尝试执行此步骤,并确保您使用正确的方法

因为在您的方案中,您正在将对象修补到formArray,所以您必须首先解析该对象并检查是否在app.module.ts中导入了ReactiveFormsModule。