Vue3-自定义 Hooks
1. Hooks 定义
官方对自定义 hook 定义:在 Vue 应用的概念中,“组合式函数” (Composables) 是一个利用 Vue 组合式 API 来封装和复用有状态逻辑的函数。
其实 Hooks 本质是一个函数,把 setup 函数中使用的 Composition API 进行了封装。自定义 Hooks 可以复用代码, 让 setup 中的逻辑更清楚易懂。
2. Hooks 使用
用 Composition API 来创建一个可响应的计数器。
2.1. 创建 hooks 文件夹
在 src 中创建 hooks 文件夹,并在该文件夹创建 useCounter.js 文件。
2.2. 创建计数器
-
首先,从
vue
库中导入reactive
和toRefs
函数。 -
在
useCounter
函数中,我们使用reactive
函数来创建一个响应式对象state
,其中包含count
属性和add
和minus
方法。count
属性被初始化为 0,add
方法增加count
的值,minus
方法减少count
的值。 -
接下来,我们使用
toRefs
函数将state
对象转换为具有响应式引用形式的对象。这样,我们可以将state
对象作为参数传递给 Vue 组件,并在模板中直接访问它的属性和方法。 -
最后,我们返回
toRefs(state)
,这样在调用useCounter
函数时,它将返回一个包含count
、add
和minus
属性的对象,这些属性都是响应式的。import { reactive, toRefs } from "vue"; export const useCounter = () => { const state = reactive({ count: 0, add() { state.count++; }, minus() { state.count--; }, }); return toRefs(state); };
2.3. 创建 UseHooks 组件
导入useCounter
函数,该函数是一个用于获取计数器状态的 Hook。useCounter
函数返回一个对象,包含add
、minus
和count
属性。我们将这些属性分别赋值给组件的add
、minus
和count
属性。
<script setup>
import {useCounter} from '../hooks/useCounter' const {(add, minus, count)} =
useCounter() // console.log(count);
</script>
在<template>
部分,我们定义了计数器的显示内容和两个按钮。其中一个按钮点击时会调用add
方法,增加计数;另一个按钮点击时会调用minus
方法,减少计数。
<template>
<div>
<span>{{ count }}</span>
<button @click="add">点我+1</button>
<button @click="minus">点我-1</button>
</div>
</template>
2.4. 显示组件
在 App 中显示子组件 UseHooks
。
<template>
<UseHooks />
</template>
<script setup>
import UseHooks from './components/UseHooks.vue';
</script>
<style scoped></style>
2.5. 演示效果
3. 完整代码
3.1. useCounter.js
import { reactive, toRefs } from "vue";
export const useCounter = () => {
const state = reactive({
count: 0,
add() {
state.count++;
},
minus() {
state.count--;
},
});
return toRefs(state);
};
3.2. UseHooks.vue
<template>
<div>
<span>{{ count }}</span>
<button @click="add">点我+1</button>
<button @click="minus">点我-1</button>
</div>
</template>
<script setup>
import { useCounter } from '../hooks/useCounter'
const { add, minus, count } = useCounter()
// console.log(count);
</script>
<style scoped></style>
3.3. App.vue
<template>
<UseHooks />
</template>
<script setup>
import UseHooks from './components/UseHooks.vue';
</script>
<style scoped></style>