这是我的父母控制器,我在那里听取事件
app.controller("SectionLayoutController", function($scope) {
$scope.$on("sectionLayout.doAction", function(e, options) {
// do some stuff
});
});
在我的孩子控制器中,我这样做
$scope.$emit("sectionLayout.doAction", { someOption: "something" });
事件应该在父控制器中触发,但它不是。在发出事件之前,我确实检查了我的子控制器范围的内容(使用console.log),并且该事件的监听器确实存在于其父事件之一中。
也许是因为子控制器的范围不是正在监听事件的范围的直接子节点?这不是一个真正的关键问题,因为我可以用
替换该行$rootScope.$broadcast("sectionLayout.doAction", { someOption: "something" });
并且它工作正常,但我仍然很好奇为什么$ scope。$ emit不工作(它确实在某个时候工作,它只是随机停止)。
(Angular版本1.2.16)
答案 0 :(得分:1)
修改强>
问题似乎是angular.js中的一个错误,而不是ui-router(它已经被报告并计划在版本1.3 https://github.com/angular/angular.js/issues/5489中修复)。在指令中使用ng-transclude似乎为指令创建了一个兄弟范围,这使得这种层次结构(使用我的第一个plunker示例):http://i.imgur.com/4OUxJSP.png。
所以是的,我想现在我将使用$ rootScope。$ broadcast
好的,从我发现的情况来看,这是ui-router的错误(忘了提到我正在使用它,哎呀)。
如果子路径的ui-view位于transcluded指令内,事件将卡在那里。这是该行动中http://plnkr.co/edit/zgqAPiDbB2LUtwJaeHhN?p=preview的一个漏洞。 Dummy控制器使用sectionLayout指令并且ui-view被转换(正如您在dummy.html中看到的那样)。
<!-- dummy.html -->
<div section-layout="layout">
<!-- transcluded stuff -->
<div ui-view></div>
</div>
<!-- sectionlayout.html -->
<div>
<p>Section Layout for {{layout.title}}</p>
<p ng-repeat="r in recieves">{{r.message}}</p>
<div ng-transclude style="background-color: #EEE;"></div>
</div>
这是$ scope。$ emit确实起作用的另一个plunkr,唯一的区别是ui-view直接在sectionlayout.html内,而不是在指令http://plnkr.co/edit/mVftwkZrynkF6KanE4zV?p=preview中被转换。
<!-- dummy.html -->
<div section-layout="layout"></div>
<!-- sectionlayout.html -->
<div>
<p>Section Layout for {{layout.title}}</p>
<p ng-repeat="r in recieves">{{r.message}}</p>
<div ui-view style="background-color: #EEE;"></div>
</div>
这是一个完全不同的plunkr,我不使用ui-router,但它仍然是一样的。在父级中使用指令,其中侦听事件,并且子控制器在指令中被转换。在这一个中,$ scope。$ emit和$ rootScope。$ broadcast工作正常,所以它似乎是ui-router中转换的ui-views的错误。 http://plnkr.co/edit/Iz5YcbMiTzrXQ6bJMskK?p=preview
<div ng-controller="ParentController">
<p>Parent Controller</p>
<p ng-repeat="r in recieves">{{r.message}}</p>
<div my-directive>
<div ng-controller="ChildController" style="background-color: #EEE;">
<p>Child Controller</p>
<button ng-click="tryEmit()">$scope.$emit</button>
<button ng-click="tryBroadcast()">$rootScope.$broadcast</button>
</div>
</div>
</div>
我会在他们的github页面上报告这个错误