参数更改时刷新角度指令


75

我有一个初始化的角度指令,如下所示:

<conversation style="height:300px" type="convo" type-id="{{some_prop}}"></conversation>

我希望它足够聪明,可以在$scope.some_prop更改时刷新指令,因为这意味着它应该显示完全不同的内容。

我已经对其进行了测试,但没有任何反应,$scope.some_prop更改时甚至没有调用链接函数。有没有办法做到这一点?

Answers:


97

链接函数仅被调用一次,因此它不会直接执行您期望的操作。您需要使用angular$watch来观看模型变量。

该手表需要在链接功能中设置。

如果将隔离范围用于指令,则范围将是

scope :{typeId:'@' }

在链接功能中,然后添加一个手表

link: function(scope, element, attrs) {
    scope.$watch("typeId",function(newValue,oldValue) {
        //This gets called when data changes.
    });
 }

如果您不使用隔离示波器,请注意 some_prop


7
我正在处理与OP类似的问题。AngularJS文档暗示使用=inscope:创建双向绑定,即子范围的更改传播到父范围,反之亦然-不是这种情况吗?我需要能够告诉指令从父控制器进行自我更新。
Eno 2015年

@Eno你明白了吗?真让我困惑!
JMK


让10000+指令的作用域启动作用域是否有害?$ watch监听布尔刷新?
莱昂佩尔蒂埃

我发现如果参数使用'=',则上述解决方案将无法正常工作,我正在对此进行调查
。– Micky

38

您想要做的是监视指令中的attribute属性。您可以使用$ observe()监视属性更改的属性,如下所示:

angular.module('myApp').directive('conversation', function() {
  return {
    restrict: 'E',
    replace: true,
    compile: function(tElement, attr) {
      attr.$observe('typeId', function(data) {
            console.log("Updated data ", data);
      }, true);

    }
  };
});

请记住,我在这里的指令中使用了'compile'函数,因为您没有提到是否有任何模型以及它是否对性能敏感。

如果您有模型,则需要将“编译”功能更改为“链接”或使用“控制器”,并监视模型更改的属性,应使用$ watch(),并使用成角的{{}}属性中的括号,例如:

<conversation style="height:300px" type="convo" type-id="some_prop"></conversation>

并在指令中:

angular.module('myApp').directive('conversation', function() {
  return {
    scope: {
      typeId: '=',
    },
    link: function(scope, elm, attr) {

      scope.$watch('typeId', function(newValue, oldValue) {
          if (newValue !== oldValue) {
            // You actions here
            console.log("I got the new value! ", newValue);
          }
      }, true);

    }
  };
});

1

我希望这将有助于从父范围重新加载/刷新指令值

<html>

        <head>
            <!-- version 1.4.5 -->
            <script src="angular.js"></script>
        </head>

        <body ng-app="app" ng-controller="Ctrl">

            <my-test reload-on="update"></my-test><br>
            <button ng-click="update = update+1;">update {{update}}</button>
        </body>
        <script>
            var app = angular.module('app', [])
            app.controller('Ctrl', function($scope) {

                $scope.update = 0;
            });
            app.directive('myTest', function() {
                return {
                    restrict: 'AE',
                    scope: {
                        reloadOn: '='
                    },
                    controller: function($scope) {
                        $scope.$watch('reloadOn', function(newVal, oldVal) {
                            //  all directive code here
                            console.log("Reloaded successfully......" + $scope.reloadOn);
                        });
                    },
                    template: '<span>  {{reloadOn}} </span>'
                }
            });
        </script>


   </html>

0
angular.module('app').directive('conversation', function() {
    return {
        restrict: 'E',
        link: function ($scope, $elm, $attr) {
            $scope.$watch("some_prop", function (newValue, oldValue) {
                  var typeId = $attr.type-id;
                  // Your logic.
            });
        }
    };
}

0

如果您使用的是AngularJS 1.5.3或更高版本,则应考虑使用组件而不是指令。它们的工作原理与指令非常相似,但是具有一些非常有用的附加功能,例如$ onChanges(changesObj)(生命周期挂钩之一),每当单向绑定更新时就会调用它。

app.component('conversation ', {
    bindings: {
    type: '@',
    typeId: '='
    },
    controller: function() {
        this.$onChanges = function(changes) {
            // check if your specific property has changed
            // that because $onChanges is fired whenever each property is changed from you parent ctrl
            if(!!changes.typeId){
                refreshYourComponent();
            }
        };
    },
    templateUrl: 'conversation .html'
});

这是用于深入了解组件的文档

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.