首页 > 解决方案 > 以角度创建递归动态扩展导航的正确方法是什么,以及如何正确切换其菜单项?

问题描述

我有一个正在开发的 Angular 8 应用程序。我在我的应用程序中使用了 boostrap 4 布局。我创建的是一个包含一些嵌套菜单项的菜单。我正在按照动态扩展导航抽屉示例创建动态扩展导航栏。

我面临的问题是,当我点击我的(第一级/父级)菜单项时,它会展开所有嵌套的菜单项,这是我想要阻止的。

下面的代码我试过:

<div class="row">
  <div *ngTemplateOutlet="recursiveMenu; context:{ $implicit: navItems }"></div>
  <ng-template #recursiveMenu let-menus>
    <ul class="w-100">
      <li *ngFor="let menu of menus;">
        <a class="align-self-stretch text-left" href="#" title="{{menu.displayName}}" (click)="onItemSelected(menu)">
          <i class="fa {{menu.iconName}}"></i> <span class="nav-header-primary p-2">{{menu.displayName}}</span> &nbsp;
          <span *ngIf="menu.children" class="fa fa-caret-down fa-2x pull-right" [@indicatorRotate]="expanded ? 'expanded': 'collapsed'">
          </span>
        </a>
        <ul *ngIf="menu.children && expanded" id="nav{{menu.id}}">
          <ng-container *ngTemplateOutlet="recursiveMenu; context:{ $implicit: menu.children }"></ng-container>
        </ul>
      </li>
    </ul>
  </ng-template>
</div>

请帮助这里是代码stackblitz 输出。让我知道我在哪里做错了。

标签: htmlcssangularrecursion

解决方案


当您展开父项时,所有子菜单项都会展开,因为您正在维护一个通用/单个标志来检查菜单是否处于展开状态。因此,当您展开父项时,展开标志设置为 true,并且您的所有菜单项也会展开。因此,您可以在地图中为每个项目维护一个标志,而不是维护一个通用标志。您可以在菜单列表中添加 id 属性:

navItems: INavItem[] = [
    {
      id: 1,
      displayName: 'Home',
      iconName: 'fa-home fa-lg p-2',
      route: 'home'
    },
    {
      displayName: 'Settings',
      id: 2,
      iconName: 'fa-cog',
      children: [
        {
          displayName: 'Navigation Management',
          iconName: 'fa-sliders',
          id: 3,
          children: [
            {
              displayName: 'Navigation & Form Mapping',
              id: 4,
              iconName: 'fa-handshake-o',
              route: 'navigation-form-mapping'
            }]
    }]
}]

您可以将使用扩展为键值对的映射,将 onItemSelected 函数更新为:

onItemSelected(item: INavItem) {
    if (item.children && item.children.length) {
      this.expanded[item.id] = !this.expanded[item.id];
    }
}

您的 html 可以更新为:

 <span *ngIf="menu.children" class="fa fa-caret-down fa-2x pull-right" [@indicatorRotate]="expanded[menu.id] ? 'expanded': 'collapsed'">
 </span>
 <ul *ngIf="menu.children && expanded[menu.id]" id="nav{{menu.id}}">
      <ng-container *ngTemplateOutlet="recursiveMenu; context:{ $implicit: menu.children }"></ng-container>
 </ul>

工作演示


推荐阅读