其他分享
首页 > 其他分享> > Vue3中新的API

Vue3中新的API

作者:互联网

常用的 Composition API(组合API)

setup

  1. Vue3.0新增的配置项,值为一个函数
  2. setup是所有Composition API的
  3. 组件中所用到的:数据,方法等等,均需要配置在setup函数中
  4. setup函数的两种返回值:
    • 若返回是一个对象,对象中的属性,方法,在模板中军可以直接使用
    • 若返回一个渲染函数,则可以自定义渲染内容
  5. setup的两个注意点:
    • setup的执行时机:在beforeCreate之前执行一次,this是undefined
    • setup的参数:
      • props:值为对象,包含外部传递过来,且组件内部申明接收了的属性
      • context:上下文对象
        • attrs:值为对象,包含组件外部传递过来,但是没有在props中配置中申明的属性,相当于this.$attrs
        • slots:收到的插槽的内容,相当于this.$slots
        • emit:分发自定义时间的函数,闲的刚玉this.$emit。(值得注意的是,Vue3中使用emit,需要使用emits去接收父组件传过来的数据,和props
          差不多)
PS:
  1. 尽量不要与Vue2的配置项混用:
    • Vue2配置项(data,methods,computed…)中可以访问到setup中的属性,方法。
    • 但在setup中不能访问到Vue2中的配置
    • 如果有重名,setup优先
  2. setup函数不能是一个async函数(后面学习异步组件,也行,需要的是Suspense和异步组件引入的配合),因为返回值不在是一个return的对象,而是promise,模板看不到return对象中的属性
<template>
    <h1>{{name}}</h1>
    <button @click="sayHi"></button>
</template>
<script>
exprot default {
    name: 'App',
    setup(props,context) {
        const name = "景天" // 不是响应式的数据
        function sayHi() {
            console.log(`Hi,我是${name}`)
        }
        
        // 返回值是一个对象
        return {
            name,
            sayHi
        }
        
        // 返回值是一个渲染函数
        return () => h('h1','这是渲染函数渲染的内容')
    }
}
</script>

ref函数

  1. 作用:定义一个响应式的数据,或者说是生成一个引用实现对象
  2. 语法:const xxx = ref(initValue)
    • 创建一个包含响应式数据的引用对象(reference对象)
    • JS中操作数据需要:xxx.value
    • 模板中读取数据:直接使用即可
PS:
  1. ref接收的数据可以是基本类型数据,也可以是对象类型
  2. 基本类型的数据:响应式是靠Object。defineProperty()的get和set完成的
  3. 对象类型的数据:内部使用了reactive函数
<template>
    <h1>{{name}}</h1>
    <h1>{{age}}</h1>
    <button @click="sayHi"></button>
</template>
<script>
import {ref} from 'vue'
exprot default {
    name: 'App',
    setup() {
        const name = ref("景天") 
        const age = ref(18) 
        const job = ref({
            type: '前端',
            money:'30K'
        }) // 其实Vue3帮你调用了reactive函数
        // 在setup中访问ref定义的基本数据类型的数据,需要 .value才能拿到值
        function sayHi() {
            name.value = '飞蓬'
            age.value = '1000'
            job.value.money = '60K'
        }
        
        return {
            name,
            age,
            job,
            sayHi
        }
    }
}
</script>

reactive函数

  1. 作用:定义一个对象类型的响应式数据
  2. 语法:const 代理对象 = reactive(源对象) 参数是一个对象或者数组,返回一个代理对象(Proxy的实例对象,简称proxy对象)
  3. reactive定义的响应式数据是深层次的
  4. 内部基于ES6的Proxy实现,通过代理对象操作源对象内部数据
<template>
    <h1>{{name}}</h1>
    <h1>{{age}}</h1>
    <button @click="sayHi"></button>
</template>
<script>
import {ref, reactive} from 'vue'
exprot default {
    name: 'App',
    setup() {
        const name = ref("景天") 
        const age = ref(18) 
        const job = reactive({
            type: '前端',
            money:'30K'
        }) 
        const hobby = ['抽烟', '喝酒', '烫头']
        
        function sayHi() {
            name.value = '飞蓬'
            age.value = '1000'
            job.money = '60K'   // 不需要.value了
            hobby[0] = '吃饭'
        }
        
        return {
            name,
            age,
            job,
            hobby,
            sayHi
        }
        
        // ref定义的基本类型的数据都要.value取值,有点烦,我们可以换一种思路,而且语义化
        const person = reactive({
            name: '景天',
            age: 18,
            jon: {
                type: '前端',
                money:'30K'
            },
            hobby: ['抽烟', '喝酒', '烫头']
        })
        
        return {
            person
        }
    }
}
</script>

computed

简写和完整版写法和Vue2都一样,只是使用不一样,需要单独引入使用,变成了一个函数

<template>
    <h1><input v-model="firstName" /></h1>
    <h1><input v-model="lastName" /></h1>
    <div>{{fullName}}</div>
</template>
<script>
import {reactive,computed} from 'vue'
exprot default {
    name: 'App',
    setup() {
        const person = reactive({
            firstName + : '景天',
            lastName: 18,
        })
        // 或者可以绑定在person对象上
        // person.fullName = computed(()=>{
        let fullName = computed(()=>{
            // 简写形式,完整版的get和set和Vue2都一样
            return person.firstName + person.lastName
        })
        
        return {
            person,
            fullName
        }
    }
}
</script>

watch

<template>
    <h1>{{num}}</h>
    <h1>{{msg}}</h>
</template>
<script>
import {ref,reactive,watch} from 'vue'
exprot default {
    name: 'App',
    setup() {
        let num = ref(0)
        let msg= ref('消息')
        let p = reactive({
            name: '景天',
            age: 18,
            a: {
                b: {
                    c: 100
                }
            }
        })
        
        // 1. 监视ref所定义的一个响应式数据
        watch(num,(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        },{immediate:true})
        
         // 2. 监视ref所定义的多个响应式数据
        watch([num,msg],(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        },{immediate:true})
        
        // 3. 监视reactive所定义的一个响应式数据。
        // 注意:此处无法正确的获得oldVal
        // 注意:强制开启了深度监视器(deep配置无效)
        watch(p,(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        },{deep:false}) // 此处的deep无效
        
        // 4. 监视reactive所定义的一个响应式数据中的某个属性。需要使用函数
        watch(()=>p.name,(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        })
        
        // 5. 监视reactive所定义的一个响应式数据中的某些属性。
        watch([()=>p.name,()=>p.age],(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        },{deep:false})
        
        // 特殊情况
        watch(()=>p.a,(newVal,oldVal)=> {
            console.log(newVal,oldVal)
        },{deep:true})      // 此处由于监视的是reactive所定义的对象中的某个属性(对象),所以deep配置有效
        
        
        return {
            num,
            msg,
            p
        }
    }
}
</script>

watchEffect函数

<template>
    <h1>{{num}}</h>
    <h1>{{msg}}</h>
</template>
<script>
import {ref,reactive,watchEffect} from 'vue'
exprot default {
    name: 'App',
    setup() {
        let num = ref(0)
        let msg= ref('消息')
        let p = reactive({
            name: '景天',
            age: 18,
            a: {
                b: {
                    c: 100
                }
            }
        })
        
        watchEffect(()=> {
            const x1 = sum.value
            const x2 = age.value
            console.log('watchEffect调用了')
        })
        
        return {
            num,
            msg,
            p
        }
    }
}
</script>

toRef

// 上面说过数据可以定义reactive,避免.value。但是这样的话,我们使用数据就要person.name这样使用,那么可以试试这样
return {
    ...toRefs(person)
}

其他Composition API

shallowReactive和shallowRef

readonly和shallowReadonly

toRaw和markRaw

customRef

demo:实现输入数据,防抖效果
<template>
    <input v-model="keyword">
    <div>{{keyword}}</div>
</template>
    
<script>
    import { customRef } from 'vue'
    export default {
        name: 'demo',
        setup() {
            // 自定义一个ref,名称为myRef
            function myRef(value,delay) {
                let timer
                // 使用vue的customRef去配置我们的myRef,参数为一个函数,这个函数有两个参数可以直接使用
                // track:
                // trigger:
                return customRef((track,trigger)=> {
                    // 要求必须返回一个对象,里面包含get和set
                    return {
                        get() {
                            // 通知vue追踪value的变化
                            track()
                            return value
                        },
                        set(neValue) {
                            clearTimeout(timer)
                            timer = setTimeout(()=> {
                                value = newValue
                                // 通知vue去重新解析模板
                                trigger()
                            },delay)
                        }
                    }
                })
            }
        }
        
        let keyword = myRef('Hello',100)
        
        return {
            keyword
        }
    }
</script>

provide和inject在Vue3中的使用

// 祖组件
import {reactive} from 'vue'
setup() {
    let car = reactive({
        name: '奥迪',
        price: '100W'
    })
    provide('car',car)
}
// 后代组件
import {inject} from 'vue'
setup(props,context) {
    const car = inject('car')
    return {
        car
    }
}

响应式数据的判断

Vue3中的新组件

Fragment

相当于一个虚拟的容器,在Vue中,每个组件,都需要有个根组件,但是在Vue3不需要,其实是Vue3帮助我们调用了这个组件,在我们的页面上,不会渲染出来

Teleport

当我们的组件总有些内容,不想显示在我们自己的组件中,可以使用这个组件,比如我们有个弹窗,想显示在body标签中

// to这里支持标签
// to支持css标签
// <teleport to="body">
<teleport to="#main">
    <div class="dialog">
        这是一个对话框
    </div>
</teleport>

Suspense

试验性

Suspense 是一个试验性的新特性,其API可能随时会发生变动。特此声明,以便社区能够为当前的实现提供反馈。

生产环境请勿使用。

以上是官方的警告!

<template>
    <div>
        <Suspense>
            // 这两个插槽名称是固定的
            // defalut:这里面写的就是我们正常要显示的组件和代码
            // fallback:这里写的就是应急代码,就是正常代码没有显示的时候的代码
            <template v-slot:defalut:>
                <Child/>
            </template>
            <template v-slot:fallback>
                <div>加载中...</div>
            </template>
        </Suspense>
    </div>
</template>
    
<script>
    // import Child from './component/Child.vue' // 平时使用的静态引入
    
    // 下面这是异步引入
    import { defineAsyncComponent } from 'vue'
    const Child = defineAsyncComponent(()=> import('./component/Child.vue'))
    export default {
        name: 'app',
        components: {
            Child
        }
        setup() {
            
        }
    }
</script>

标签:name,对象,setup,reactive,API,中新,Vue3,组件,ref
来源: https://blog.csdn.net/WFL804203164/article/details/122615905