const state = reactive({ list: [ref(0)], }); // 不会自动展开, 须使用 `.value` state.list[0].value === 0; // true state.list.push(ref(1)); // 不会自动展开, 须使用 `.value` state.list[1].value === 1; // true
当我们需要操作DOM的时候,比如我们在项目中使用swiper需要获取DOM,那么我们还可以这样!
<div> <swiper :options="swiperOption" ref="mySwiper"> <swiper-slide v-for="(img ,index) in tabImgs.value" :key="index"> <img @click="handleClick(img.linkUrl)" :src="img.imgUrl" /> </swiper-slide> </swiper> </div>
然后在setup函数中定义一个const mySwiper = ref(null);,之前在vue2.x中,我们是通过this.$refs.mySwiper来获取DOM对象的,现在也可以使用ref函数代替,返回的mySwiper要和template中绑定的ref相同!
import { ref, onMounted } from "@vue/composition-api"; setup(props, { attrs, slots, parent, root, emit, refs }) { const mySwiper = ref(null); onMounted(() => { // 通过mySwiper.value 即可获取到DOM对象! // 同时也可以使用vue2.x中的refs.mySwiper ,他其实mySwiper.value 是同一个DOM对象! mySwiper.value.swiper.slideTo(3, 1000, false); }); return { mySwiper } }
reactive
reactive() 函数接收一个普通对象,返回一个响应式的数据对象,等价于 vue 2.x 中的 Vue.observable() 函数,vue 3.x 中提供了 reactive() 函数,用来创建响应式的数据对象Observer,ref中我们一般存放的是基本类型数据,如果是引用类型的我们可以使用reactive函数。
当reactive函数中,接收的类型是一个Array数组的时候,我们可以在这个Array外面在用对象包裹一层,然后给对象添加一个属性比如:value(这个属性名你可以自己随便叫什么),他的值就是这个数组!
<script> // 使用相关aip之前必须先引入 import { ref, reactive } from "@vue/composition-api"; export default { name: "home", setup(props, { attrs, slots, parent, root, emit, refs }) { const active = ref(""); const timeData = ref(36000000); // 将tabImgs数组中每个对象都变成响应式的对象 const tabImgs = reactive({ value: [] }); const ball = reactive({ show: false, el: "" }); return { active, timeData, tabImgs, ...toRefs(ball), }; } }; </script>
那么在template模版中我们想要访问这个数组的时候就是需要使用.value的形式来获取这个数组的值。
<template> <div> <swiper :options="swiperOption" ref="mySwiper"> <swiper-slide v-for="(img ,index) in tabImgs.value" :key="index"> <img @click="handleClick(img.linkUrl)" :src="img.imgUrl" /> </swiper-slide> </swiper> </div> </template>
isRef
isRef() 用来判断某个值是否为 ref() 创建出来的对象;当需要展开某个可能为 ref() 创建出来的值的时候,可以使用isRef来判断!
import { isRef } from '@vue/composition-api' setup(){ const headerActive = ref(false); // 在setup函数中,如果是响应式的对象,在访问属性的时候,一定要加上.value来访问! const unwrapped = isRef(headerActive) ? headerActive.value : headerActive return {} }
toRefs
toRefs函数会将响应式对象转换为普通对象,其中返回的对象上的每个属性都是指向原始对象中相应属性的ref,将一个对象上的所有属性转换成响应式的时候,将会非常有用!
import { reactive,toRefs } from '@vue/composition-api' setup(){ // ball 是一个 Observer const ball = reactive({ show: false, el: "" }); // ballToRefs 就是一个普通的Object,但是ballToRefs里面的所有属性都是响应式的(RefImpl) const ballToRefs = toRefs(ball) // ref和原始属性是“链接的” ball.show = true console.log(ballToRefs.show) // true ballToRefs.show.value = false console.log(ballToRefs.show) // false return { ...ballToRefs // 将ballToRefs对象展开,我们就可以直接在template模板中直接这样使用这个对象上的所有属性! } }
点击添加按钮,小球飞入购物车动画:
<template> <div> <transition @before-enter="beforeEnter" @enter="enter" @afterEnter="afterEnter"> <!-- 可以直接使用show--> <div v-if="show"> <li> <span @click="addToCart($event,item)"> <svg-icon icon-class="add"></svg-icon> </span> </li> </div> </transition> </div> </template>
computed
computed函数的第一个参数,可以接收一个函数,或者是一个对象!如果是函数默认是getter函数,并为getter返回的值返回一个只读的ref对象。