文章目录
- 监听属性
- 深度监听
- 监听属性和计算属性
- 使用监听属性实现
- 使用计算属性实现
监听属性
监听的属性发生变化时,会自动调用回调函数,执行相关操作。
监听属性有两种写法,如下:
-
new Vue()
中传入watch
配置。 - 通过
vm.$watch
进行监听。
看个具体的例子。
- 在new Vue()中传入watch配置。
<body>
<div id="root">
<div>今天天气很{{info}}</div><br/>
<button @click="changeWeather">切换天气</button>
</div>
<script>
Vue.config.productionTip = false;
new Vue({
el:"#root",
data:{
isHot:true
},
computed:{
info(){
return this.isHot ? "炎热" : "凉爽";
}
},
methods:{
changeWeather(){
this.isHot = !this.isHot;
}
},
watch:{
isHot:{
immediate:true,
handler(newValue,oldValue){
console.log("监听isHot:","newValue="+newValue,"oldValue="+oldValue);
}
}
}
})
</script>
</body>
如果watch isHot 时,只提供了回调函数handler,如下:
watch:{
isHot:{
handler(newValue,oldValue){
console.log("isHot:newValue="+newValue,"oldValue="+oldValue);
}
}
}
则可以简写成如下形式:
watch:{
isHot(newValue,oldValue){
console.log("isHot:newValue="+newValue,"oldValue="+oldValue);
}
}
- 通过vm.$watch进行监听。
<body>
<div id="root">
<div>今天天气很{{info}}</div><br/>
<button @click="changeWeather">切换天气</button>
</div>
<script>
Vue.config.productionTip = false;
const vm = new Vue({
el:"#root",
data:{
isHot:true
},
computed:{
info(){
return this.isHot ? "炎热" : "凉爽";
}
},
methods:{
changeWeather(){
this.isHot = !this.isHot;
}
}
})
vm.$watch("isHot",{
immediate:true,
handler(newValue,oldValue){
console.log("监听isHot:","newValue="+newValue,"oldValue="+oldValue);
}
})
</script>
</body>
如果watch isHot时,只提供了handler,如下:
vm.$watch("isHot",{
handler(newValue,oldValue){
console.log("isHot:newValue="+newValue,"oldValue="+oldValue);
}
})
则可以简写成以下形式:
vm.$watch("isHot",function(newValue,oldValue){
console.log("isHot:newValue="+newValue,"oldValue="+oldValue);
})
打开浏览器,测试下。
深度监听
<body>
<div id="root">
<div>a的值是{{numbers.a}}</div>
<button @click="numbers.a++">点我加1</button>
</div>
<script>
Vue.config.productionTip = false;
new Vue({
el:"#root",
data:{
numbers:{
a:1,
b:1
}
},
watch:{
"numbers.a":{
handler(newValue,oldValue){
console.log("a:","newValue="+newValue,"oldValue="+oldValue);
}
},
"numbers":{
deep:true,
handler(newValue,oldValue){
console.log("numbers发生了变化!");
}
}
}
})
</script>
</body>
监听多级结构的某个属性,如numbers.a
,当numbers对象的a属性发生变化时,Vue将侦听到,并执行回调handler。
监听多级结构的所有属性(深度监听),如"numbers":{deep:true}
,当numbers对象的任一属性发生变化,Vue也能侦听到,并执行回到handler。
监听属性和计算属性
使用监听属性实现
<body>
<div id="root">
姓:<input type="text" v-model="firstName" /><br/><br/>
名:<input type="text" v-model="lastName" /><br/><br/>
全名:<span>{{fullName}}</span>
</div>
<script>
new Vue({
el:"#root",
data:{
firstName:"张",
lastName:"三",
fullName:"张-三"
},
watch:{
firstName(val){
this.fullName = val + this.lastName;
},
lastName(val){
this.fullName = this.firstName + "-" + val;
}
}
})
</script>
</body>
使用计算属性实现
<body>
<div id="root">
姓:<input type="text" v-model="firstName" /><br/><br/>
名:<input type="text" v-model="lastName" /><br/><br/>
全名:<span>{{fullName}}</span>
</div>
<script>
new Vue({
el:"#root",
data:{
firstName:"张",
lastName:"三"
},
computed:{
fullName(){
return this.firstName+"-"+this.lastName;
}
}
})
</script>
</body>
可以看到:计算属性能够完成的,监听属性一定能够完成。
但,监听属性能够完成的,计算属性不一定能够完成,比如当数据变化时执行异步操作。看个具体的例子:当firstName变化时,等1秒后,fullName才变化。
<body>
<div id="root">
姓:<input type="text" v-model="firstName" /><br/><br/>
名:<input type="text" v-model="lastName" /><br/><br/>
全名:<span>{{fullName}}</span>
</div>
<script>
new Vue({
el:"#root",
data:{
firstName:"张",
lastName:"三",
fullName:"张-三"
},
watch:{
firstName(val){
setTimeout(() => {
this.fullName = val + "-" + this.lastName;
},1000);
},
lastName(val){
this.fullName = this.firstName + "-" + val;
}
}
})
</script>
</body>
【vue】方法、计算属性、数据监听也对计算属性和监听属性做过对比。虽然计算属性在大多数情况下更合适,但当需要在数据变化时执行异步操作时,监听属性更有用。
另外,再次建议:
- 由Vue管理的函数,最好写成普通函数,这样函数中的this指向才是Vue实例。
- 不被Vue管理的函数,如定时器函数、ajax回调函数、promise函数,最好写成箭头函数。因为箭头函数没有自己的this。