与子指令范围共享范围对象

时间:2015-12-01 23:41:09

标签: javascript angularjs

我有一个父指令,它在link期间创建第三方对象的实例,并且该指令可以访问该变量。

但是,有两个限制:

  • 每页可以有多个实例,因此javascript文件顶部的单例不起作用。
  • 子指令是递归的,所以他们必须创建自己的范围。

我能想到的唯一方法是将该值作为属性传递给每个子指令。这感觉效率低下但是考虑到上述限制,我没有看到任何替代方案。

// Some imaginary third-party object
function Tree() {}

// Root directive which creates an instance of the object, links to the page, and loads the data needed.
app.directive('tree', function() {
    return {
        restrict: 'E',
        replace: true,
        template: '<div><nodes nodes="nodes"></nodes></div>',
        scope: {
          nodes: '='
        },
        link: function(scope, $element) {
           // This value needs to be accessible to all child directives
           scope.tree = new Tree();
        }
    };
});

// A directive to render an array of nodes
app.directive('nodes', function() {
    return {
        restrict: 'E',
        replace: true,
        template: '<ol>' +
            '<li ng-repeat="node in nodes track by node.id">' +
                '<node node="node"></node>' +
            '</li>' +
        '</ol>',
        scope: {
            nodes: '='
        }
    };
});

// A directive to render a single node, and recursively any child nodes
app.directive('node', ['$compile', function($compile) {
    return {
        restrict: 'E',
        replace: true,
        scope: {
            node: '='
        },
        template: '<div><span ng-bind="node.text"></span></div>',
        link: function(scope, $element) {
            if (scope.node.children && scope.node.children.length > 0) {
              console.log(scope.node.children);
                var tmpl = '<nodes nodes="node.children"></nodes>';
                var children = $compile(tmpl)(scope);
                $element.append(children);
            }

            // @todo Here's a good example of where I need access to scope.tree
        }
    };
}]);

我能想到的唯一解决方案是将tree: '='添加到scope个对象,然后将tree="tree"传递给每个孩子。

Plunker

1 个答案:

答案 0 :(得分:0)

一种解决方案是不隔离范围,这样子指令将从其父范围继承。如果父项具有scope.tree = new Tree(),则嵌套指令将继承scope.tree

但是,由于您提到每页可能有多个此实例,这意味着您可能需要一个隔离范围(这是您目前拥有的)。将数据传递到隔离范围的唯一方法是通过标记中的指令属性。

我想你回答了自己的问题:)