Vue3實(shí)現(xiàn)組件級(jí)基類的多種方法
Vue3的組件有三種代碼組織方式
- 純Option API (不含setup)
- option API + setup
- 純 setup (即composition API)
對(duì)于這三種形式,設(shè)置基類的方法也略有不同。
使用 mixins、extends
vue3提供了 mixins和extends,但是嘗試之后發(fā)現(xiàn)這兩種方法只支持純OptionAPI,設(shè)置的data會(huì)被識(shí)別,但是設(shè)置的setup里return 的 reactive,完全無(wú)效,setup也沒有被執(zhí)行。
所以這種方式只能使用于第一種方式。
使用 hooks (function、class)
既然官方?jīng)]有提供,那么我們自己來(lái)想想辦法。我們先觀察一下組件的代碼(第二種情況):
<template> <!--模板--> 舉例 </template> <script lang="ts"> import { defineComponent } from 'vue' export default defineComponent({ name: 'ui-core-', components: { // 注冊(cè)共用組件 }, props: { // 定義共用屬性 }, setup(props, context) { // 各種共用操作 _logger() _setTitle() // 共用成員 const foo = reactive ({}) return { foo } } }) </script>
defineComponent 方法接收一個(gè)對(duì)象,對(duì)象需要有特定的幾個(gè)屬性,比如name、components、props、setup等。
那么也就是說(shuō),我們可以做一個(gè)函數(shù)返回這樣的對(duì)象即可。
比如我們先建立一個(gè)js(或則ts)文件:
export function base (name, callback) { return { name: 'ui-' + name, components: { // 注冊(cè)共用組件 }, props: { // 定義共用屬性 }, setup(props, context) { // 各種共用操作 _logger() _setTitle() // 共用成員 const foo = reactive ({}) // 執(zhí)行其他操作 const re = callback(props, context) return { foo, ...re } } } }
有點(diǎn)像模板模式。
傳入name和一個(gè)回調(diào)函數(shù),props, context作為參數(shù)進(jìn)行傳遞。內(nèi)部成員也可以作為參數(shù)傳遞。
這樣一個(gè)簡(jiǎn)單的基類就做成了,如果你覺得function不好看,那么可以換成class。
export default class BaseComponent { name: string components: any props: any setup: any constructor (name: string, callback: (props: any, context: any) => any) { this.name = name this.components = {} this.props = {} this.setup = (props: any, context: any) => { // 各種共用操作 _logger() _setTitle() // 執(zhí)行其他操作 const re = callback(props, context) return { ...re } } } }
有了class之后,還可以設(shè)置子類,不過(guò)感覺有點(diǎn)繁瑣??傊?,反正可以實(shí)現(xiàn)就對(duì)了。
script setup怎么辦
上述這種方法應(yīng)該也是可以支持純composition API的,但是有點(diǎn)小問(wèn)題,defineProps 和 defineEmits 并不是普通 js 函數(shù),而是一種“宏”。
引用官網(wǎng)的解釋:
defineProps 和 defineEmits 都是只能在 <script setup> 中使用的編譯器宏。他們不需要導(dǎo)入,且會(huì)隨著 <script setup> 的處理過(guò)程一同被編譯掉。
也就是說(shuō) defineXXX系列 只有在 <script setup> 標(biāo)簽內(nèi)部才會(huì)被識(shí)別,如果在單獨(dú)的js文件里面,不會(huì)被識(shí)別。
這就導(dǎo)致 defineProps 和 defineEmits 無(wú)法做成基類的形式。
如果需要的基類不涉及 defineProps 和 defineEmits 的話,那么還是可以在單獨(dú)的js文件里面定義一個(gè)function或者class的,(即做一個(gè)綜合的hooks)。
如果涉及 defineProps 和 defineEmits,那么,我也沒想出來(lái)辦法。(只能第二種方式)
到此這篇關(guān)于Vue3實(shí)現(xiàn)組件級(jí)基類的幾種方法的文章就介紹到這了,更多相關(guān)Vue3組件級(jí)基類內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Vue中 v-if/v-show/插值表達(dá)式導(dǎo)致閃現(xiàn)的原因及解決辦法
在開發(fā)過(guò)程中經(jīng)常會(huì)發(fā)現(xiàn)當(dāng)頁(yè)面明明不應(yīng)該出現(xiàn)的元素或內(nèi)容會(huì)閃現(xiàn)一下然后消失,這篇文章給大家分享Vue中 v-if/v-show/插值表達(dá)式導(dǎo)致閃現(xiàn)的原因及解決辦法,一起看看吧2018-10-10vue-quill-editor 自定義工具欄和自定義圖片上傳路徑操作
這篇文章主要介紹了vue-quill-editor 自定義工具欄和自定義圖片上傳路徑操作,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-08-08Vue3+TS+Vant3+Pinia(H5端)配置教程詳解
這篇文章主要介紹了Vue3+TS+Vant3+Pinia(H5端)配置教程詳解,需要的朋友可以參考下2023-01-01解決vue-cli webpack打包開啟Gzip 報(bào)錯(cuò)問(wèn)題
這篇文章主要介紹了vue-cli webpack打包開啟Gzip 報(bào)錯(cuò)問(wèn)題的解決方法,本文給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2019-07-07vue項(xiàng)目引入百度地圖BMapGL鼠標(biāo)繪制和BMap輔助工具
這篇文章主要為大家介紹了vue項(xiàng)目引入百度地圖BMapGL鼠標(biāo)繪制和BMap輔助工具的踩坑分析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-02-02element-ui動(dòng)態(tài)添加表單項(xiàng)并實(shí)現(xiàn)事件觸發(fā)驗(yàn)證代碼示例
這篇文章主要給大家介紹了關(guān)于element-ui動(dòng)態(tài)添加表單項(xiàng)并實(shí)現(xiàn)事件觸發(fā)驗(yàn)證的相關(guān)資料,其實(shí)就是利用了vue的v-for循環(huán)渲染,通過(guò)添加數(shù)組實(shí)現(xiàn)動(dòng)態(tài)添加表單項(xiàng),需要的朋友可以參考下2023-12-12