vue.js $watch 对象数组
vue.js $watch array of objects
mounted: function() {
this.$watch('things', function(){console.log('a thing changed')}, true);
}
things
是一个对象数组 [{foo:1}, {foo:2}]
$watch
检测何时添加或删除对象,但不检测对象上的值何时更改。我该怎么做?
您应该传递一个对象而不是布尔值作为 options
,因此:
mounted: function () {
this.$watch('things', function () {
console.log('a thing changed')
}, {deep:true})
}
或者您可以像这样将观察者设置到 vue
实例中:
new Vue({
...
watch: {
things: {
handler: function (val, oldVal) {
console.log('a thing changed')
},
deep: true
}
},
...
})
如果有人需要获取数组中更改的项目,请检查它:
post示例代码:
new Vue({
...
watch: {
things: {
handler: function (val, oldVal) {
var vm = this;
val.filter( function( p, idx ) {
return Object.keys(p).some( function( prop ) {
var diff = p[prop] !== vm.clonethings[idx][prop];
if(diff) {
p.changed = true;
}
})
});
},
deep: true
}
},
...
})
您可以使用 $watch('arr.0', () => {})
或 $watch('dict.keyName', () => {})
独立观察数组或字典中的每个元素的变化
来自 https://vuejs.org/v2/api/#vm-watch:
Note: when mutating (rather than replacing) an Object or an Array, the
old value will be the same as new value because they reference the
same Object/Array. Vue doesn’t keep a copy of the pre-mutate value.
但是,您可以独立地迭代 dict/array 和 $watch 每个项目。 IE。 $watch('foo.bar')
- 这会监视对象 'foo'.
的 属性 'bar' 中的变化
在此示例中,我们查看 arr_of_numbers 中的所有项目,以及 arr_of_objects 中所有项目的 'foo' 属性:
mounted() {
this.arr_of_numbers.forEach( (index, val) => {
this.$watch(['arr_of_numbers', index].join('.'), (newVal, oldVal) => {
console.info("arr_of_numbers", newVal, oldVal);
});
});
for (let index in this.arr_of_objects) {
this.$watch(['arr_of_objects', index, 'foo'].join('.'), (newVal, oldVal) => {
console.info("arr_of_objects", this.arr_of_objects[index], newVal, oldVal);
});
}
},
data() {
return {
arr_of_numbers: [0, 1, 2, 3],
arr_of_objects: [{foo: 'foo'}, {foo:'bar'}]
}
}
有一种无需 deep-watch 即可查看数组项的更简单方法:使用计算值
{
el: "#app",
data () {
return {
list: [{a: 0}],
calls: 0,
changes: 0,
}
},
computed: {
copy () { return this.list.slice() },
},
watch: {
copy (a, b) {
this.calls ++
if (a.length !== b.length) return this.onChange()
for (let i=0; i<a.length; i++) {
if (a[i] !== b[i]) return this.onChange()
}
}
},
methods: {
onChange () {
console.log('change')
this.changes ++
},
addItem () { this.list.push({a: 0}) },
incrItem (i) { this.list[i].a ++ },
removeItem(i) { this.list.splice(i, 1) }
}
}
https://jsfiddle.net/aurelienlt89/x2kca57e/15/
我们的想法是构建一个计算值 copy
,它具有我们想要检查的内容。计算值很神奇,只会让观察者关注实际读取的属性(这里,list
的项目在 list.slice()
中读取)。 copy
观察器中的检查实际上几乎没有用(除了奇怪的极端情况),因为计算值已经非常精确。
mounted: function() {
this.$watch('things', function(){console.log('a thing changed')}, true);
}
things
是一个对象数组 [{foo:1}, {foo:2}]
$watch
检测何时添加或删除对象,但不检测对象上的值何时更改。我该怎么做?
您应该传递一个对象而不是布尔值作为 options
,因此:
mounted: function () {
this.$watch('things', function () {
console.log('a thing changed')
}, {deep:true})
}
或者您可以像这样将观察者设置到 vue
实例中:
new Vue({
...
watch: {
things: {
handler: function (val, oldVal) {
console.log('a thing changed')
},
deep: true
}
},
...
})
如果有人需要获取数组中更改的项目,请检查它:
post示例代码:
new Vue({
...
watch: {
things: {
handler: function (val, oldVal) {
var vm = this;
val.filter( function( p, idx ) {
return Object.keys(p).some( function( prop ) {
var diff = p[prop] !== vm.clonethings[idx][prop];
if(diff) {
p.changed = true;
}
})
});
},
deep: true
}
},
...
})
您可以使用 $watch('arr.0', () => {})
或 $watch('dict.keyName', () => {})
来自 https://vuejs.org/v2/api/#vm-watch:
Note: when mutating (rather than replacing) an Object or an Array, the old value will be the same as new value because they reference the same Object/Array. Vue doesn’t keep a copy of the pre-mutate value.
但是,您可以独立地迭代 dict/array 和 $watch 每个项目。 IE。 $watch('foo.bar')
- 这会监视对象 'foo'.
在此示例中,我们查看 arr_of_numbers 中的所有项目,以及 arr_of_objects 中所有项目的 'foo' 属性:
mounted() {
this.arr_of_numbers.forEach( (index, val) => {
this.$watch(['arr_of_numbers', index].join('.'), (newVal, oldVal) => {
console.info("arr_of_numbers", newVal, oldVal);
});
});
for (let index in this.arr_of_objects) {
this.$watch(['arr_of_objects', index, 'foo'].join('.'), (newVal, oldVal) => {
console.info("arr_of_objects", this.arr_of_objects[index], newVal, oldVal);
});
}
},
data() {
return {
arr_of_numbers: [0, 1, 2, 3],
arr_of_objects: [{foo: 'foo'}, {foo:'bar'}]
}
}
有一种无需 deep-watch 即可查看数组项的更简单方法:使用计算值
{
el: "#app",
data () {
return {
list: [{a: 0}],
calls: 0,
changes: 0,
}
},
computed: {
copy () { return this.list.slice() },
},
watch: {
copy (a, b) {
this.calls ++
if (a.length !== b.length) return this.onChange()
for (let i=0; i<a.length; i++) {
if (a[i] !== b[i]) return this.onChange()
}
}
},
methods: {
onChange () {
console.log('change')
this.changes ++
},
addItem () { this.list.push({a: 0}) },
incrItem (i) { this.list[i].a ++ },
removeItem(i) { this.list.splice(i, 1) }
}
}
https://jsfiddle.net/aurelienlt89/x2kca57e/15/
我们的想法是构建一个计算值 copy
,它具有我们想要检查的内容。计算值很神奇,只会让观察者关注实际读取的属性(这里,list
的项目在 list.slice()
中读取)。 copy
观察器中的检查实际上几乎没有用(除了奇怪的极端情况),因为计算值已经非常精确。