AngularJS - 递归指令不起作用(无限循环)

时间:2015-11-13 14:30:09

标签: javascript angularjs angularjs-directive ecmascript-6

我需要创建一个能够处理多个(非确切数字)级别子菜单的菜单

MainMenu.js(包含所有菜单项的菜单属性)

class MainMenu {

    // @ngInject
    constructor() {


        this.menu = {
            name: 'Main menu',
            list: [
               {
                name: 'Sub menu lvl 1',
                list: [
                    {
                     name: 'Sub menu lvl 2',
                     list: [
                        {
                         name: 'Sub menu lvl 3'
                        } 
                     ]
                    }
                ]
               } 
            ]
        }



    }
}

export default function () {
    return {
        scope: {},
        templateUrl: 'path/to/MainMenu.tpl.html',
        replace: true,
        controller: MainMenu,
        controllerAs: 'mainMenuCtrl'
    };
};

这是模板html文件(MainMenu.tpl.html)

<div>
    <nav id="menu" class="cm-menuwrapper">
        <ul class="cm-menu">
            <li ng-repeat="menuItem in mainMenuCtrl.menu.list">
                <a class="cursor-pointer" ng-click="mainMenuCtrl.someMethod(menuItem)"><span>{{menuItem.name}}</span></a>
                <sub-menu menu-item="menuItem" ng-if="menuItem.list"></sub-menu>
            </li>
        </ul>
    </nav>
</div>

SubMenu.js

class SubMenu {

    // @ngInject
    constructor() {

    }


}

export default function () {
    return {
        scope: {},
        templateUrl: 'path/to/SubMenu.tpl.html',
        replace: true,
        controller: SubMenu,
        controllerAs: 'subMenuCtrl',
        bindToController: {
            menuItem : "="
        }
    };
};

子菜单html模板文件(SubMenu.tpl.html)

<ul class="cm-submenu">
    <li ng-repeat="submenu in subMenuCtrl.menuItem.list" ng-class="submenu.itemClass">
        <a class="cursor-pointer" ng-click="subMenuCtrl.someMethod(submenu)"><span>{{submenu.name}}</span></a>
        <sub-menu menu-item="submenu" ng-if="submenu.list"></sub-menu>
    </li>
</ul>

正如您所看到的,我已将<sub-menu ....> directivve置于SubMenu.tpl.html中,这似乎导致某种无限循环。 浏览器卡在空白页面上,消耗内存和CPU。

对此问题的任何建议?

1 个答案:

答案 0 :(得分:1)

你必须在Angular的初始编译中隐藏你的子指令。在链接函数中动态添加递归子菜单。这是修改后的SubMenu.js:

/* @ngInject */ 
function submenuDirective($compile) {
  return {
    scope: {},
    templateUrl: 'path/to/SubMenu.tpl.html',
    replace: true,
    controller: SubMenu,
    controllerAs: 'subMenuCtrl',
    bindToController: {
        menuItem : "="
    },
    link: function(scope, elm) {
       const submenuNode = elm.find('.cm-submenu-list');
       submenuNode.append('<sub-menu menu-item="submenu" ng-if="submenu.list"></sub-menu>');
       $compile(submenuNode)(scope);
    }
  };
};

不要忘记将包装器添加到模板中:

<ul class="cm-submenu">
  <li ng-repeat="submenu in subMenuCtrl.menuItem.list" ng-class="submenu.itemClass">
    <a class="cursor-pointer" ng-click="subMenuCtrl.someMethod(submenu)"><span>{{submenu.name}}</span></a>
    <!-- submenu items will be rendered here later -->
    <div class="cm-submenu-list"></div>
  </li>
</ul>