本文翻译自:How to deep watch an array in angularjs?
There is an array of objects in my scope, I want to watch all the values of each object. 我的范围中有一个对象数组,我想要观察每个对象的所有值。
This is my code: 这是我的代码:
function TodoCtrl($scope) {
$scope.columns = [
{ field:'title', displayName: 'TITLE'},
{ field: 'content', displayName: 'CONTENT' }
];
$scope.$watch('columns', function(newVal) {
alert('columns changed');
});
}
But when I modify the values, eg I change TITLE
to TITLE2
, the alert('columns changed')
never popped. 但是当我修改值时,例如我将TITLE
更改为TITLE2
, alert('columns changed')
从未弹出。
How to deep watch the objects inside an array? 如何深入观察数组内的对象?
There is a live demo: http://jsfiddle.net/SYx9b/ 有一个现场演示: http : //jsfiddle.net/SYx9b/
#1楼
参考:https://stackoom.com/question/zjHl/如何深度观察angularjs中的数组
#2楼
If you're going to watch only one array, you can simply use this bit of code: 如果你只想观看一个数组,你可以简单地使用这段代码:
$scope.$watch('columns', function() {
// some value in the array has changed
}, true); // watching properties
But this will not work with multiple arrays: 但这不适用于多个数组:
$scope.$watch('columns + ANOTHER_ARRAY', function() {
// will never be called when things change in columns or ANOTHER_ARRAY
}, true);
To handle this situation, I usually convert the multiple arrays I want to watch into JSON: 为了处理这种情况,我通常将我想要观看的多个数组转换为JSON:
$scope.$watch(function() {
return angular.toJson([$scope.columns, $scope.ANOTHER_ARRAY, ... ]);
},
function() {
// some value in some array has changed
}
As @jssebastian pointed out in the comments, JSON.stringify
may be preferable to angular.toJson
as it can handle members that start with '$' and possible other cases as well. 正如@jssebastian在评论中指出的那样, JSON.stringify
可能比angular.toJson
更可取,因为它可以处理以'$'开头的成员以及可能的其他情况。
#3楼
You can set the 3rd argument of $watch
to true
: 您可以将$watch
的第3个参数设置为true
:
$scope.$watch('data', function (newVal, oldVal) { /*...*/ }, true);
See https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watch 请参阅https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watch
Since Angular 1.1.x you can also use $watchCollection to watch shallow watch (just the "first level" of) the collection. 从Angular 1.1.x开始,您还可以使用$ watchCollection来观看浅表(只是“第一级”)的集合。
$scope.$watchCollection('data', function (newVal, oldVal) { /*...*/ });
See https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watchCollection 请参阅https://docs.angularjs.org/api/ng/type/$rootScope.Scope#$watchCollection
#4楼
There are performance consequences to deep-diving an object in your $watch. 在你的$ watch中深度潜水物体会产生性能影响。 Sometimes (for example, when changes are only pushes and pops), you might want to $watch an easily calculated value, such as array.length. 有时(例如,当更改只是推送和弹出时),您可能希望$观察一个容易计算的值,例如array.length。
#5楼
It's worth noting that in Angular 1.1.x and above, you can now use $watchCollection rather than $watch. 值得注意的是,在Angular 1.1.x及更高版本中,您现在可以使用$ watchCollection而不是$ watch。 Although the $watchCollection appears to create shallow watches so it won't work with arrays of objects like you expect. 虽然$ watchCollection似乎创建了浅表,但它不能像你期望的那样使用对象数组。 It can detect additions and deletions to the array, but not the properties of objects inside arrays. 它可以检测数组的添加和删除,但不能检测数组内对象的属性。
#6楼
This solution worked very well for me, i'm doing this in a directive: 这个解决方案对我很有用,我在一个指令中这样做:
scope.$watch(attrs.testWatch, function() {.....}, true); 范围。$ watch(attrs.testWatch,function(){.....},true);
the true works pretty well and react for all the chnages (add, delete, or modify a field). 真实的工作非常好,并对所有的chnages做出反应(添加,删除或修改字段)。
Here is a working plunker for play with it. 这是一个可以玩它的工作的plunker。
Deeply Watching an Array in AngularJS 在AngularJS中深入观察数组
I hope this can be useful for you. 我希望这对你有用。 If you have any questions, feel free for ask, I'll try to help :) 如果您有任何疑问,请随时提问,我会尽力帮助:)