三、其他Composition Api
1、shallowReactive与shallowRef
- shallowReactive:只对对象最外层属性进行响应式处理
- shallowRef:只对基本数据类型进行处理,不对对象的响应式处理
应用场景:
- 有一个对象数据,结构比较深,但变化时只需要外层属性变化,shallowReactive
- 有一个对象数据,后续功能不会修改该对象的属性,而是用新生对象去替换,shallowRef
2、readonly和shallowReadonly
- readonly:让一个响应式数据变为只读
- shallowReadonly:让一个响应式数据变为(第一层属性)只读
数据修改有两种场景:
- 数据修改了,但是没有响应式,即页面不更新
- 数据压根没有修改
这两个api就是属于第二种没有修改数据
应用场景:不希望数据被修改,在组件拿到数据后不能被修改的场景可以用,确保一定没被修改
3、toRaw与markRaw
- toRaw:
- 作用:将reactive响应式对象转成普通对象
- 应用场景:用于读取响应式对象对应的普通对象,对这个普通对象的所有操作,不会引起页面更新
- markRaw:
- 作用:标记一个对象,让它不会成为响应式对象
- 应用场景:
- 有些值不应被设置成响应式
- 当渲染具有不可变数据源的大列表的时候,跳过响应式转换可以提高性能
4、customRef
// 实现一个输入框输入数据,下面的h4标签延迟1秒进行输出
function myRef(value,delay){
// 必须要有返回值,跟ref一样,返回一个对象
// 使用customRef来实现自定义
let timer
return customRef((track,trigger)=>{
// 这个自定义的ref必须有返回值
return{
get(){
track()
return value
},
set(newVal){
clearTimeout(timer)
timer = setTimeout(()=>{
value = newVal
trigger()
},delay)
}
}
})
}
let keyWord = myRef('hello',500)
5、provide和inject
作用:实现祖孙组件间通信
使用:父组件有一个provide
选项提供数据,子组件有一个inject
选项来接收数据
具体写法:
- 祖组件中:
setup(){
let car = reactive({name:'奔驰'})
provide('car',car)
return {...toRefs(car)}
}
- 孙组件中:
setup(){
let car = inject('car')
}
6、响应式数据的判断
- isRef:检查一个值是否为ref对象
- isReactive:检查一个值是否由reactive创建的响应式代理
- isReadonly:检查一个值是否由readonly创建的只读代理
- isProxy:检查一个值是否由reactive、readonly创建的代理
四、Composition Api的优势
1、Options Api存在的问题
使用传统Options Api中,新增或者修改一个需求,就需要分别在data、methods、computed里修改
2、Composition Api的优势
可以更加优雅的组织汪茂的代码,函数。让相关功能的代码更加有序的组织在一起
五、新的组件
1、Fragment
- vue2中:必须要有一个根标签
- vue3中:可以没有根组件,内部会将多个标签包含在一个Fragment虚拟元素中
好处:减少标签层级,减少内存占用
2、Teleport
介绍:它是一种能够将我们的组件html结构移动到指定位置的技术
// 移动的位置是选择器填写
<teleport to="移动的位置">
<div v-if="isShow" class="mask">
<div class="dialog">
<h3>我是一个弹窗</h3>
<button @click="isShow = false">关闭弹窗</button>
</div>
</div>
</teleport>
3、Suspense
作用:等待异步组件渲染一些额外内容,让应用有更好的用户体验
使用步骤:
- 异步引入组件
import { defineAsyncComponent } from 'vue'
const Child = defineAsyncComponent(()=>import('./components/Child.vue'))
- 使用suspense包裹组件,配置好
default
与callback
<template>
<h3>我是组件</h3>
<Suspense>
<template v-slot:default>
<Child/>
</template>
<template v-slot:fallback>
加载中
</template>
</Suspense>
</template>