需要用到watch监听的,直接看文章了。
1.监听一个ref的值,非常简单:
const title = ref("")
watch(title, (n, o) => {
console.log("title改变了", n, o)
})
2.需要监听多个ref的值,写法多了点,逻辑是一样的。
log出来的是一个数组,取对应下标就行。
const title = ref("")
const age = ref(0)
watch([title,age], (n, o) => {
console.log("数据改变了", n, o) //log [title,age] , []
})
3.监听一个数组,写法稍微有点不同。
const arr = reactive([1, 2, 3, 4])
arr.push(5)
watch(() => [...arr], (n, o) => {
console.log("数组变了", n, o)
})
4.监听一个整个深度对象或者数组,也是需要用到deep的啦。
这里需要安装一个lodash(不安装使用直接监听,直接监听不需要带() =>,newValue和oldValue会一样。)
文档:https://lodash.com/
安装方式:$ npm i --save lodash ()
import _ from 'lodash'
const state = reactive({
title: "",
attributes: {
title: '123',
}
})
watch(() => _.cloneDeep(state), (newValue, oldValue) => {
console.log("reactive的title变了", n, o)
}, { deep: true })
还有一种监听单个对象属性的
const state = reactive({
title: "",
attributes: {
title: '123',
}
})
watch(() => state.attributes.title, (newValue, oldValue) => {
console.log("reactive的title变了", n, o)
})
5.使用新增的watchEffect
页面上定义
const count=ref(1)
watchEffect(() => { console.log(count.value) })
默认会执行一次,输出1.
之后的每一次count改变都会执行,只能监听ref,和reactive封装的对象。
定义一个stop变量后,效果是一样的,像这样
const stop = watchEffect(() => {
let a = count.value;
console.log(a)
})
需要停止的时候 ,可以判断停止监听:
const changeCount = () => {
count.value++;
if (count.value > 5) {
stop()
} else {
}
}
重点来啦:
如果我们需要展示一个列表,当用户id改变的时候重新去请求数据的话,如果请求还没来得及响应,又改变了,这会使多次发起很多请求,对于性能是很不好的,所以我们可以在它改变多次的时候,只请求最后一次的响应成功的数据。
const stop = watchEffect((onInvalidate) => {
let a = count.value;
let time;
let p = new Promise((resolve, reject) => {
time = setTimeout(() => {
axios.get("/api", {}).then(res => {
resolve("timeout")
})
}, 1000);
})
p.then(res => {
console.log(res);
})
onInvalidate(() => clearInterval(time)) //onInvalidate()函数,清除副作用.
},{
flush: 'post' //flush:'post' 就是等待当前组件dom更新后,再去触发watchEffect。
})
再添一个
6.监听子组件接受到的值
props: {
count: {
type: Number,
default: 0
},
},
setup (props) {
let { count } = toRefs(props) //使用toRefs变成可监听的ref值 count:ObjectRefImpl{}
watch(count, (n, o) => {
console.log(n, o)
})
onMounted(() => {
console.log(count.value)
})
return {
}
},
好了,简洁的结尾,加油吧少年!