【问题标题】:How to add DOM Elements (Angular directives) via jQuery's .append()?如何通过 jQuery 的 .append() 添加 DOM 元素(Angular 指令)?
【发布时间】:2013-12-02 06:41:26
【问题描述】:

有没有什么方法可以使用像 append() 这样的 jQuery 方法添加一个 Angular 指令元素,并让 Angular 进行编译/链接以使其工作,就像你首先包含该指令一样?

例子:

app.directive('myAngularDirective', [function () {
    ...
    // Lots of stuff in here; works when used normally but not when added via jQuery
});

$("body").append("<my-angular-directive />");

它目前只是附加了一个名为“my-angular-directive”的空 DOM 元素,但 Angular 并没有发挥作用并发挥它的魔力。

【问题讨论】:

  • 我怀疑你需要告诉 Angular 新元素现在存在,因为如果你动态添加它,它可能不存在于 doc Ready 中

标签: jquery angularjs


【解决方案1】:

试试这个

angular.element($("#appendToDiv")).append($compile("<my-angular-directive />")($scope));

【讨论】:

    【解决方案2】:

    接受的答案没有提供完整的示例,这是一个:

    https://codepen.io/rhinojosahdz/pen/ZpGLZG

    <body ng-app="app" ng-controller="Ctrl1 as ctrl1">
    </body>
    <script>
    angular.module('app',[])
    .controller('Ctrl1', ['$scope', '$compile', function($scope, $compile){
        var vm = this;
        vm.x = 123;
        $('body').append($compile("<hola x='ctrl1.x' />")($scope));
    }])
    .directive('hola', function(){
        return {
            template: '<div ng-click="vm.alertXFromGivenScope()">click me!</div>'
            ,scope: {
                x : '='
            }
            ,controller: function(){
                var vm = this;
                vm.alertXFromGivenScope = function(){
                    alert(vm.x);                
                };
            }
            ,controllerAs: 'vm'
            ,bindToController: true
        }
    })
    <script>
    

    【讨论】:

      【解决方案3】:

      一个完整的例子,来自the Angular documentation

      // Angular boilerplate
      var app = angular.module("myApp", []);
      app.controller("MyCtrl", function($scope) {
        $scope.content = {
          label: "hello, world!",
        };
      });
      
      // Wrap the example in a timeout so it doesn't get executed when Angular
      // is first started.
      setTimeout(function() {
        // The new element to be added
        var $div = $("<div ng-controller='MyCtrl'>new: {{content.label}}</div>");
        
        // The parent of the new element
        var $target = $("[ng-app]");
      
        angular.element($target).injector().invoke(function($compile) {
          var $scope = angular.element($target).scope();
          $target.append($compile($div)($scope));
          // Finally, refresh the watch expressions in the new element
          $scope.$apply();
        });
      }, 100);
      <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
      <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
      
      <div ng-app="myApp">
         <div ng-controller="MyCtrl">old: {{content.label}}</div>
      </div>

      【讨论】:

      • 对我来说似乎是最简单的解决方案。
      • OP 要求指令。
      【解决方案4】:

      理想情况下,您应该避免这样做。

      但是,如果您真的、真的、真的需要,那么您可以注入并使用$compile service,后跟element.append

      如果您的指令不需要访问特定范围,那么您甚至可以在应用程序的run 函数中将$compile$rootScope 服务分配给window模块,然后通过创建一个新的scope ($rootScope.new()) 从角度上下文之外使用它们,并使用$rootScope.apply() 包装元素的附加。

      【讨论】:

      • 为什么要避免动态添加元素?有其他选择吗?
      • 我猜你会在视图中使用该指令并使用 ui.router 之类的东西将视图放在 ui-view 中
      【解决方案5】:

      如果可以的话,你真的想避免做任何 jquery,但不久前我遇到了一个类似的问题,这里是 my question 和应该能够帮助你的正确答案。简短的回答是使用 $compile。

      【讨论】:

        【解决方案6】:

        正确的方法是使用:$compile,如果你的指令返回:directive definition object(顺便说一句,推荐的方法)你可以调用link函数(注入@例如 987654324@)。

        $('body').append($compile("<my-angular-directive />")(scope));
        scope.$apply(); 
        

        【讨论】:

        • 您的代码不完整。能否请您发布一个 jsfiddle 版本的代码。
        • 如果您已经在$digest 循环中怎么办?也许改用$timeout
        猜你喜欢
        • 2019-03-12
        • 2012-10-01
        • 2014-09-19
        • 1970-01-01
        • 2013-10-26
        • 2014-03-08
        • 2017-12-18
        • 1970-01-01
        • 2011-05-09
        相关资源
        最近更新 更多