如果您更改正在观看$watch
次的变量,我希望x
能够触发x
次。在我放在一起的一个小例子中,我将变量$scope.foo
的值改为3次,但关联的$watch
只运行一次......
<html>
<head>
<title></title>
<script src="https://code.angularjs.org/1.3.8/angular.js"></script>
</head>
<body ng-app='myApp'>
<div ng-controller='MyCtrl'></div>
<script>
var myApp = angular.module('myApp', []);
myApp.controller('MyCtrl', function($scope) {
$scope.$watch('foo', function(oldVal, newVal) {
console.log(oldVal, newVal);
});
$scope.foo = "foo";
$scope.foo = "bar";
$scope.foo = "baz";
});
</script>
</body>
</html>
是否有人能够解释这是什么原因,或者我可以采取不同的方法来获得理想的结果?
我期待以下控制台输出:
undefined foo
foo bar
bar baz
但是......
baz baz
myApp.controller('MyCtrl', function($scope, $timeout) {
$scope.$watch('foo', function() {
$scope.bar = 'bar';
});
$scope.foo = "foo";
// now the value of $scope.foo has changed, I was expecting the $watch to have run at this point.
// Apparently is has not because $scope.bar is still undefined. Accessing $scope.bar in a $timeout works, but is there a better way?
console.log($scope.bar)
});
答案 0 :(得分:2)
$watch
只会在每个角度$ digest周期中触发一次! (如果观看属性 - 最简单的情况)。
您对foo
所做的三项更改都发生在同一周期内。而角度将比较循环前和循环后的值。
根据您的情况,您需要触发一个新周期,例如,更改$timeout
内的值。
修改强>
对于你的例子,你可以做这样的事情
myApp.controller('MyCtrl', function($scope) {
$scope.foo = "foo";
// run on controller init
fooWatch();
// watch for changes
$scope.$watch('foo', fooWatch);
function fooWatch() {
$scope.bar = 'bar';
}
});
答案 1 :(得分:1)
因为每次更改范围内的变量时都不会运行$digest
周期(幸运的是)。
但是当您使用$timeout
时会触发它。
你的用例是什么?
在控制器中使用$watch
进行BTW通常不是一种好的做法,而且很容易避免。
答案 2 :(得分:0)
角度变化太快,$timeout
可以正常工作:
<html>
<head>
<title></title>
<script src="https://code.angularjs.org/1.3.8/angular.js"></script>
</head>
<body ng-app='myApp'>
<div ng-controller='MyCtrl'></div>
<script>
var myApp = angular.module('myApp', []);
myApp.controller('MyCtrl', function($scope, $timeout) {
$scope.$watch('foo', function(oldVal, newVal) {
console.log(oldVal, newVal);
});
$scope.foo = "foo";
$scope.foo = "bar";
$scope.foo = "baz";
$timeout(function(){
$scope.foo = "foo";
},0)
$timeout(function(){
$scope.foo = "bar";
},0)
$timeout(function(){
$scope.foo = "baz";
},0)
});
</script>
</body>
</html>