angularjs指令:链接和控制器之间如何通信?

时间:2015-06-28 15:51:46

标签: javascript angularjs angularjs-directive dom-manipulation

我有一个指令,其'config'属性值我需要在我的指令控制器中访问。 由于首先执行控制器构造函数,因此可以从控制器到链接进行通信,但反之亦然。 应该是实现这一目标的最佳方法是什么? 我考虑过以下方法

1)将变量添加到范围 - 在我看来,这会污染范围,使得变量可以在范围被共享的其他地方访问。

2)使用$broadcast 再次出现与上述相同的问题

3)在控制器的this上传递一个回调函数,并以config为参数从链接函数中调用它

4)通过服务传递价值 - 在我的情况下,我有多个这样的指令需要通过此服务传递日期

或者是否有一些更好的方法,我错过了这样做?

module.directive('myDirective',function(){

return{
 restrict:'E',
 templateUrl:'path/to/html',
 link:function(scope,iElement,iAttrs,controller){

  var config=iAttrs.config;
//How to access this value inside the directive controller?

},
controller:function($scope){
//the directive attribute 'config' is required here for some larger computations which are not
//manipulating the DOM and hence should be seperated from the link function
})

1 个答案:

答案 0 :(得分:3)

在那里你可以使用隔离范围概念,在你的控制器内创建隔离范围&不会从其父范围原型继承。为此,您需要在指令选项中使用scope: { ... }。有三个选项可以通过属性

在指令中传递范围值
  1. @:单向绑定
  2. =:双向绑定
  3. &:表达式
  4. 在你的情况下,前两种情况会很好,取决于你需要使用哪种情况。如果你只是想在这种情况下将范围变量的值传递给指令,你可以使用第一种方法,@单向绑定。

    如果你想更新指令和控制器中的变量,只需要双向绑定,那么你需要使用=

    我认为=适合您的情况,因此您应该选择=

    <强>标记

    <my-directive config="config"></my-directive>
    

    <强>指令

    app.directive('myDirective', function() {
      return {
        restrict: 'E',
        scope: {
          config: '='
        },
        templateUrl: 'path/to/abc.html',
        link: function(scope, iElement, iAttrs, controller) {
          //here it will be access as scope.config
          console.log(scope.config);
        },
        controller: function($scope) {
          console.log($scope.config); //here also it would be available inisde scope
          //you could put a watch to detect a changes on config
        }
      }
    });
    

    Demo Plunkr

    <强>更新

    由于config值来自{{}}这样的表达式,因此我们可以通过将[**$observe**][2]放在$attrs上来获取控件内部的更改。为此,您需要在控制器上注入$attrs依赖项,它将为您提供指令元素上可用的所有属性集合。在相同的$attrs对象上,我们将$observe$watch的内容相同,后者执行脏检查&amp;如果价值得到改变,它就会触发该手表。

    <强>指令

    app.directive('myDirective', function() {
      return {
        restrict: 'E',
        templateUrl: 'path/to/abc.html',
        link: function(scope, iElement, iAttrs, controller) {
          //here it will be access as scope.config
          console.log(scope.config);
        },
        controller: function($scope,$attrs) {
          //you could put a watch to detect a changes on config
          $attrs.$observe('config', function(newV){
            console.log(newV);
          })
        }
      }
    });
    

    Updated Demo