借助ngFor索引访问formControlName错误时遇类型匹配错误求助
问题分析与解决方案
错误原因
你遇到的“No overload match this call”错误,核心原因是FormGroup.get()方法要求传入字符串类型的路径参数,但模板里的i是数字类型的索引,类型不匹配触发了Angular的类型检查报错。
另外你的代码写法存在冗余:当前<td>已经设置了[formGroupName]="i",意味着已经处于对应行的表单组上下文内,完全没必要从顶层的voucherEntries表单逐层定位控件。
修复方案
方案1:修正索引类型(保留原路径逻辑)
把数字索引i转为字符串,满足get()方法的参数类型要求:
[ngClass]="{'voucher-table-entry-error': this.voucherEntries.get('entries')?.get(i.toString())?.get('name')?.errors}"
或者用模板字符串拼接实现类型转换:
[ngClass]="{'voucher-table-entry-error': this.voucherEntries.get('entries')?.get(`${i}`)?.get('name')?.errors}"
方案2:利用当前表单上下文(推荐更简洁写法)
直接通过*ngFor循环里的control变量(当前行的表单组实例)访问控件,彻底避免索引类型问题:
<input [ngClass]="{'voucher-table-entry-error': control.get(header.header)?.errors && (control.dirty || control.touched)}" tabindex="1" [id]="i" list="nameEntryList" [placeholder]="header.header" [formControlName]="header.header" (keyup)="autoGenNextEntryRows($event)" (keydown.escape)="removeFocus($event)" type="text">
这里的control就是循环遍历的entriesControls.controls里的每一个表单组,直接用它获取对应控件的错误状态,逻辑更清晰也更高效。
最终完整模板示例
<tbody> <div [formGroup]="voucherEntries" class="voucher-entries-container"> <!-- Create Rows --> <tr formArrayName='entries' *ngFor="let control of entriesControls.controls; let i = index" class="table-data"> <td [formGroupName]="i" *ngFor="let header of headers; let headerIndex = index" [style.flex]="header.flex"> <div [id]="headerIndex+1" [tabIndex]="header.skip" [style.flex]="header.flex" (keydown)="test($event)" > <input [ngClass]="{'voucher-table-entry-error': control.get(header.header)?.errors && (control.dirty || control.touched)}" tabindex="1" [id]="i" list="nameEntryList" [placeholder]="header.header" [formControlName]="header.header" (keyup)="autoGenNextEntryRows($event)" (keydown.escape)="removeFocus($event)" type="text"> <datalist id="nameEntryList"> <option *ngFor="let item of itemData;" [value]="item.desc.name"></option> </datalist> </div> </td> </tr> </div> </tbody>
内容的提问来源于stack exchange,提问作者user11586200
相关产品推荐
相关产品推荐

