vue3特性

  1. 增加了setup语法糖,用来写组合api
    这是大佬对于setup的讲解:莫问前程F6的vue3之setup的使用理解
  2. 支持多个根节点,支持jsx
  3. 只引入所需要的Api
  4. 引入了proxy来重写双向绑定
    proxy与vue2的Object.defineProperty(obj, prop, desc)方式相比有以下优势:
    丢掉麻烦的备份数据
    省去for in 循环
    可以监听数组变化
    代码更简化
  5. 增加了补丁标记用来标记动态文本,在vue2中数据变更是进行全量的diff计算,而在vue3中只对于有标记的动态文本进行diff计算,大大优化了vue的性能

Ref全家桶

ref 深层次响应

  1. 深层次响应
  2. 修改、取值需要加上.vlaue

shallowRef 浅层次响应

  1. shallowRef 浅层次响应,即数据修改后不会响应到页面
<template>
  <button @click="change">修改</button>
  <div>{{ man2 }}</div>
</template>
<script lang="ts" setup>
import {ref, shallowRef} from 'vue'
const man1 = ref({na: 'h,e,l,l,o'})
const man2 = shallowRef({name: 'hello word'})
const change = () => {
  man2.value.name = '大满'
  console.log(man2)
}
</script>

数据已经修改,视图未响应
直接修改.value可以对shallowRef 绑定的数据进行视图响应

  man2.value = {
    name: '大满'
  }

在这里插入图片描述

triggerRef强制更新

triggerRef强制执行更新视图,shallowRef和triggerRef一起使用可以达到ref的响应效果

<script lang="ts" setup>
import {ref, shallowRef, triggerRef} from 'vue'
const man2 = shallowRef({name: 'hello word'})
const change = () => {
  man2.value.name = '大满'
  triggerRef(man2)
  console.log(man2)
}
//视图点击修改效果如上
</script>

shallowRef 和ref一起使用会被受到影响响应到页面上,因为ref会调用triggerRef强制执行更新视图

<template>
  <button @click="change">修改</button>
  <div>{{ man1 }}</div>
  <div>{{ man2 }}</div>
</template>
<script lang="ts" setup>
import {ref, shallowRef} from 'vue'
const man1 = ref({na: 'h,e,l,l,o'})
const man2 = shallowRef({name: 'hello word'})
const change = () => {
  man1.value.na = '大满'
  man2.value.name = '大满'
  console.log(man2)
}
</script>

点击修改按钮后,视图都更新了
在这里插入图片描述

customRef 自定义响应

可以利用customRef结合定时任务,实现防抖
!!!在修改前如果有定时器(定时时间内多次修改),那么先关闭这个定时器,再继续修改(实现防抖效果)

const guanguan = MyRef('guanguan')
function MyRef(value: string) {
  let timer: any
  return customRef((track, trigger) => {
    return {
      get() {
        track() //通知value的值会被修改,需要被追踪
        return value
      },
      set(newVal) {
        clearTimeout(timer)   //在修改前如果有定时器(定时时间内多次修改),那么先关闭这个定时器,再继续修改(实现防抖效果)
        timer = setTimeout(() => {
          value = newVal
          trigger()   //去通知get()要重新渲染
            console.log(guanguan)
          timer = null
        })
      }
    }
  })
}
const change = () => {
  guanguan.value = '大美女'

}

isRef

进行响应式数据判断,返回true和false
shallowRef和customRef都可以进行属于响应式数据都可进行判断

reactive全家桶

reactive 深层次

  1. 只能绑定引用数据类型,object、array、map、set等
  2. reactive取值修改不需要加上.value,适合form表单中使用,ref需要加上.value
  3. 调用接口修改数组时不能直接等号赋值,会把外层的proxy覆盖掉破坏了响应式对象,导致无法响应,数组 可以使用push加字符串模板解构赋值,或者添加一个对象,把数组当作一个属性去处理
<template>
  <button @click="change">修改</button>
  <div>{{ guanguan }}</div>
  <div>{{ guanguan1 }}</div>
</template>
<script lang="ts" setup>
import { reactive} from 'vue'
let guanguan = reactive({
  off: {
    name: 'guanguan'
  }
})
let guanguan1 = reactive({
  off: {
    name: [1, 2]
  }
})
const change = () => {
  guanguan.off.name = '大美女'
  let num = [3, 4]
  let timer = setTimeout(() => {
    guanguan1.off.name = num
  }, 500)

}
</script>

点击修改按钮后,guanguan1的数据不会响应到视图层,不会再实现双向绑定效果
解决办法:

 let timer = setTimeout(() => {
    guanguan1.off = {
      name: [...num]
    }
  }, 500)
  setTimeout(() => {
    guanguan1.off = {
      name: []
    }
    guanguan1.off.name.push(...num)
  }, 500)

shallowReactive 浅层次

  1. 直接修改无法响应到视图
  2. 指到第一个属性修改可以响应到视图层
  3. 和 reactive 一起使用会被受到影响(即响应到视图层)
<script lang="ts" setup>
import {reactive, shallowReactive} from 'vue'
let a = shallowReactive({
  off: {
    name: 'guanguan'
  }
})
const change = () => {
  a.off = {name: '大美女'}  // 响应到视图层
  a.off.name = '大美女' // 不响应到视图层
}
</script>

readonly isReadonly isShallow

readonly:只读
isReadonly:判断是否只读
isShallow:判断是否属于浅层次响应

<script lang="ts" setup>
import {isReadonly, isShallow, reactive, readonly, shallowReactive} from 'vue'

let guanguan = readonly(reactive({
  off: {
    name: 'guanguan'
  }
}))
let a = shallowReactive({
  off: {
    name: 'guanguan'
  }
})
const change = () => {
  console.log(isShallow(a)) // true
  console.log(isReadonly(guanguan)) //true
  guanguan.off.name = '大美女' //编译器代码规范提示
}
</script>

点击事件控制台打印:
在这里插入图片描述

toRef toRefs 和 toRaw

toRef(对象名,key)

  1. toRef只对响应式对象起作用,对于非响应式对象不起作用
  2. 用于对象中key值的单独使用
<script lang="ts" setup>
import {reactive, toRef} from 'vue'
let guanguan = reactive({
  name: 'guanguan',
  sex: '女'
})
let name = toRef(guanguan, 'name')
const change = () => {
  name.value = '大美女' //会响应到视图层
  console.log(name)
}
</script>

toRefs(对象名)

适用于响应式对象的解构赋值

 let {name, sex} = toRefs(guanguan)

原理:

const toRefs = <T extends object>(obj: T) => {
  let map: any = {}
  for (let key in obj) {
    map[key] = toRef(obj, key)
  }
  return map
}
let {name, sex} = toRefs(guanguan)

toRaw

将响应式对象转为非响应式对象

  console.log(guanguan)
  console.log(toRaw(guanguan))

在这里插入图片描述

Logo

前往低代码交流专区

更多推荐