从父指令或控制器中的指令名称数组呈现AngularJS指令

Rendering AngularJS directives from array of directive names in a parent directive or controller

本文关键字:指令 数组 AngularJS 控制器      更新时间:2023-09-26

我正在尝试基于指令名称的配置数组动态呈现指令。这在角度上可能吗?我还希望这些呈现的指令生活在一个单独的父dom元素中,而不是每个都得到一个新的包装器(就像你对ng repeat所做的那样)

http://jsfiddle.net/7Waxv/

var myApp = angular.module('myApp', []);
myApp.directive('one', function() {
    return {
        restrict: 'A',
        template: '<div>Directive one</div>'
    }
});
myApp.directive('two', function() {
    return {
        restrict: 'A',
        template: '<div>Directive two</div>'
    }
});
function MyCtrl($scope) {
    $scope.directives = ['one', 'two'];
}
<div ng-controller="MyCtrl">
    <div ng-repeat="directive in directives">
        <div {{directive}}></div>
    </div>
</div>

编辑:自从发布这篇文章以来,我也尝试过:

.directive('parentDirective', function () {
  return {
    restrict: 'A',
    replace: true,
    link: function (scope, element) {
      scope.directives = ['one', 'two'];
      for (var i = 0; i < scope.directives.length; i++) { 
        element.prepend('<div ' + scope.directives[i] + '></div>')
      }
    }
  };
});
<div parent-directive></div>

这样,预处理指令中的模板就不会被呈现。

下面是我的想法(花了很长时间)。。。不过,该解决方案非常通用,您可以随意修改$scope.directives阵列,指令将动态生成。您还可以指向当前作用域中的任何特定属性以从中检索指令列表。

演示链接

app.js

var myApp = angular.module('myApp', []);
myApp.directive('one', function() {
    return {
        restrict: 'E',
        replace: true,
        template: '<div>Directive one</div>'
    }
});
myApp.directive('two', function() {
    return {
        restrict: 'E',
        replace: true,
        template: '<div>Directive two</div>'
    }
});
myApp.directive('dynamic', function ($compile, $parse) {
  return {
    restrict: 'A',
    replace: true,
    link: function (scope, element, attr) {
      attr.$observe('dynamic', function(val) {
        element.html('');
        var directives = $parse(val)(scope);
        angular.forEach(directives, function(directive) {
          element.append($compile(directive)(scope));
        });
      });
    }
  };
});
function MyCtrl($scope) {
    $scope.directives = ['<one/>', '<two/>'];
    $scope.add = function(directive) {
        $scope.directives.push(directive);
    }
}

index.html

<div ng-controller="MyCtrl">
    <div dynamic="{{directives}}"></div>
    <button ng-click="add('<one/>')">Add One</button>
    <button ng-click="add('<two/>')">Add One</button>
</div>

因此,如果我在前缀指令上使用$compile,第二次尝试就会成功,比如:

.directive('parentDirective', function($compile)
    ....
element.prepend($compile('<div ' + scope.directives[i] + '"></div>')(scope));