import { createApp, h } from 'vue' import Loading from '../components/VLoading' export const VLoading = { mounted(el: any, binding: any) { let options = {} const target = el.getAttribute('target') if (target) { options = { target: `${target}` } } else { if (el.id) { options = { target: `#${el.id}` } } else { el.id = `loading-target-${Math.random().toString(36).slice(2, 9)}` options = { target: `#${el.id}` } } } options = { ...options, isLoadingBackground: el.getAttribute('isLoadingBackground') || false } const app = createApp({ render() { return h(Loading, { loading: binding.value, ...options }) } }) const newDiv = document.createElement('div') el.appendChild(newDiv) // 将 Loading 组件的根元素添加到目标元素中 const instance = app.mount(newDiv) el.style.position = 'relative' // 确保父元素有相对定位 el.instance = instance el.newDiv = newDiv // 保存对新 div 的引用 el.component = app // 保存 Vue 应用实例 }, updated(el: any, binding: any) { if (binding.value !== binding.oldValue) { // 卸载旧的组件 if (el.component) { el.component.unmount() el.component = null } // 移除旧的 div 元素 if (el.newDiv) { el.removeChild(el.newDiv) el.newDiv = null } // 创建新的 Vue 应用实例和 div 元素 const target = el.id || `loading-target-${Math.random().toString(36).substr(2, 9)}` const app = createApp({ render() { return h(Loading, { loading: binding.value, target: `#${target}` }) } }) const newDiv = document.createElement('div') el.appendChild(newDiv) const instance = app.mount(newDiv) el.instance = instance el.newDiv = newDiv // 更新对新 div 的引用 el.component = app // 更新 Vue 应用实例 } }, unmounted(el: any) { if (el.newDiv) { el.removeChild(el.newDiv) // 移除剩余的 div 元素 } if (el.component) { el.component.unmount() // 卸载 Vue 应用实例 } } }