【问题标题】:Single angular js directive and many controllers单个角度 js 指令和许多控制器
【发布时间】:2014-02-10 16:52:01
【问题描述】:

我想知道如何在模板元素的 ng-click 事件上调用驻留在控制器中的函数。我必须在许多页面中使用此指令。因此我需要在各个控制器页面中处理单击事件。下面的代码调用驻留在指令中的单击函数(moreitemdetails)。我尝试将范围设置为 moreitemdetails: '=' 。它也不起作用。

我一直在使用指令

app.directive('groceryList', function){

    return {
        restrict: 'E',
        scope: {
            array: '=',
            listItemClick:'&',
            moreitemdetails: '&', 
        },
        templateUrl: 'list.html',

        link: function(scope, element, attrs) {
            scope.label = attrs.label;
            scope.listItemClick=function(e){
                $(e.currentTarget).find('.next-items').slideToggle('fast');   
            }
             scope.moreitemdetails=function(name,type){
               //other code
             }
        }
    };
});

指令的调用是

<grocery-list array="items"></grocery-list>

这是模板文件

<div ng-click="listItemClick($event)">
        <div>
            <div class="item">
                <span class="item-details">
                    {{array[0].Item}}

                </span>
                <span class="down-arrow"></span>
            </div>
            <div class="next-items">
                <ul>
                    <li class="item" ng-repeat="list in array">
                        <div class="item-details" ng-click="moreitemdetails(list.Name,list.Type)">{{list.Item}}</div>
                    </li> 
                </ul>
            </div>

有办法绕过去吗?

我也想知道 $location 在另一个指令中的用法。引用前面的例子(除了 moreitemdetails() 中的指令定义和操作外,其他一切都相同)

app.ui.directive('groceryList', ['$location', function(location){
return {
            restrict: 'E',
            scope: {
                array: '=',
                listItemClick:'&',
                moreitemdetails: '&', 
            },
            templateUrl: 'list.html',

            link: function(scope, element, attrs) {
                scope.label = attrs.label;
                scope.listItemClick=function(e){
                    $(e.currentTarget).find('.next-items').slideToggle('fast');   
                }
                 scope.moreitemdetails=function(name,type){
                   $location.path('/home/');
                 }
            }
        };
}]);

提前致谢

【问题讨论】:

  • 您在指令中创建了一个范围,因此您必须使用 scope.$parent 访问控制器,但这是不好的做法

标签: angularjs angularjs-directive


【解决方案1】:

所以通过声明

   scope: {
        array: '=',
        listItemClick:'&',
        moreitemdetails: '&', 
    },

您正在为您的指令创建一个隔离范围。一种解决方案可能是不在指令中声明此范围。这意味着您的 ng-click="moreitemdetails(list.Name,list.Type) 将触发您的控制器范围内的功能。

或者,您可以使用发射和侦听器。为此,您可以在指令中调用:

scope.moreitemdetails=function(name,type){
   var deets = {
       name: name,
       type: type
    };
    scope.emit('moreitemdetails',deets)
}

然后在你实现的各种控制器中:

scope.$on('moreitemdetails',function(event,details){
// do some code with your name and type
}

我不确定您想了解关于 $location 的确切信息,如果您能更具体一点,我可能会提供更多帮助。

希望这在某种程度上有所帮助!


编辑: 没有声明任何范围的指令如下所示:

 return {
    restrict: 'E',
    templateUrl: 'list.html',
    link: function(scope, element, attrs) {
        scope.label = attrs.label;
        scope.listItemClick=function(e){
            $(e.currentTarget).find('.next-items').slideToggle('fast');   
        }
         scope.moreitemdetails=function(name,type){
           //other code
         }
    }
};

【讨论】:

  • 我不知道为什么你不能只使用 ng-repeat 和通用函数名。还要参考 ui-router,因为这可能是您的应用程序/站点的重要资产。 (github.com/angular-ui/ui-router/wiki)
  • @mylescc 一种解决方案可能是不在指令中声明此范围。这意味着您的 ng-click="moreitemdetails(list.Name,list.Type) 将触发控制器范围上的功能。---您的意思是声明一个范围,如 codescope: { array: '= ', listItemClick:'&', } code 但我不确定它是否会起作用。我没有尝试过'emit'解决方案。会尝试让你知道。然后关于$location,我发布的代码碎片化我的第一篇文章没有工作,它给出了一个错误 $location is not defined。请问有什么帮助吗?
  • @Misty - 嘿,迷雾,所以我的意思是不包括任何范围的声明。因此,如果您查看对我上面答案的编辑,我并没有声明范围。这意味着您的指令将继承其父范围,因此可以调用其父控制器的任何函数。不确定我解释得很好,但这有意义吗?
  • @mylescc 是有道理的 :) 谢谢。我还没有尝试过解决方案。如果需要更多帮助,会做并抓住你:)
猜你喜欢
  • 2016-06-21
  • 2015-01-29
  • 1970-01-01
  • 1970-01-01
  • 2018-03-31
  • 1970-01-01
  • 2015-07-20
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多