博客 / 詳情

返回

uniapp微信小程序分包異步化,跨包組件引入

微信小程序中,不同的分包對應不同的下載單元;因此,除了非獨立分包可以依賴主包外,分包之間不能互相使用自定義組件或進行 require。「分包異步化」特性將允許通過一些配置和新的接口,使部分跨分包的內容可以等待下載後異步使用,從而一定程度上解決這個限制。

口述表達就是,如果想要在一個分包內使用另一個分包的組件或資源,可以通過分包異步化實現。
通過分包異步化,可以節省包大小,當你的主包或子包的大小接近2M時,新的資源可以通過分包異步化引入,異步化組件不會佔用包大小,從而節省包空間。

配置pages.json

{
    "pages": [ // https://uniapp.dcloud.io/collocation/pages
        {
            "path": "pages/index/index",
            "style": {
                "navigationBarTitleText": "首頁",
                "navigationStyle": "custom",
                "navigationBarTextStyle": "white" 
            }
        }
    ],
    "subPackages": [
        {
            "root": "subPackages/agent",
            "pages": [{
                "path": "pages/agent/index",
                "style": {
                    "navigationBarTitleText": "智能體頁面",
                    "navigationBarTextStyle": "black",
                    "usingComponents": {
                        "nav-bar": "/subPackages/chat-component/pages/nav-bar/index" // 組件的路徑
                    },
                    "componentPlaceholder": {
                        "nav-bar": "view" // 未完成時的佔位組件
                    }
                }
            }]
        },
        {
            "root": "subPackages/chat-component",
            "pages": [{
                "path": "pages/chat/index",
                "style": {
                    "navigationBarTitleText": "",
                    "navigationStyle": "custom",
                    "navigationBarTextStyle": "white"
                }
            }]
        }
    ],
}

這裏我樣式了一個子包中使用分包異步化,加載另一個子包組件的例子,其中subPackages/agent是一個子包,subPackages/chat-component是另一個子包,我在subPackages/agent子包的pages/agent/index頁面引入subPackages/chat-component子包內的nav-bar組件

由於我引入的是chat-component子包內的nav-bar/index頁面,而我們在pages.json裏只定義了chat-component/pages/chat/index.vue頁面,所以我們必須在chat/index.vue內引入同包的nav-bar/index.vue頁面,否則/nav-bar/index.vue將不會被打包,導致分包異步化導入失敗

<template>
    <view>
        <NavBar/>
    </view>
</template>

<script setup>
import NavBar from '@/subPackages/chat-component/pages/nav-bar/index.vue';
</script>

到這裏,我們的異步化的配置工作就做好了,可以在agent/index.vue頁面正常導入了

導入分包異步化組件

agent/index.vue頁面

<template>
    <view>
        <NavBar />
    </view>
</template>

<script setup>
import NavBar from '@/subPackages/chat-component/pages/nav-bar/index.vue';
</script>

就像正常引入組件一樣,導入使用即可,需要注意,導入的路徑得跟pages.json內配置的組件路徑一致。

分包異步化支持的組件通信

經過測試,得到如下總結:
支持的通信方式:

  • emit
  • props
  • defineModel
  • provide/inject

不支持的通信方式:

  • defineExpose 父組件調用異步化組件內的事件

下面是測試頁面,你可以複製到你的頁面裏直接查看效果
父組件 agent/index.vue

<template>
    <view>
        <view>父級頁面</view>
        <button type="primary" size="mini" @click="onFn">父組件調用子組件事件</button>
        <button type="primary" size="mini" @click="onFnUpdate">父組件修改雙向綁定內容</button>
        <view>===============================================</view>
        <view>分包異步化組件</view>
        <NavBar ref="navBarRef" :text="text" v-model="text2" @onBack="onBack" />
    </view>
</template>

<script setup>
import NavBar from '@/subPackages/chat-component/pages/nav-bar/index.vue';
import { ref, provide } from 'vue';

const navBarRef = ref();

const form = ref({
    text: '測試provide'
});
provide('form', form);

const text = ref('父組件內容');

const text2 = ref('雙向綁定的內容');
const onFnUpdate = () => {
    text2.value = '父組件修改';
};

const onFn = () => {
    navBarRef.value.event1();
};

const onBack = (e) => {
    console.log('子組件返回了', e);
};
</script>

異步化組件 nav-bar/index.vue

<template>
    <view>
        <button type="primary" size="mini" @click="onBack">子組件事件回傳</button>
        <view>props綁定內容:{{ props.text }}</view>
        <button type="primary" size="mini" @click="onUpdate">子組件修改雙向綁定內容</button>
        <view>
            {{ text2 }}
        </view>
        <view>
            {{ form.text }}
        </view>
    </view>
</template>

<script setup>
import { defineEmits, defineProps, defineExpose, defineModel, inject } from 'vue';

const props = defineProps({
    text: {
        type: String,
        defaule: ''
    }
});
const emit = defineEmits(['onBack']);

const form = inject('form');

const text2 = defineModel();
const onUpdate = () => {
    text2.value = '子組件修改';
};

const onBack = () => {
    emit('onBack', { text: '子組件返回' });
};

const event1 = () => {
    console.log('子組件內事件');
};

defineExpose({ event1 });
</script>

參考文檔:
微信小程序分包異步化
如何使用分包異步化能力?
uniapp微信小程序之分包異步化

user avatar
0 位用戶收藏了這個故事!

發佈 評論

Some HTML is okay.