【问题标题】:Accessing Scope from Directive Controller从指令控制器访问范围
【发布时间】:2013-05-30 18:34:57
【问题描述】:

从指令中定义的控制器访问范围变量的正确方法是什么?

例如,我想让 click 事件调用父指令控制器上的函数。在父指令中,我希望控制器能够访问“常量”、FOO_VIEW、BAR_VIEW、BAM_VIEW

将这些常量放在顶级控制器中是否更有意义,在本例中为 SearchCtrl(未显示)?

指令:

.directive('usersAndApps', function() {
        return {
            restrict:'EA',
            scope: true,
            controller: function() {
                this.toggleView = function(viewName){
                    console.log('show view ' + viewName);
                }
            },
            link:function(scope, elem, attrs) {
                scope.FOO_VIEW = 'fooView';
                scope.BAR_VIEW = 'barView';
                scope.BAM_VIEW = 'bamView';
            }
        }
    }).directive('usersAndAppsNav', function() {
        return {
            restrict: 'AE',
            require:'^?usersAndApps',
            replace:true,
            scope:true,
            link:function(scope,elem,attrs,usersAndAppsCtrl){
                scope.toggleView = function(viewName){
                    usersAndAppsCtrl.toggleView(viewName);
                }
            },
            templateUrl:'partials/usersAndApps/throwmeaway'
        }
    });

模板:

<div>
    <button class="btn btn-large btn-primary" ng-click="toggleView(FOO_VIEW)">Foo View</button>
    <button class="btn btn-large btn-primary" ng-click="toggleView(BAR_VIEW)">Bar View</button>
    <button class="btn btn-large btn-primary" ng-click="toggleView(BAM_VIEW)">Bam View</button>
</div>

指令和嵌套(子)指令:

<div ng-controller="SearchCtrl">
    <users-and-apps>
        <users-and-apps-nav></users-and-apps-nav>
    </users-and-apps>
</div>

【问题讨论】:

    标签: angularjs angularjs-directive


    【解决方案1】:

    您所拥有的一切都很好,但是由于您没有在 usersAndAppsNav 中使用隔离或转导范围,因此您无需在 usersAndApps 上定义控制器 API — 您可以简单地利用 prototypal scope inheritance 来访问方法toggleViewParent,如果你在与usersAndApps关联的范围内定义它:

    .directive('usersAndApps', function() {
    return {
        restrict:'EA',
        scope: true,
        link:function(scope, elem, attrs) {
            scope.FOO_VIEW = 'fooView';
            ...
            scope.toggleViewParent = function(viewName){
                console.log('show view ' + viewName);
            }
        }
    }
    }).directive('usersAndAppsNav', function() {
    return {
        restrict: 'AE',
        replace:true,
        scope:true,
        link:function(scope,elem,attrs) {
            scope.toggleView = function(viewName){
                scope.toggleViewParent(viewName);
            }
        },
       templateUrl: ...
    }
    });
    

    Fiddle.

    请注意,当您在模板中编写ng-click="toggleView(FOO_VIEW)" 时,您已经在使用原型继承——FOO_VIEW 评估为fooView 的唯一原因是因为原型继承——FOO_VIEW 是在与@987654332 关联的范围内定义的@(作用域 004),子作用域(作用域 005)通过继承链/查找(即,沿着虚线)找到它。

    【讨论】:

      【解决方案2】:

      看看这个涵盖该主题的快速视频教程@http://www.egghead.io/video/LJmZaxuxlRc

      他还有许多其他非常棒的 AngularJS 教程视频链接到该网站。

      【讨论】:

      • 这些视频很棒,你是对的。我正在寻找更具体的东西,特别是因为这个特殊问题涉及到操作 DOM,这应该在指令级别完成。
      • 我链接到的视频讨论了调用控制器方法的指令 - 这不是您要问的吗?他还有另一个关于指令的视频 -> 指令通信@egghead.io/video/rzMrBIVuxgM
      • 不是我想要的。我对与指令的控制器对话的指令更感兴趣(公开为 API 以供其他指令通过 require:'^?myDirective 与之对话)。请参阅上面的代码片段。再次感谢您的建议。我实际上正在弄清楚一些事情,并且在某些时候我将有足够的信息来回答这个问题(在蛋头视频等的帮助下)。再次感谢!
      猜你喜欢
      • 2016-03-28
      • 2015-09-09
      • 2018-08-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多