Angular:FormGroup中FormArray取值方法及动态表单控件异常排查
The Root Cause of Your Issue
Right now, each entry in your properties FormArray is a single FormControl, but you're binding both an <input> and <select> to the same formControlName (the array index). This means every time either control is updated, it overwrites the value in that single FormControl—so only one value gets saved per array item.
To capture both values, each item in your FormArray needs to be a FormGroup that contains two separate FormControls (one for the text input, one for the dropdown).
Step 1: Update the Component Code
First, adjust how you initialize and modify the FormArray to use FormGroups instead of single FormControls:
import { Component, OnInit } from '@angular/core'; import { FormGroup, FormBuilder, FormArray, FormControl } from '@angular/forms'; import { IcoService } from '../../services/ico.service'; @Component({ selector: 'app-team', templateUrl: './team.component.html', styleUrls: ['./team.component.css'] }) export class TeamComponent implements OnInit { searchForm: FormGroup; constructor(private fb: FormBuilder, private icoService: IcoService) { } ngOnInit() { this.searchForm = this.fb.group({ properties: this.fb.array([]) }); this.onAddProperty(); // Add initial form group } // Helper getter to easily access the properties FormArray get properties(): FormArray { return this.searchForm.get('properties') as FormArray; } submit() { console.log(this.searchForm.value); // Now you'll see an array of objects with both text and select values this.icoService.teamDetail(this.searchForm.value).subscribe( (result) => console.log(result), (err) => console.log('err', err) ); } onAddProperty() { // Push a new FormGroup with two controls instead of a single FormControl this.properties.push( this.fb.group({ textValue: new FormControl(''), // For the text input selectValue: new FormControl('') // For the dropdown }) ); } onDelProperty(index: number) { // Remove the specific FormGroup at the given index (no unnecessary loop) this.properties.removeAt(index); } }
Key changes:
- Added a helper getter
propertiesto simplify accessing the FormArray onAddPropertynow pushes a FormGroup with two distinct controls (textValueandselectValue)- Removed redundant loops in
onAddPropertyandonDelProperty(they only ran once anyway)
Step 2: Update the HTML Template
Modify the template to link each array item to its FormGroup, then bind each control to its specific FormControl name:
<div class="container"> <p></p> <div> <form [formGroup]="searchForm" novalidate (ngSubmit)="submit()"> <div formArrayName="properties"> <div *ngFor="let prop of properties.controls; let i = index" [formGroupName]="i"> <!-- Bind text input to the 'textValue' control in the FormGroup --> <input type="text" class="form-control" formControlName="textValue"> <!-- Bind dropdown to the 'selectValue' control in the FormGroup --> <select class="form-control" formControlName="selectValue"> <option value="x">x</option> <option value="y">y</option> <option value="xy">xy</option> <option value="z">z</option> </select> <button *ngIf="properties.length > 1" (click)="onDelProperty(i)">Delete</button> </div> </div> <p></p> <a (click)="onAddProperty()">Add</a> <button class="btn btn-bold btn-primary" type="submit">submit</button> </form> </div> </div>
Key template changes:
- Added
[formGroupName]="i"to wrap each input/select pair (links to the FormGroup at indexiin the FormArray) - Changed
[formControlName]="i"toformControlName="textValue"andformControlName="selectValue"for each control - Used the
propertiesgetter for cleaner, more readable code
What This Fixes
When you submit the form now, this.searchForm.value will return an array of objects with both values captured correctly:
{ properties: [ { textValue: "your input text", selectValue: "x" }, { textValue: "another input", selectValue: "y" }, // ... additional items as needed ] }
No more overwriting values—each input/select pair retains its own data.
内容的提问来源于stack exchange,提问作者Raj kumar

