Vue3
Vue2的生命周期
- beforeCreate
- create
- beforeMount(挂载前)
- mounted(挂载后)
- beforeUpdate(更新前)
- Updated(更新后)
- beforeDestroy(销毁前)
- destroyed
Vue3的生命周期和生命周期钩子
- beforeCreate——setup
- create——setup
- beforeMount(挂载前)——onBeforeMount
- mounted(挂载后)——onMounted
- beforeUpdate(更新前)——onBeforeUpdate
- Updated(更新后)——onUpdated
- beforeUnmount(卸载前)——onBeforeUnmount
- unmounted——onUnmounted
- 根据需要,可以在页面中import中引用对应的生命周期钩子,然后在setup里直接使用
- 当同时在组合式生命周期和配置项生命周期一起配置的时候,发现组合式生命周期比同级别的要快一点
自定义hook函数
- 本质上是一个函数,把setup函数中使用的Composition API进行封装
- 类似Vue2中的mixin
- 自定义的hook,让setup中的逻辑更清楚易懂
类似,新建一个js
- 将setup中的代码进行封装
import {
ref,reactive, onMounted, onBeforeMount } from "vue";
//实现鼠标打点的hook
export default function activepoint() {
let ispoint = ref('ispoint')
let point = reactive({
x: 0,
y: 0,
});
function savepoint(event) {
console.log(event)
point.x = event.pageX;
point.y = event.pageY;
}
function changeispoint() {
ispoint.value = !ispoint.value
}
onMounted(() => {
window.addEventListener("click", savepoint);
});
onBeforeMount(() => {
window.removeEventListener("click", savepoint);
});
return {
point
};
}
在需要使用的页面上
- import引入
import userPoint from "../utils/point";
- 使用
setup() {
const point = userPoint();
return {
point };
},
toRef
- 创建一个ref对象,其value值指向另一个对象中的某个属性
- 以下代码看似没问题,但丧失了响应式
- 原因:return的时候,你其实相当于新定义了变量接收了一个字符串parant.name,也就是你把乞力马扎罗字符串重新赋给了name
export default {
name: "Demo",
setup() {
let parant =reactive({
name: "乞力马扎罗",
sum:0,
job: {
a: 1,
b: 2,
},
})
return {
name: parant.name,
sum:parant.sum,
};
},
};
- 解决方法:
- 参数1,想操作哪个对象,参数2,想操作对象里的哪个值
- 不论是多少层的对象,第二个参数就是你要用的值即可
return {
name: toRef(parant, "name"),
sum: toRef(parant, "sum"),
a: toRef(parant.job, "a"),
};
toRef和ref的区别
- 当同时返回源数据和源数据中的值的时候:
- toref是将源数据中的值进行绑定。源数据会跟随变化
- ref改的不是源数据的对象,而是新弄出的ref的ref对象,会造成数据分家
情况1
<template>
<!-- VUE3组件中的模板结构可以没有根标签 -->
<div>{
{
parant}}</div>
<div>{
{
sum }}</div>
<button @click="sum++">sum++</button>
<div>{
{
b }}</div>
<button @click="b++">sum++</button>
</template>
<script>
import {
ref, reactive, onMounted, onBeforeMount, toRef } from "vue";
export default {
name: "Demo",
setup() {
let parant = reactive({
name: "乞力马扎罗",
sum: 0,
job: {
a: 1,
b: 2,
},
});
return {
parant,
name: toRef(parant, "name"),
sum: toRef(parant, "sum"), //参数1,想操作哪个对象,参数2,想操作对象里的哪个值
b: ref(parant.job.b),
};
},
};
</script>
<style>
</style>
toRefs,可以返回多个
- torefs,可以批量创建多个ref对象,但只能创建对象的第一层,不能把深层的也一起创建
- 因为创建的是个对象,想要使用对象里的第一层,就要通过es6的…
但如果你想在页面中直接使用对象里的对象
- 方法1
- 抛出一层,页面中使用类似job.a的方式使用
...toRefs(parant), //只给个想操作的对象即可
<div>{
{
job.a }}</div>
<button @click="job.a++">job.a++</button>
- 方法2
- 抛出对象的时候,就直接抛出对象里的对象
...toRefs(parant.job), //只给个想操作的对象即可
代码图片展示:
其他组合式Api
shallowReactive和shallowRef
shallowReactive(浅响应式)
- shallowReactive 只处理对象最外层属性的响应式(浅响应式)
shallowRef和ref的区别
- ref响应对象的时候,内部会使用reactive去响应
- shallowRef只响应式基本数据,不会内部使用reactive去响应
readonly和shallowReadonly
readonly(深只读)
- readonly让一个响应式数据变成只读
- 将数据保护起来,不让修改
setup() {
let parant2 = shallowReactive({
name: "乞力马扎罗",
sum: 0,
b: 2,
job: {
a: 1,
},
});
parant2 = readonly(parant2);
return {
parant2,
};
},
shallowReadonly(浅只读)
- 是让对象的第一层变成只读不可修改
toRaw和markRaw
toRaw(暂时转化)
- 将一个由reactive生成的响应式对象转为普通对象
- 注意,只能转化是reactive定义的响应式数据
- 作用:用于读取响应式对象对应的普通对象,对这个普通对象的所有操作,不会引起页面更新
markRaw(永久转化)
- 标记一个对象,使其永远不会再成为响应式对象
- 场景:有些值不应被设置为响应式的,例如,复杂的第三方库
- 当渲染具有不可变数据源的大列表的时候,跳过响应式转换可以提高性能
customRef(自定义ref)
- 创建一个自定义的ref,并对其依赖信息跟踪和更新触发进行显示控制