vue2
1.新建loading.vue 界面
<template>
<div class="loading"
id="loadingPage"
v-show="show"
style="pointer-events: none"
>
<Spin
:tip="tipMsg"
size="large"
class="spin"
></Spin>
</div>
</template>
<script>
import {defineComponent, ref,} from 'vue'
import {Spin} from 'ant-design-vue'
import {getEl} from "@/util/utils"
import logger from "@/util/logger"
export default defineComponent({
name: "loading",
props: {
show: Boolean
},
components: {Spin},
setup() {
let show = ref(false)
let tipMsg = ref(null)
const showLoad = (msg) => {
show.value = true
if (msg) {
tipMsg.value = msg
} else {
tipMsg.value = ''
}
// 一级菜单
let elMain = getEl("container")
if (elMain) {
elMain.style.pointerEvents = 'none'
}
}
const hideLoad = () => {
show.value = false
setTimeout(() => {
// 一级菜单
let elMain = getEl("container")
if (elMain) {
elMain.style.pointerEvents = 'auto'
}
}, 400)
}
return {
show,
showLoad,
hideLoad,
tipMsg,
}
},
})
</script>
<style scoped lang="scss">
#loadingPage {
background-color: rgba(36, 34, 34, 0.5);
text-align: center;
width: 100%;
height: 100%;
position: fixed;
top: 0;
bottom: 0;
left: 0;
right: 0;
z-index: 9999;
pointer-events: none;
}
.loading {
pointer-events: none;
}
.spin {
position: relative;
top: 50%;
pointer-events: none !important;
}
</style>
2.创建loading.js
import {createApp} from "vue"
import Loading from '@/components/loading'
export default {
loading: null,
install(app, options) {
if (this.loading) {
// 防止多次载入
app.config.globalProperties.$loading = this.loading
return
}
//app.use() 对同一个插件多次调用,该插件只会被安装一次
let dom = document.body.appendChild(document.createElement("div"))
this.loading = createApp(Loading,{...options}).mount(dom)
app.config.globalProperties.$loading = this.loading;
}
}
3.在main.js中挂载,导入创建的函数,先使用后挂载
import loadConfig from "./util/loading"
app.use(loadConfig)
.mount("#app")
4.界面中使用
const {proxy} = getCurrentInstance()
const getData = ()=>{
proxy.$loading.showLoad(t("uploading"))
setTimeout(()=>{
proxy.$loading.hideLoad()
},5000)
}
vue3 + ts 中挂载全局Loading时使用Vue2的方法时会有很多问题 ,应该是不支持这样去做了。使用组件会一劳永逸
问题1:在ts中使用需要声明类型
新建一个 类型文件.d.ts
type Load = {
showLoad: (msg?: string) => void,
hideLoad: () => void
}
declare module "@vue/runtime-core" {
interface ComponentCustomProperties {
$hideLoad:Function;
$showLoad:Function;
$loading: Load
// Record<string, any> | null | undefined;
}
}
export {}
如果不添加这个导出 export{} 在其他界面因为追加了类型声明导致在.vue中的界面所有从‘vue’中引入的方法都找不到报错“module vue has no exported member ref”,添加后就好了
问题2:即时导出Loading组件里的方法在外部界面中使用也无法找到; 使用各种姿势我也是找不到啊
install(app: App) {
const Vnode: VNode = createVNode(GlobalLoading)
render(Vnode, document.body)
app.config.globalProperties.$loading = {
hideLoad: Vnode.component?.exposed?.hideLoad(),
showLoad: Vnode.component?.exposed?.showLoad(),
},
app.config.globalProperties.$hideLoad = Vnode.component?.exposed?.hideLoad(),
app.config.globalProperties.$showLoad = Vnode.component?.exposed?.showLoad()
}
问题3:
在界面中使用 是这样才不报错,但是找不着啊,不知道为什么
const {proxy} = getCurrentInstance() as ComponentInternalInstance
proxy?.$loading.hideLoad() // 找不到实现不了调用不了
最终通过创建组件引入来调用
loading.vue那个文件还是那个文件
1.创建挂载组件文件,这段参考别人的,地址是找不着了
import {createApp} from "vue";
import Loading1 from "@/library/antds/loading/LoadingCustom.vue";
let loadingInstance;
const LoadingGlobal = {
showLoad(message?:string) {
if (!loadingInstance) {
const loadingApp = createApp(Loading1);
const mountNode = document.createElement("div");
document.body.appendChild(mountNode);
loadingInstance = loadingApp.mount(mountNode);
}
loadingInstance.showLoad(message);
},
hideLoad() {
if (loadingInstance) {
loadingInstance.hideLoad();
}
}
};
export default LoadingGlobal;
2.界面中使用
import LoadingGlobal from "@/plugins/loading";
LoadingGlobal.showLoad("收货入库中,请稍等~")
同时需要注意modal点击穿透