Skip to content

响应式Props解构

js
const props = defineProps({
    name: {
        type: Number
    }
})
const { name } = toRefs(props)
// const { name } = toRef(props, 'name');

3.5之前直接解构props会失去响应式, 可以使用toRefs或者toRef解构

js
const { name = '冷然' } = defineProps({
    name: {
        type: Number
    }
})

vue3.5+可直接进行解构并且可以赋默认值

watch

  • deep: boolean | number
    • boolean:是否深度监听
    • number:指定最大遍历深度(3.5+)
  • once: 回调函数只执行一次(3.4+)
js
const obj1 = reactive({
    name: 'obj1',
    obj2: {
        name: 'obj2',
        obj3: {
            name: 'obj3'
        }
    }
})

function handleClick() {
    obj1.obj2.obj3.name = '冷然'
}

watch(
    obj1,
    (newVal, oldVal) => {
        console.log('🚀 ~ newVal:', newVal)
    },
    { deep: 2 }
)

此时的watch是监听不到obj3的变化的,应为deep指定遍历层数为2

useTemplateRef

  • 3.5+专门用来获取dom或者组件实例

原来获取dom需要给div绑定一个ref,js中声明一个ref变量

js
;<div ref="divEl"></div>
const divEl = ref()

ref是用来声明响应式数据的,通过ref来作为dom实例容易让人困惑,useTemplateRef语义更加明确

js
;<div ref="divEl"></div>
const divEl = useTemplateRef()

注意 useTemplateRef返回的是一个浅层ref也就是shallowRef

defineModel

3.4+ 简化了原来的组件v-model, 该宏自动注册一个 prop, 并返回一个可以直接变更的 ref, 看好了是可以在子组件中直接改变的ref值

js
// 直接接收v-model参数
const props = defineProps(['modelValue'])

// defineModel宏
const model = defineModel()

v-bind缩写

html
<img :src />

3.4+ 如果v-bind绑定值与变量同名可以省略

defineOptions

3.3+可以在script setup中为组件配置选项

js
defineOptions({
    name: 'MyComponent', // 设置组件名称
    props: {
        message: {
            type: String,
            required: true
        }
    },
    emits: ['click'], // 声明事件
    inheritAttrs: false // 是否继承父组件的属性
})

可以在defineOptions中去声明组件 name、props、emits、inheritAttrs,并且defineOptions支持ts的类型推导

defineExpose

3.2+ 用于在 script setup 中暴露组件的内部方法或属性给外部使用

js
const name = ref('lengran')
function hello() {
    console.log(name)
}
defineExpose({
    name,
    hello
})

通过defineExpose暴露name与hello,父组件可通过 ref 或 expose 在父组件中访问