一、什么是监视?
- 在
Vue3
中,监视是一种函数 - 监视的作用是监视数据的变化
- 它可以监视四种类型:
ref
定义的数据reactive
定义的数据。- 函数的返回值(
getter
函数)。- 一个包含上述内容的数组。
二、监视的使用
在Vue3中监视的使用方法:
<script lang="ts">
import {watch} from 'vue' //引入监视
watch(value,function) //value 为监视对象, function 为监视对象发生变化后做出的回应
</script>
如何停止监视?方法如下
<script lang="ts">
//...
const stopWatch = watch(value,(newValue)=>{ //newValue 是监视对象改变后的值
if (newValue >= 10){
stopWatch() //在监视对象值改变为10时停止监视
}
})
</script>
三、使用监视的不同情况
在Vue3
中使用监视
的过程中会遇到以下情况:
情况一:
监视ref
定义的【基本类型】数据:直接写数据名即可,监视的是其value
值的改变。
<template>
<div class="Sample">
<h1>当前数据:{{num}}</h1>
<button @click="changeNum">更改数据</button>
</div>
</template>
<script lang="ts" setup name="Sample1">
import {ref,watch} from 'vue'
// 数据
let num = ref(0)
// 方法
function changeNum(){
num.value += 1
}
// 情况一:监视ref定义的【基本类型】数据
watch(num,(newValue)=>{ // num 直接写数据名,没有.value后缀
console.log("Num changed!",newValue)
})
</script>
情况二:
监视ref
定义的【对象类型】数据:直接写数据名,监视的是对象的【地址值】的改变
<template>
<div class="Sample">
<h1>当前数据:{{ data.num }}</h1>
<h1>当前人物:{{ data.name }}</h1>
<button @click="changeNum">更改数据</button>
<button @click="changeData">更改对象</button>
</div>
</template>
<script lang="ts" setup name="Sample2">
import {ref,watch} from 'vue'
// 数据
let data = ref({
num: 2,
name: "sampleNum"
})
// 方法
function changeNum(){
data.value.num += 1
}
function changeData(){
data.value = {num: 10, name: "betaNum"}
}
// 情况二:监视ref定义的【对象类型】数据
watch(data,(newValue)=>{
console.log("data changed!",newValue)
})
</script>
上述代码的监视只能在整个对象地址发生改变时才会生效,如果希望让它同时可以监视对象内容的话,需要手动设置深度监视:
给watch()
函数传入配置对象{deep:true}
<script lang="ts" setup name="Sample2">
// ...
watch(data,(newValue)=>{
console.log("data changed!",newValue)
},{deep:true})
</script>
情况三:
监视reactive
定义的【对象类型】数据,且默认开启了深度监视,并且不可关闭。
<template>
<div class="Sample">
<h1>当前数据:{{ data.num }}</h1>
<h1>当前人物:{{ data.name }}</h1>
<button @click="changeNum">更改数据</button>
<button @click="changeData">更改对象</button>
</div>
</template>
<script lang="ts" setup name="Sample3">
import {reactive,watch} from 'vue'
// 数据
let data = reactive({
num: 2,
name: "sampleNum"
})
// 方法
function changeNum(){
data.num += 1
}
function changeData(){
Object.assign(data,{num: 10, name: "betaNum"})
}
// 监视,情况三:监视【reactive】定义的【对象类型】数据,且默认是开启深度监视的
watch(data,(newValue)=>{
console.log("data changed!",newValue)
})
</script>
情况四:
监视ref
或reactive
定义的【对象类型】数据中的某个属性,需要注意:
- 若该监视的属性值不是一个对象类型,则需要写成
getter
函数的形式 - 若该监视的属性值是一个对象类型,可以直接写,也可以写成
getter
函数的形式,但推荐写成函数的形式 - 在监视一个对象类型时,需要手动开启深度监视
<template>
<div class="sample">
<h1>数据名:{{ data.name }}</h1>
<h1>数据: {{ data.num }}</h1>
<h1>子数据名:{{ data.inData.inDataName }}</h1>
<h1>子数据: {{ data.inData.inDatanum }}</h1>
<button @click="changeName">修改数据名</button>
<button @click="changeNum">修改数据</button>
<button @click="changeInName">修改子数据名</button>
<button @click="changeInNum">修改子数据</button>
<button @click="changeChild">修改子对象</button>
</div>
</template>
<script lang="ts" setup name="sample4">
import { reactive ,watch} from 'vue';
// 数据
let data = reactive({
name: "sampleName",
num: 0,
inData:{
inDataName: "inSampleName",
inDatanum: 0
}
})
// 方法
function changeName(){
data.name = "deltaName"
}
function changeNum(){
data.num += 1
}
function changeInName(){
data.inData.inDataName = "deltaInName"
}
function changeInNum(){
data.inData.inDatanum += 1
}
function changeChild(){
data.inData = {inDataName:"alphaInName", inDatanum: 10}
}
// 监视
watch(()=>{data.inData.inDataName},(newValue)=>{ //使用getter函数监视一个特定的元素
console.log("InDataName changed!",newValue)
})
watch(()=>data.inData,(newValue)=>{
console.log("InData changed!", newValue)
},{deep:true}) //手动开启深度监视
</script>