說明:如果是Composition Api在功能複雜、程式碼量龐大的元件下,我們配合自訂Hook,將程式碼按功能分塊寫,變數和方法在一起定義和調用,例如A功能下集成了響應式變數和方法,我們後期維護只需要改動A功能模組下的程式碼,不會像Vue2在Option Api需要同時關注邏輯分散的methos和data。
所以自訂Hook的寫Vue3必須掌握的!它無不體現Vue3 Composition Api 低耦合高內聚的思想!筆者在看了官方文件和開源的admin模板都是大量使用自訂Hooks的!
雖然官方沒有明確指明或定義什麼是自訂Hooks,但卻無所不在用;
#以函數形式抽離一些可復用的方法像鉤子一樣掛著,隨時可以引入和調用,實現高內聚低耦合的目標;
將可復用功能抽離為外部JS檔案
函數名稱/檔案名稱以use開頭,形如:useXX
引用時將響應式變數或方法明確解構暴露出來如:const {nameRef,Fn} = useXX()
#(在setup函數中解構出自定義hooks的變數和方法)
簡單的加減法計算,將加法與減法抽離為2個自訂Hooks,並且相互傳遞響應式資料
加法功能-Hook
import { ref, watch } from 'vue'; const useAdd= ({ num1, num2 }) =>{ const addNum = ref(0) watch([num1, num2], ([num1, num2]) => { addFn(num1, num2) }) const addFn = (num1, num2) => { addNum.value = num1 + num2 } return { addNum, addFn } } export default useAdd
減法功能-Hook
//减法功能-Hook import { ref, watch } from 'vue'; export function useSub ({ num1, num2 }){ const subNum = ref(0) watch([num1, num2], ([num1, num2]) => { subFn(num1, num2) }) const subFn = (num1, num2) => { subNum.value = num1 - num2 } return { subNum, subFn } }
加減法計算元件
<template> <div> num1:<input v-model.number="num1" /> <br /> num2:<input v-model.number="num2" /> </div> <span>加法等于:{{ addNum }}</span> <br /> <span>减法等于:{{ subNum }}</span> </template> <script setup> import { ref } from 'vue' import useAdd from './useAdd.js' //引入自动hook import { useSub } from './useSub.js' //引入自动hook const num1 = ref(2) const num2 = ref(1) //加法功能-自定义Hook(将响应式变量或者方法形式暴露出来) const { addNum, addFn } = useAdd({ num1, num2 }) addFn(num1.value, num2.value) //减法功能-自定义Hook (将响应式变量或者方法形式暴露出来) const { subNum, subFn } = useSub({ num1, num2 }) subFn(num1.value, num2.value) </script>
Mixin不足
在Vue 2 中,mixin 是將部分元件邏輯抽象化成可重複使用區塊的主要工具。但是,他們有幾個問題:
1、Mixin 很容易發生衝突:因為每個mixin 的property 都被合併到同一個元件中,所以為了避免property 名衝突,你仍然需要了解其他每個特性。
2、重複使用是有限的:我們不能向 mixin 傳遞任何參數來改變它的邏輯,這降低了它們在抽象邏輯方面的靈活性。
上面這段是Vue3官方文件的內容,可以概括和補充為:
Vue3自訂Hooks卻可以
Vue3自訂Hooks, 引用時將響應式變數或方法明確曝光如:
const {nameRef,Fn} = useXX()
#Mixins
export default { mixins: [ a, b, c, d, e, f, g ], //一个组件内可以混入各种功能的Mixin mounted() { console.log(this.name) //问题来了,这个name是来自于哪个mixin? } }
Mixin不明的混淆,我們根本無法獲知屬性來自於哪個Mixin文件,給後期維護帶來困難
Vue3自訂Hooks
//加法功能-自定义Hook(将响应式变量或者方法形式暴露出来) const { addNum, addFn } = useAdd({ num1, num2 }) addFn(num1.value, num2.value) //减法功能-自定义Hook (将响应式变量或者方法形式暴露出来) const { subNum, subFn } = useSub({ num1, num2 }) subFn(num1.value, num2.value)
我們很容易看出每個Hooks明確暴露出來的響應式變數和方法
但是Vue3自訂Hooks卻可以:
Vue3自訂Hooks可以靈活傳遞任何參數來改變它的邏輯,參數不限於其他hook的暴露出來的變數
Mixins
export default { mixins: [ addMixin, subMixin], //组件内混入加法和减法Mixin mounted(){ this.add(num1,num2) //调用addMixin内部的add方法 this.sub(num1,num2) //调用subMixin内部的sub方法 } }
可以透過呼叫Mixin內部方法來傳遞參數,卻無法直接給Mixin傳遞參數,因為Mixin不是函數形式暴露的,不發傳參
Vue3自訂Hook
在上面實例基礎上新增個算平均的Hook
//平均功能-Hook import { ref, watch } from "vue"; export function useAverage(addNum) { const averageNum = ref(0); watch(addNum, (addNum) => { averageFn(addNum); }); const averageFn = (addNum) => { averageNum.value = addNum / 2; }; return { averageNum, averageFn, }; }
元件內
//组件内 //加法功能-自定义Hook(将响应式变量或者方法形式暴露出来) const { addNum, addFn } = useAdd({ num1, num2 }) addFn(num1.value, num2.value)//主动调用,返回最新addNum //平均功能-自定义Hook- hook传入参数值来其他hook暴露出来的变量 const { averageNum, averageFn} = useAverage(addNum) averageFn(addNum.value)
Vue3自訂Hooks可以靈活傳遞任何參數來改變它的邏輯,參數不限於其他hook的暴露出來的變量,這提高了Vue3在抽象邏輯方面的靈活性。
Vue3自訂Hook可以在引入的時候對同名變數重新命名
Mixins
export default { mixins: [ addMixin, subMixin], //组件内混入加法和减法Mixin mounted(){ this.add(num1,num2) //调用加法addMixin内部的add方法 this.sub(num1,num2) //调用减法subMixin内部的sub方法 } }
如果this .add(num1,num2)和this.sub(num1,num2) 計算的結果回傳的同名變數totalNum,由於JS單線程,後面引入的會覆蓋前面的,totalNum最終是減法sub的值
Vue3自訂Hooks
//加法功能-自定义Hook(将响应式变量或者方法形式暴露出来) const { totalNum:addNum, addFn } = useAdd({ num1, num2 }) addFn(num1.value, num2.value) //减法功能-自定义Hook (将响应式变量或者方法形式暴露出来) const { totalNum:subNum, subFn } = useSub({ num1, num2 }) subFn(num1.value, num2.value)
在Vue3自訂Hooks中,雖然加法和減法Hooks都回傳了totalNum,但利用ES6物件解構很輕鬆地為變數重命名
以上是Vue3中怎麼自訂Hooks的詳細內容。更多資訊請關注PHP中文網其他相關文章!