角度指令单向绑定控制器中的变化值

angular directive one way binding changing value in controller

本文关键字:变化 控制器 绑定 指令      更新时间:2023-09-26

我使用从控制器到指令的角度单向绑定。当我更新指令中的值时,它不应该更新控制器中的值。但它是双向绑定的。有人能找到我的错误吗。

angular.module("myApp",[])  
  .directive("myDirective",['$timeout', function ($timeout) {
    return {
      scope: {myValue: "&myAttribute"},
      template: '<input type="text" ng-model="myValue().name">',
      link: function (scope, iElm, iAttrs) {
        var x = scope.myValue();
        console.log(x);
        $timeout(function(){
          x.name= "directive";
        },4000);
      }
    };
  }]).controller("myController", function ($scope, $timeout) {
    $scope.someObject = {name: "test"};
    $timeout(function(){
      $scope.someObject.name= "controller";
    },2000);
});

http://plnkr.co/edit/9wihx1VYgKoTK00awN67?p=preview

我不确定是否有更简单的方法,但您可以在隔离范围中使用带有@绑定的单向绑定,并在属性上添加一个观察者,以便在更改时更新指令中的对象。

@绑定从父级获取数据,并将它们作为字符串传递给指令。要创建对象,必须使用scope.$eval(interpolatedStrValue)

(Ampersand绑定没有像另一个答案中提到的那样工作,因为getter正在传递对父对象的引用。因此任何更改都会更新父对象。)

请看下面的演示或这个小提琴。

angular.module('demoApp', [])
	.directive('oneWay', OneWay)
  .controller('mainController', MainController);
  
function OneWay($timeout, $parse) {
	return {
  	scope: {
    	myValue: '@myAttribute'
    },
  	template: '<input type="text" ng-model="myValue.name"/>',
    link: function(scope, element, attrs) {
    	console.log('link', scope.myValue);
      attrs.$observe('myAttribute', function(myValStr) {
      	scope.myValue = scope.$eval(myValStr);
        console.log('controller myValue obj', scope.myValue);
      });
      
      $timeout(function() {
      	console.log('change dir');
        scope.myValue.name = "directive changed";
       }, 4000);
      
      
    }
  }
}
function MainController($scope, $timeout) {
	$scope.testObj = {
  	name: 'before mod.'
  };
  
  $timeout(function() {
  	$scope.testObj.name = 'Controller modify';
  }, 2000);
  
  $timeout(function() {
  	$scope.testObj.name = '2nd Controller modify';
  }, 8000);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.4.9/angular.js"></script>
<div ng-app="demoApp" ng-controller="mainController">
  Controller: {{testObj.name}}<br/>
  Directive: <one-way my-attribute="{{testObj}}"/>
</div>

您应该使用"@"而不是下面的"&"

scope: {myValue: "@myAttribute"}

以下链接解释

&vs@和=在angularJS 中

根据文档(对于1.xx)https://docs.angularjs.org/api/ng/service/$compile ampersand将返回在父作用域(getter)中执行的属性表达式的值,在本例中,它是一个对象引用,对任何对象属性的更改都将反映在两者中。

不过,对指令作用域中myValue的更改不会影响父作用域。