Рекурсивный шаблон внутри внутреннего @for в Angular 17

Я пытаюсь создать рекурсивный шаблон и столкнулся с проблемой. Мой шаблон:

<ng-template #recursiveGroups let-groups>
  @for (group of groups; track group; let i = $index) {
      <!-- Some stuff are shown -->
      @for (subGroup of group.subGroups; track subGroup;  let j = $index) {
        <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: data[i].subGroups[j]}"></ng-container>
        <!-- ALSO, SEPARATLY, TRIED: -->
        <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: subGroup}"></ng-container>
        <!-- OR: -->
        <ng-container *ngTemplateOutlet = "recursiveGroups; context:{groups: subGroup}"></ng-container>
      }
  }
 </ng-template>
<ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: data}"></ng-container>

Мои данные выглядят так:

data: [
  {
    ...,
    children: [
      {
        ...
      }
    ],
    subGroups: [
      {
        ...,
        children: [
          {
            ...
          }
        ],
        subGroups: [
          {
            ...,
          }
        ],
      }
    ],
  },
  ...
]

Использование context:{groups: <*>} показывает только самый верхний уровень.

Использование context:{@implicit: <*>} показывает только самый верхний уровень, а также вызывает ошибку:

core.mjs:6531 ERROR TypeError: newCollection[Symbol.iterator] is not a function

Что мне здесь не хватает? Спасибо.

вам просто нужно добавить условие ngIf перед второй группой цикла. Подгруппы

Dakshesh Baldaniya 16.05.2024 08:39

Было бы здорово, если бы вы предоставили примеры данных. Вы предоставляете data, который является объектом в <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: data}"></ng-container>, data не повторяется.

Yong Shun 16.05.2024 08:46

@DaksheshBaldaniya, можешь поподробнее? ngif с каким условием? Для чего это?

Liran_T 16.05.2024 09:36

@YongShun Извините, вы правы, я забыл написать «данные» как массив объектов. Зафиксированный. В любом случае, я вижу, что первый слой состоит из дочерних элементов и метаданных каждой подгруппы, но опять же, только в первом слое.

Liran_T 16.05.2024 09:40
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Angular и React для вашего проекта веб-разработки?
Angular и React для вашего проекта веб-разработки?
Когда дело доходит до веб-разработки, выбор правильного front-end фреймворка имеет решающее значение. Angular и React - два самых популярных...
Эпизод 23/17: Twitter Space о будущем Angular, Tiny Conf
Эпизод 23/17: Twitter Space о будущем Angular, Tiny Conf
Мы провели Twitter Space, обсудив несколько проблем, связанных с последними дополнениями в Angular. Также прошла Angular Tiny Conf с 25 докладами.
Угловой продивер
Угловой продивер
Оригинал этой статьи на турецком языке. ChatGPT используется только для перевода на английский язык.
Мое недавнее углубление в Angular
Мое недавнее углубление в Angular
Недавно я провел некоторое время, изучая фреймворк Angular, и я хотел поделиться своим опытом со всеми вами. Как человек, который любит глубоко...
Освоение Observables и Subjects в Rxjs:
Освоение Observables и Subjects в Rxjs:
Давайте начнем с основ и постепенно перейдем к более продвинутым концепциям в RxJS в Angular
2
4
221
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Ваш шаблон recursiveGroups ожидает массив, поэтому я не вижу, чтобы вам нужен вложенный @for для subGroups. Шаблон можно повторно использовать для итерации subGroups.

Изменения:

  1. Удалите вложенные @for.

  2. Укажите group.subGroups в контексте вложенного <ng-container>.

<ng-template #recursiveGroups let-groups>
  @for (group of groups; track group; let i = $index) {
    
    <ng-container *ngTemplateOutlet = "recursiveGroups; context:{ $implicit: group.subGroups }"></ng-container>
  }
</ng-template>

Демо @ StackBlitz

Вы запускаете цикл forLoop в верхней части шаблона, поэтому в рекурсии больше циклов for не требуется. Все, что вам нужно сделать, это убедиться, что входные данные для рекурсивного шаблона остаются в виде массива, тогда он будет отображаться правильно:

import { CommonModule } from '@angular/common';
import { Component } from '@angular/core';
import { bootstrapApplication } from '@angular/platform-browser';
import 'zone.js';

@Component({
  selector: 'app-root',
  standalone: true,
  imports: [CommonModule],
  template: `
    <ng-template #recursiveGroups let-groups>
      @for (group of groups; track group; let i = $index) {
        {{group.id}}
        <hr/>
        <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: group.children}"></ng-container>
        <hr/>
        <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: group.subGroups}"></ng-container>
      }
    </ng-template>
    <ng-container *ngTemplateOutlet = "recursiveGroups; context:{$implicit: data}"></ng-container>
  `,
})
export class App {
  name = 'Angular';
  data: any = [
    {
      id: 1,
      children: [
        {
          id: 2,
        },
      ],
      subGroups: [
        {
          id: 3,
          children: [
            {
              id: 4,
            },
          ],
          subGroups: [
            {
              id: 5,
            },
          ],
        },
      ],
    },
  ];
}

bootstrapApplication(App);

Демо-версия Stackblitz

Большое спасибо! Я бы тоже принял этот ответ, но я могу принять только один.

Liran_T 16.05.2024 14:47

Другие вопросы по теме