angularjs指令第二次运行控制器

时间:2016-09-13 10:43:58

标签: javascript angularjs angularjs-directive

我有一个带有嵌套ui-view的angularJS应用程序(简化版):

的index.html

<html ng-app="admineConsoleApp">
<head> </head>
<body>
  <div>
      <div ui-view=""></div>
  </div>
</body>
</html>

我的主要包装器注入其他视图:

main.html中

<div id="page-wrapper">
    <div ui-view=""></div>
</div>

我的配置:

    ....
    $urlRouterProvider.otherwise('/');
    $urlRouterProvider.when('', '/');

    $stateProvider
        .state('dashboard', {
            url: '',
            templateUrl: 'views/main.html'
        })
        .state('dashboard.home', {
            url: '/',
            controller: 'HomeController as home',
            templateUrl: 'views/home.html'
        })
        ....

在我使用指令处理模式弹出之前,一切正常。这是我的指示:

subscription.directive.js

angular
    .module('adminConsoleApp')
    .directive('modalDetail', modalDetail);

function modalDetail() {
    var directive = {
        restrict: 'EA',
        scope: {
            modalContainer: '=?',
            callbackbuttonleft: '&ngClickLeftButton',
            callbackbuttonright: '&ngClickRightButton'
        },
        templateUrl: 'scripts/directives/subscription/modal.subscription.template.html',
        transclude: true,
        controllerAs: 'home',
        controller: 'HomeController',
        bindToController: true
    };

    return directive;

我还注意到我的控制器内的每个函数实际上都运行了两次。当然我需要controllerAs,因为stateProvider引用了我的控制器的别名,因为指令模板使用了控制器的别名。 使用此配置,HomeController将运行两次,但如果我删除controllerAs该指令不起作用(当然),但控制器只运行一次。这是我的控制器实例的console.log(this);

console log for 'this' instance

如果您注意到,第一个this引用了我的初始控制器实例。第二个只是一个带有指令引用的对象。 我已经遵循了最常见的解决方案,如:

  • 删除ng-controller元素
  • 中的div个参数
  • 有/无手动引导程序
  • 检查多指令实例或参考

我唯一没有尝试的是将指令模态的控制器逻辑直接包装在指令本身内(我的意思是:避免使用controller: HomeController并定义一个新的)。但我想知道我是否可以保留实际情况并应用解决方案以避免控制器运行两次。

注意:这种行为很烦人,但事情很好(第二次调用之后)。我只是想知道一个很好的解决方案,以确保指令不会运行控制器两次。

2 个答案:

答案 0 :(得分:1)

在角度中,同一控制器的所有使用都是独立的实例。你的控制器功能只是控制器构造函数。

所有代码,应该只运行一次,你应该放置运行和配置块(以及ub路由器和服务的mb解析(使用任何类型的缓存))。

在您的情况下,无法避免控制器代码运行两次。

答案 1 :(得分:0)

已解决:只需覆盖家庭控制器内部指令并使用不同的控制器。像这样:

function modalDetail() {
    var directive = {
        restrict: 'EA',
        scope: {
            modalContainer: '=?',
            callbackbuttonleft: '&ngClickLeftButton',
            callbackbuttonright: '&ngClickRightButton'
        },
        templateUrl: 'scripts/directives/subscription/modal.subscription.template.html',
        transclude: true,
        controller: function() {
           // your implementation here
        }
    };

    return directive;

}

当然,更改params模板引用以使其有效。