【问题标题】:How to get the value of list with same formcontrolname?如何获取具有相同表单控件名称的列表的值?
【发布时间】:2019-08-28 14:57:25
【问题描述】:

我有 4 个使用 loop 生成的输入。我正在为 UI 使用角度形式,但问题是我只得到最后一个输入值,并且要求我需要所有输入值,前提是我无法生成 formControlName 动态。有没有办法绕过只获取最后一个值并获取所有值?

相同的HTML代码是(这个循环将根据dataArr执行,这里假设它执行了4次):

<form [formGroup]="dataForm">
   <div *ngFor = "let data of dataArr;">

    <input type="text" placeholder="Key" value={{data.key}} formControlName="key"/>

   </div>
</form>

<button type="button" style="background-color: #4980FF;" (click)="save();">Save</button>

.ts 文件中的代码:

  // it is initializing and registering the form value
  dataForm = new FormGroup({
    key: new FormControl('', [Validators.required])

  });

  save(){
   // Here I am trying to print the form value 
  }

我希望在单击保存按钮时获取所有值,而不仅仅是最后一个值。

【问题讨论】:

  • 我不会推荐您创建表单的方式。在这种情况下使用FormArray 代替

标签: angular typescript angular7 angular-forms


【解决方案1】:

您需要改用FormArray

在您的组件中,创建您的 FormGroupFormArray

this.dataForm = new FormGroup({
    key: new FormArray(this.dataArr.map(data => new FormControl(data.key, [Validators.required])))
    // Add other form groups or form controls here
});

save() {
    console.log(this.dataForm.value);
}

在您的form 中绑定这些控件,如下所示。您不需要value 属性,因为FormControl 将为您绑定值。

<form [formGroup]="dataForm">
    <div *ngFor="let data of dataArr; let i = index" formArrayName="key">
        <input type="text" placeholder="Key" [formControlName]="i" />
    </div>
</form>

<button type="button" style="background-color: #4980FF;" (click)="save();">Save</button>

【讨论】:

  • 如果您只需要一个表单数组,请只使用一个 formArray - 它不需要创建一个内部有一个 formArray 的 formGroup,请参阅stackoverflow.com/questions/56622872/…
  • @Eliseo - 我认为提问者在他的FormGroup 中有其他数据,并且只发布了他的问题的相关数据。 @NeerajNauni - 如果FormGroup 中没有其他数据,那么是的,只创建一个FormArray 就足够了。
  • @NeerajNauni - 让我知道解决方案是否适合您
  • @nash11 不完全是,我做了一些调整。
【解决方案2】:

在处理表单中的项目数组时,您可能需要添加控件或删除控件,甚至编辑现有项目的值,始终使用角度 FormArray。

下面是 FormArray 的一个工作示例。这是一个工作 Stackblitz 更多关于FormArray

import {
  Component,
  OnInit
} from '@angular/core';
import {
  FormBuilder,
  FormGroup,
  FormArray
} from '@angular/forms';

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit {
  name = 'Angular';
  dataForm: FormGroup;
  items: FormArray;
  dataArr: any;
  constructor(private formBuilder: FormBuilder) {

  }
  ngOnInit() {
    this.dataForm = this.formBuilder.group({
      items: this.formBuilder.array([])
    });
    setTimeout(() => {
      this.dataArr = [{
          key: 'First'
        },
        {
          key: 'Second'
        },
        {
          key: 'Third'
        },
        {
          key: 'Fourth'
        }
      ];
      this.createItems();
    }, 2000)
  }
  createItems() {
    this.items = this.dataForm.get('items') as FormArray;
    this.dataArr.forEach((elem: any) => {
      const ctrl = this.formBuilder.group({
        key: [elem.key]
      });
      this.items.push(ctrl);
    })
  }


  save() {
    console.log(this.dataForm.get('items').value)
    return this.dataForm.get('items').value;
  }

}
<form [formGroup]="dataForm">
  <div formArrayName="items" *ngFor="let item of dataForm.get('items').controls; let i = index;">
    <div [formGroupName]="i">
      <input type="text" placeholder="Key" formControlName="key" />
    </div>
  </div>
</form>

<button type="button" style="background-color: #4980FF;" (click)="save();">Save</button>

希望这会有所帮助。

【讨论】:

  • dataArr 中的数据将来自 API,问题是由于 API 调用本质上是异步的,因此表单首先呈现,然后 API 被调用,所以我的 dataArr 显示null ,同时呈现表单。
  • 所以这根本不是问题,只需在表单上使用 *ngIf。更新代码以在 api 返回结果时执行。我添加了 2 秒的 setTimeout,之后设置了 dataArr 对象并加载了表单。这解决了您的 API 数据问题..
  • 但是 dataArr 的大小不是固定的,也不包含任何像'key'这样的键
  • 没关系 dataArr 可以是任何大小,所有项目都会显示出来。此外,该属性键是我为演示 FormArray 而设置的,您可以使用任何您想要的或 dataArr 中的任何属性..
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-07-17
  • 2018-03-26
  • 1970-01-01
  • 2020-03-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多