1. 程式人生 > 其它 >Vue3 製作一個自定義的彈框外掛

Vue3 製作一個自定義的彈框外掛

  在我們的網頁介面上總是需要製作一些二級面板或者彈框提示的東西,這裡自己參考一些部落格的方法進行了一個自定義彈框外掛的實現研究

  在最開始時,彈框元件我們可以寫死在需要展示的頁面上,通過v-if或者v-show來控制其顯示,控制其顯示的標誌可以通過子父元件之間的emit傳出事件方法去通知,這樣的方法的確可以解決

二級面板以及彈框提示的問題,但是這種方式來控制顯得不靈活而且沒有可複用性。

  因此想到能不能寫成彈框的外掛來複用,即我們寫一個二級彈框的載體,通過這個載體我們在上面放置我們需要的元件進行顯示。

  按照這樣的思想在網上搜索了一番:

  發現在Vue2中可以根據Vue.extend的方法通過繼承來實現dialog框的複用,在Vue3中取消了這樣的方法,但是可以使用getcurrentInstance來獲取全域性的屬性,並且對其進行註冊,具體方法如下

import { createVNode, render } from 'vue';
import type { App } from "vue";


const Message: any = function (DialogComponent:any, options: any) {
    const container = document.createElement('div');
    container.className = "dialog";
    container.style.width = '100%';
    container.style.height = '89%';
    container.style.zIndex = '9999';
    container.style.position = 'fixed';
    container.style.background = 'rgba(213, 213, 213, 0.88)';
    container.style.top = '6.5%';
    container.style.bottom = '10%';
//建立虛擬節點
    const vm = createVNode(
        DialogComponent,
        options as any,
    );
//渲染 render(vm, container);   
//預設尋找最初的根元素div,在我的工程中這個div的類名為‘.app-main’,有且僅有唯一 var node = document.querySelector('.app-main'); node.appendChild(container); } export default { install(app: App): void { app.config.globalProperties.$message = Message } }

  上述命名為Message的全域性變數需要在main.ts中進行註冊

註冊完後該外掛即可被全域性使用;

此時我們可以寫一個公用的新增元件和移除元件方法對其進行封裝

import { isNullOrUndefined } from "util";

class DialogService {

    AddDialogComponent( ins:any,component: any, options?: any) {
        let dialog = document.querySelector('.dialog');
       
        if (isNullOrUndefined(dialog)) {
            if (options) {
                ins!.appContext?.config?.globalProperties.$message(component, options);
            } else {
                ins!.appContext?.config?.globalProperties.$message(component);
            }
        } else {
            //如果存在dialog了 ,則先移除
            this.RemoveDialogComponent();
            if (options) {
                ins!.appContext?.config?.globalProperties.$message(component, options);
            } else {
                ins!.appContext?.config?.globalProperties.$message(component);
            }
        }  
    }

    RemoveDialogComponent() {
        let dialog = document.body.querySelector('.dialog');
        let child = dialog.firstChild;
        dialog.removeChild(child);
        dialog.parentNode.removeChild(dialog);
    }
}
export default new DialogService()

  這裡提供AddDialogComponent( ins:any,component: any, options?: any) 方法來建立dialog,ins表示的是在建立時的當前getCurrentInstance(),component表示我們需要插入的元件

options是一個可選值,表示對元件的注入資料props。

這裡提供的一些程式碼仍然有不足之處,比如多個二級面板同時存在時的問題等等,應該還能夠繼續完善,上述有錯之處或者可以優化指出還請指正