在递归角度形式上无法使用ngIf找到带有路径的控件 [英] Cannot Find Control with Path Using ngIf on Recursive Angular Form

查看:74
本文介绍了在递归角度形式上无法使用ngIf找到带有路径的控件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是下面代码的堆栈闪电. 我正在使用FormArrays和子组件制作一个相当复杂的深层嵌套Angular表单.在大多数情况下,一切都按预期进行. group对象包含conjunctorconditions[]groups[]. groups[]是一个嵌套组,可以无限嵌套包含同一对象.

Here is the stackblitz for the code below. I am making a fairly complex deeply nested Angular form using FormArrays, and child components. For the most part, everything is working as expected. A group object contains a conjunctor, conditions[], and groups[]. groups[] is a nested group that can be nested infinitely containing the same object.

当前,您可以选择添加组",添加嵌套组",添加条件",删除组"和删除条件".这样就可以制作一个嵌套的表单对象.为此,该应用程序分为三个部分:

Currently, you have the option to "add group", "add nested group", "add condition", "delete group", and "delete condition" so that it makes a nested form object. To do this, the app is split into 3 components:

AppComponent:持有带有ng-container s和*ngFor的主窗体以遍历组

AppComponent: Holds the main form with ng-containers and *ngFor to iterate over the groups

GroupControlComponent:保存AppComponent内部每个项目的逻辑,并与AppComponent进行相同的操作,只是针对条件和嵌套组

GroupControlComponent: Holds the logic of each item inside the AppComponent and does the same thing as the AppComponent but for Conditions and Nested Groups

ConditionsForm:保存条件项的逻辑

ConditionsForm: Holds the logic of the conditions items

并且有一个ActionsButtonsBarComponent来保存按钮以发出事件,添加和删除组和条件.

And there is an ActionsButtonsBarComponent to hold the buttons to emit events, add, and remove the groups and conditions.

我正在尝试在第二组中做到这一点,连接器有一个输入.我根本不需要第一个实例,因为我希望第一个实例始终为null.但是,在第2次及其后的实例中,我希望出现连接器输入,并提供选项为"AND"或"AND".或"OR".创建此代码时,出现错误:ERROR: Cannot find control with path: 'statement → groups → 1 → conjunctor来自AppComponent.

I am trying to make it so on every second group, there is an input for the Conjunctor. I don't want it at all on the first instance since I want the first to always be null. However, on the 2nd and thereafter instances, I want the conjunctor input to appear giving the option to be either "AND" or "OR". As I create this, I am getting the error: ERROR: Cannot find control with path: 'statement → groups → 1 → conjunctor coming from the AppComponent.

这是AppComponent的外观:

Here's how the AppComponent looks:

<form [formGroup]="_form">
    <ng-container formGroupName="statement">
        <ng-container formArrayName="groups">
            <ng-container *ngFor="let group of _groupsFormArray?.controls; index as i">
         <div *ngIf="i > 0">
           <div [formGroupName]="i">
             <input type="text" formControlName="conjunctor">
           </div>
         </div>
            <app-group-control 
             (remove)="_delete(i)"
             [formControlName]="i"
             [formLabel]="'Group '+ (i + 1) + ':'">
            </app-group-control>
            </ng-container>
        </ng-container>
    </ng-container>
</form>

如您所见,有一个div包含ngIf逻辑:

As you can see, there is a div containing the ngIf logic:

<div *ngIf="i > 0">
  <div [formGroupName]="i">
    <input type="text" formControlName="conjunctor">
  </div>
</div>

此方法不起作用,但是我尝试过的其他方法都没有.

This method is not working, but neither have the other methods I have tried.

到目前为止,我已经尝试过多次将FormGroupName更改为groupsstatementsiindex,但没有任何改善.

So far, I have tried changing the FormGroupName many times to groups, statements, i, index, resulting in no improvement.

我还尝试使用@ViewChildren('templateRef') templateRefVar: QueryList<ElementRef>;从AppComponent跟踪每个ngFor的实例,然后使用模板引用#templateRef跟踪ngFor内部.从那里,我使用@Input() groupInstances将此templateRef.length传递给我的子组件GroupControlComponent,然后在内部使用ngIf.这是我得到的最接近的问题,但是问题是,每当满足ngIf条件时,它就会出现在每个组数组实例(包括第一个)上,并且出现错误:ExpressionChangedAfterItHasBeenCheckedError: Expression has changed after it was checked. Previous value: '0'. Current value: '1'.. 这里是使用此方法获得的最接近的StackBlitz .并且这是上述代码中的StackBlitz .

I have also tried tracking the instances of each ngFor from the AppComponent using @ViewChildren('templateRef') templateRefVar: QueryList<ElementRef>; and then inside the ngFor, using a template ref #templateRef. From there, I pass this templateRef.length to my child component GroupControlComponent using @Input() groupInstances , and then using the ngIf inside. This is the closest I have gotten, but the problem is, every single time the ngIf condition is met, it appears on EVERY instance of the group arrays, including the first, as well as gives me the error: ExpressionChangedAfterItHasBeenCheckedError: Expression has changed after it was checked. Previous value: '0'. Current value: '1'.. Here is a StackBlitz of the closest I've got using this method. And here is the StackBlitz from the code as of above.

如果您想查找有关此递归表格的更多信息,可以在此处了解有关此递归表格的信息.

If you'd like to find more about this recursive form, you can read about that here.

推荐答案

groupInstance替换为showConjunctor只是为了使其在用途上更加明显.

Let's replace groupInstance for showConjunctor just to make it more obvious in what it's there for.

您可以在自己的 app.component.hml 中进行此操作:

You can do this in you app.component.hml:

<app-group-control 
  #templateRef
  (remove)="_delete(i)"
  [formControlName]="i"
  [formLabel]="'Group '+ (i + 1) + ':'"
  [showConjunctor]="!((i + 1) % 2)">
</app-group-control>

我正在考虑上述片段中的i*ngFor中当前循环的索引(就像Stackblitz演示中一样).

I'm considering that i, in the above snippet, is the index of the current loop in *ngFor (like in the Stackblitz demo).

另外,从app.component.html删除此部分:

<div *ngIf="i > 0">
  <div [formGroupName]="i">
    <input type="text" formControlName="conjunctor">
  </div>
</div>

[更新] :根据您的评论,如果您希望所有连接器中都包含连接器 您可以在GroupControlComponent内将@Input() showConjuntor设置为true(

[UPDATE]: Per your comments, if you want to have the conjunctor in all of the nested Groups, you can set the @Input() showConjuntor to true inside the GroupControlComponent (Stackblitz demo):

<ng-container formArrayName="groups">
  <app-group-control *ngFor="let s of _groupsFormArray?.controls; index as i"
                      (remove)="_deleteGroupFromArray(i)" 
                      [formControlName]="i"
                      [formLabel]="'Nested Group '+ (i + 1) + ':'"
                      [showConjunctor]="true">
  </app-group-control>
</ng-container>

这篇关于在递归角度形式上无法使用ngIf找到带有路径的控件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆