简体   繁体   English

Angular 中的嵌套反应形式

[英]Nested reactive forms in Angular

I am trying to dynamically create a nested FormArray in my Angular 6 application.我正在尝试在我的 Angular 6 应用程序中动态创建一个嵌套的 FormArray。

I have a quote, which has a collection of quote-items我有一个报价单,其中包含报价项的集合

export class Quote {
    quoteId: number;
    quoteItems: QuoteItem[]
    status: string;
}

export class QuoteItem {

    quoteItemId: number;
    description: string;
    quoteItemDetails: QuoteItemDetail[]
}

export class QuoteItemDetail {        
    quoteItemDetailId: number;
    rate: number;
    quantity: number;
    total: number;
}

I have a form that has the Quote object, where a user can click on a button to add and remove one or more QuoteItems.我有一个包含 Quote 对象的表单,用户可以在其中单击一个按钮来添加和删除一个或多个 QuoteItem。

This is my code where I initialise my form:这是我初始化表单的代码:

ngOnInit() {
    this.quoteForm = this.fb.group({
        status: [''],
        quoteItems: this.fb.array([])
    });
    this.addQuoteItem();
}

And this is how I get the dynamic adding and removing working:这就是我如何进行动态添加和删除工作:

get quoteItems() {
    return this.quoteForm.get('quoteItems') as FormArray;
}  

addQuoteItem() {
    this.quoteItems.push(this.fb.group({
        description: '',
        quoteItemDetails: this.fb.array([])
    }));
}


removeQuoteV2Item(index) {
  this.quoteV2Items.removeAt(index);
}

And my html:还有我的 html:

<div formArrayName="quoteItems">

    <div @items *ngFor="let item of quoteItems.controls; let contentIndex=index" [formGroupName]="contentIndex">
        <input type="text" formControlName="description">
    </div>
</div>

<p>
  <a (click)="addQuoteItem()">Add Quote Item</a>
</p>

What I'm trying to do is then have the same functionality but for my QuoteItemDetail array.我想要做的是具有相同的功能,但对于我的 QuoteItemDetail 数组。 So a user can add one or more quoteItems, and within them add one or more QuoteItemDetails.因此用户可以添加一个或多个quoteItems,并在其中添加一个或多个QuoteItemDetails。

I'm really stuck at the first point, I can't work out how to get a form array assessor, this doesn't work as an example, as I'm not sure how to pass the index across:我真的被困在第一点,我无法弄清楚如何获得表单数组评估器,这不能作为示例,因为我不确定如何传递索引:

get quoteItemDetails() {
  return this.quoteItems.get('quoteItemDetails') as FormArray;
}

You will not be able to do it with an accessor.您将无法使用访问器来执行此操作。 The accessor is going to give you a reference to one attribute.访问器将为您提供对一个属性的引用。 But as you said, in this case you need an index to specify what quoteItemDetails FormArray reference you need (since as far as I understand you want a FormArray in each quoteItem, so each quoteItem can have several quoteItemDetails, right?).但是正如您所说,在这种情况下,您需要一个索引来指定您需要的quoteItemDetails FormArray 引用(因为据我所知,您希望每个quoteItem 中有一个FormArray,因此每个quoteItem 可以有多个quoteItemDetails,对吗?)。

I don't see a problem with that though.不过,我不认为这有什么问题。 Instead of doing it with an accessor like you have done with the quoteItems, you will have to do it with a method taking the one parameter you need, the index.不是像使用quoteItems那样使用访问器来执行它,而是必须使用一种方法来执行它,该方法采用您需要的一个参数,即索引。 Something like this:像这样的东西:

quoteItemDetails(quoteItemIndex: number): FormArray {
  return this.quoteItems.at(quoteItemIndex).get('quoteItemDetails') as FormArray;
}

And then you represent it on the template:然后你在模板上表示它:

<div formArrayName="quoteItems">

  <div @items *ngFor="let item of quoteItems.controls; let contentIndex=index" [formGroupName]="contentIndex">
    <input type="text" formControlName="description">
    <div *ngFor="let quoteItemDetail of quoteItemDetails(contentIndex).controls; let detailIndex=index" [formArrayName]="detailIndex">
      <input type="number" formControlName="description" />
    </div>
  </div>
</div>

I hope this helps you.我希望这可以帮助你。 I have not tested the code but the solution should be someshere along these lines.我还没有测试代码,但解决方案应该是沿着这些路线的某个地方。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM