案例:组合式API待办事项

学习完组合式 API 的内容之后,可以把上一章的待办事项系统重构为采用 Vue 3 组合式 API 的语法。

功能描述

主要功能和 3.8 节的待办事项系统功能一致,这里不再赘述。

案例完整代码

这里举几个配置式 API 转换成组合式 API 的代码示例。

例如,在 todo.vue 中将 data 中定义的响应式变量替换为 setup 方法中的响应式变量,代码如下:

export default {
    name: 'todo',// 组件的名称,尽量和文件名一致
    components: {
      titem
    },
    data() {
        return {
            newTodoContent: '',  // 输入框 input 的内容
            todoItems: []        // 待办事项的列表
        }
    }
    ...
}

替换为组合式 API 对应的代码如下:

import { reactive } from 'vue'  // 注意引入 reactive
export default {
    name: 'todo',              // 组件的名称,尽量和文件名一致
    setup() {
        const state = reactive({
            newTodoContent: '',   // 输入框 input 的内容
            todoItems: []         // 待办事项的列表
        })
        ...
    }
    ...
}

todo.vue 中,将 watch 监听逻辑转换为对应的 watch 方法,代码如下:

...
watch:{
    // 一旦有改动,立刻调用更新存储
    todoItems:{
        handler(val){
            this.storeItems(val)
        },
        deep:true
    }
},
...

替换为组合式 API 对应的代码如下:

import {watch} from 'vue'     // 注意引入 reactive
setup() {
    ...
    watch (
        () => JSON.parse(JSON.stringify(state.recycleItems)),
        (val, oldVal) => {
            storeItems(val)   // 一旦有改动,立刻调用更新存储
        },
        {deep:true}
    )
}

注意,组合式 API 的 watch 方法采用深度监听 deep:true,对于复杂对象 recycleItems,需要 JSON.parse()JSON.stringify() 拷贝对象。

例如,在 titem.vue 中,将 props 接收的数据作为 data 的默认值,采用 computed 转换为在 setup 方法中接收默认的 props 值,代码如下:

export default {
    name: 'titem',
    props: {
        item: {                    // 接收父组件传递的事项数据
            type: Object
        }
    },
    data(){
        return {
            isCompleted: false       // 默认从事项数据中获取,否则为false
        }
    },
    created(){
        this.isCompleted = this.item.isCompleted
    },
    computed:{
        // 利用computed存储props的默认值
        itemData(){
            return this.item
        }
    },
}

替换为组合式 API 对应的代码如下:

export default {
    name: 'titem',
    props: {
        item: { // 接收父组件传递的事项数据
            type: Object
        }
    },
    setup(props){
        const state = reactive({
            item: props.item,
            // 默认从事项数据中获取,否则为false
            isCompleted: props.item.isCompleted || false
        })
        ...
    }
}

以上只是列举一些典型的配置式 API 转换成组合式 API 的代码场景,具体的业务逻辑代码不再列举,读者可参考完整源码,执行 npm run serve 命令即可启动完整源码程序。

本案例完整源码:/案例源码/Vue.js Composition API。

小结与练习

本章讲解了 Vue 3 引入的组合式 API 的相关知识,主要内容包括:组合式 API 基础、setup 方法、响应式类方法、监听类方法、生命周期类方法、methods 方法、provideinject。其中 setup 方法是组合式 API 的重点,所有相关的组合式 API 新提供的接口都需要在 setup 中使用;响应式类方法中的 ref 方法和 reactive 方法常被用来定义响应式对象;监听类方法中的 computed 方法和 watch 方法则提供了监听到响应式对象变化的时机;生命周期类方法基本和配置式 API 中的使用类似;methods 方法则需要注意同名的情况;最后 provideinject 是在 setup 方法中实现组件通信的重要工具。

在后续的实战项目中,我们会大量地使用组合式 API,所以学好本章内容非常重要。

下面来检验一下读者对本章内容的掌握程度:

  • setup 方法中接收的两个参数,它们的作用分别是什么?Vue.js 中的父子组件如何通信?

  • 如果需要定义基本类型数据为响应式,应该调用哪个方法?

  • watchwatchEffect 的区别和各自的使用场景是什么?

  • 如何在被 inject 的组件中修改 provide 的数据?

  • 如果在模板中调用的 setup 方法和配置式 API 中 methods 定义的方法同名会怎么样?