Angular中如何将HTML表单数据转换为指定格式传入TS文件
Angular表单转指定JSON格式解决方案
我是前端/Angular新手,第一次开发表单功能,需要把HTML表单数据转换成如下JSON格式并传到TS里:
{ "feedbackId": 1, "applicantId": 1, "positionId": 1, "comments": "test", "description": "test1", "recommendation": 1, "status": 1, "resourceRating": [ {"skillId":1,"ratingId":2}, {"skillId":2,"ratingId":3}, {"skillId":3,"ratingId":2}, {"skillId":4,"ratingId":3}, {"skillId":5,"ratingId":2}, {"skillId":6,"ratingId":3}, {"skillId":7,"ratingId":2}, {"skillId":8,"ratingId":3} ] }
现有HTML代码
<form [formGroup]="feedbackForm" (ngSubmit)="submitData()"> <div> <label class="form-control-label" for="">Rating Scale: </label> <div *ngFor='let rating of ratings'>{{rating.rating}}<span>. </span>{{rating.ratingName}}</div> </div> <table class="res-tbl"> <thead style="background-color: #f6f9fc;"> <tr> <th class="table-head"></th> </tr> </thead> <tbody> <tr class="skill-tr" *ngFor='let skill of skills; let i = index;'> <td class="skill-td"> <b>{{skill.skillName}}<span>:</span></b>{{skill.description}} </td> <td> <mat-radio-group > <span class="radio-span">0</span><mat-radio-button class="radio-btn" value="0"></mat-radio-button> <span class="radio-span">1</span><mat-radio-button class="radio-btn" value="1"></mat-radio-button> <span class="radio-span">2</span><mat-radio-button class="radio-btn" value="2"></mat-radio-button> <span class="radio-span">3</span><mat-radio-button class="radio-btn" value="3"></mat-radio-button> <span class="radio-span">4</span><mat-radio-button class="radio-btn" value="4"></mat-radio-button> </mat-radio-group> </td> </tr> </tbody> </table> <button>Submit</button> </form>
现有TS代码
export class FeedbackFormComponent implements OnInit { ngOnInit(): void { this.ratings = this.ratingService.getAllRatings(); console.log(this.ratings); this.skills = this.skillService.getAllSkills(); this.feedbackForm = this.fb.group({ applicantId:[''], positionId:[''], comments:[''], recommendation:[], resourceRating: this.fb.array([ this.fb.group({ skillId:[''], ratingId:[''] })]) }); } }
解决方案步骤
1. 动态生成resourceRating表单数组
当前resourceRating仅初始化了一个FormGroup,需根据skills数量生成对应分组。修改TS逻辑:
import { FormBuilder, FormGroup, FormArray } from '@angular/forms'; export class FeedbackFormComponent implements OnInit { feedbackForm!: FormGroup; ratings: any[] = []; skills: any[] = []; constructor( private fb: FormBuilder, private ratingService: RatingService, private skillService: SkillService ) {} // 便捷获取resourceRating数组 get resourceRating(): FormArray { return this.feedbackForm.get('resourceRating') as FormArray; } ngOnInit(): void { this.ratings = this.ratingService.getAllRatings(); this.skills = this.skillService.getAllSkills(); // 初始化基础表单 this.feedbackForm = this.fb.group({ applicantId: [''], positionId: [''], comments: [''], recommendation: [''], description: [''], // 目标JSON含此字段,需添加 status: [1], // 固定值可默认设置 resourceRating: this.fb.array([]) }); // 根据skills动态添加FormGroup this.skills.forEach(skill => { this.resourceRating.push( this.fb.group({ skillId: [skill.skillId], // 绑定当前技能ID ratingId: [''] // 留待单选框选择 }) ); }); } }
2. 关联HTML单选按钮到表单控件
修改HTML的tbody和单选框绑定逻辑,让每个技能的单选框对应resourceRating数组中的控件:
<tbody formArrayName="resourceRating"> <tr class="skill-tr" *ngFor='let skill of skills; let i = index;' [formGroupName]="i"> <td class="skill-td"> <b>{{skill.skillName}}<span>:</span></b>{{skill.description}} </td> <td> <mat-radio-group formControlName="ratingId"> <span class="radio-span">0</span><mat-radio-button class="radio-btn" value="0"></mat-radio-button> <span class="radio-span">1</span><mat-radio-button class="radio-btn" value="1"></mat-radio-button> <span class="radio-span">2</span><mat-radio-button class="radio-btn" value="2"></mat-radio-button> <span class="radio-span">3</span><mat-radio-button class="radio-btn" value="3"></mat-radio-button> <span class="radio-span">4</span><mat-radio-button class="radio-btn" value="4"></mat-radio-button> </mat-radio-group> </td> </tr> </tbody>
3. 补充缺失的表单控件
目标JSON中的applicantId、positionId等字段需要对应输入控件,在表单开头添加:
<div> <label>申请人ID: <input formControlName="applicantId" type="number"></label> <label>职位ID: <input formControlName="positionId" type="number"></label> <label>评论: <textarea formControlName="comments"></textarea></label> <label>描述: <textarea formControlName="description"></textarea></label> <label>推荐: <mat-radio-group formControlName="recommendation"> <mat-radio-button value="1">是</mat-radio-button> <mat-radio-button value="0">否</mat-radio-button> </mat-radio-group> </label> </div>
4. 实现submitData提交方法
在TS中添加提交逻辑,将表单值转换为目标JSON格式:
submitData() { if (this.feedbackForm.valid) { const formValue = this.feedbackForm.value; // 组装最终数据,转换数字类型(单选框返回字符串) const finalData = { feedbackId: 1, // 可根据业务逻辑动态生成 ...formValue, resourceRating: formValue.resourceRating.map(item => ({ skillId: Number(item.skillId), ratingId: Number(item.ratingId) })), recommendation: Number(formValue.recommendation), applicantId: Number(formValue.applicantId), positionId: Number(formValue.positionId) }; console.log('提交数据:', finalData); // 调用服务提交,例如:this.feedbackService.submit(finalData) } else { // 标记所有控件为已触碰,触发验证提示 this.feedbackForm.markAllAsTouched(); } }
内容的提问来源于stack exchange,提问作者Rose
相关产品推荐
相关产品推荐

