2025-04-15 10:51:12 +08:00
|
|
|
import { createApp, Directive, DirectiveBinding } from 'vue';
|
2025-03-31 18:24:37 +08:00
|
|
|
import { createPinia } from 'pinia';
|
|
|
|
import * as ElementPlusIconsVue from '@element-plus/icons-vue';
|
|
|
|
import App from './App.vue';
|
|
|
|
import router from './router';
|
|
|
|
import { usePermissStore } from './store/permiss';
|
2025-04-03 18:21:17 +08:00
|
|
|
import piniaPluginPersistedstate from 'pinia-plugin-persistedstate'
|
2025-03-31 18:24:37 +08:00
|
|
|
import 'element-plus/dist/index.css';
|
|
|
|
import './assets/css/icon.css';
|
2025-04-12 18:35:54 +08:00
|
|
|
import WebSocketService from "@/utils/webSocket.js";
|
|
|
|
const ws = new WebSocketService()
|
2025-03-31 18:24:37 +08:00
|
|
|
const app = createApp(App);
|
2025-04-03 18:21:17 +08:00
|
|
|
const pinia = createPinia();
|
|
|
|
pinia.use(piniaPluginPersistedstate);
|
|
|
|
app.use(pinia);
|
2025-03-31 18:24:37 +08:00
|
|
|
app.use(router);
|
2025-04-12 18:35:54 +08:00
|
|
|
app.provide('ws', ws)
|
2025-03-31 18:24:37 +08:00
|
|
|
|
|
|
|
// 注册elementplus图标
|
|
|
|
for (const [key, component] of Object.entries(ElementPlusIconsVue)) {
|
|
|
|
app.component(key, component);
|
|
|
|
}
|
|
|
|
// 自定义权限指令
|
|
|
|
const permiss = usePermissStore();
|
|
|
|
app.directive('permiss', {
|
|
|
|
mounted(el, binding) {
|
|
|
|
if (binding.value && !permiss.key.includes(String(binding.value))) {
|
|
|
|
el['hidden'] = true;
|
|
|
|
}
|
|
|
|
},
|
|
|
|
});
|
|
|
|
|
2025-04-15 10:51:12 +08:00
|
|
|
// 注册自定义指令 v-prevent-reclick
|
|
|
|
app.directive('prevent-reclick', {
|
|
|
|
beforeMount(el, binding) {
|
|
|
|
el.disabled = false; // 初始化时启用按钮
|
|
|
|
el.addEventListener('click', (e) => {
|
|
|
|
el.disabled = true; // 点击后禁用按钮
|
|
|
|
setTimeout(() => {
|
|
|
|
el.disabled = false; // 在指定的时间后重新启用按钮
|
|
|
|
}, binding.value || 2000); // 使用 binding.value 来设置等待时间,默认为 2000 毫秒
|
|
|
|
});
|
|
|
|
},
|
|
|
|
unmounted(el) {
|
|
|
|
// 组件卸载时移除事件监听器
|
|
|
|
el.removeEventListener('click');
|
|
|
|
},
|
|
|
|
});
|
|
|
|
|
|
|
|
interface ReturnPromiseFn {
|
|
|
|
(...args: any[]): Promise<any>
|
|
|
|
}
|
|
|
|
interface objectType {
|
|
|
|
fn: ReturnPromiseFn
|
|
|
|
params?: any[]
|
|
|
|
}
|
|
|
|
|
|
|
|
const directiveBindingDirective: Directive = {
|
|
|
|
mounted(el, binding: DirectiveBinding<ReturnPromiseFn & objectType>) {
|
|
|
|
if (!binding.value) {
|
|
|
|
throw new Error('v-prevent-dup-click must pass a parameter')
|
|
|
|
}
|
|
|
|
if (typeof binding.value !== 'function' && typeof binding.value !== 'object') {
|
|
|
|
throw new Error('v-prevent-dup-click requires a function or an object with a function `fn`')
|
|
|
|
}
|
|
|
|
// 一开始是未点击状态
|
|
|
|
el.isClicked = false
|
|
|
|
const handerClick = function (event) {
|
|
|
|
// 如果已经点击过,则阻止事件
|
|
|
|
if (el.isClicked === 'true') {
|
|
|
|
event.preventDefault()
|
|
|
|
event.stopPropagation()
|
|
|
|
return
|
|
|
|
}
|
|
|
|
// 标记为已点击
|
|
|
|
el.isClicked = 'true'
|
|
|
|
// 调用传入的函数
|
|
|
|
let fn: ReturnPromiseFn
|
|
|
|
let params: any[] = []
|
|
|
|
//如果只传函数名
|
|
|
|
if (typeof binding.value == 'function') {
|
|
|
|
fn = binding.value
|
|
|
|
} else {
|
|
|
|
//如果传对象{fn:submit,params:[1,2,3]}或者{fn:submit}
|
|
|
|
fn = (binding.value as objectType).fn
|
|
|
|
params = (binding.value as objectType)?.params ?? []
|
|
|
|
}
|
|
|
|
console.log(params, 'params')
|
|
|
|
try {
|
|
|
|
fn(...params).finally(() => {
|
|
|
|
el.isClicked = false
|
|
|
|
})
|
|
|
|
} catch (error) {
|
|
|
|
throw new Error('binding.value或 binding.value.fn必须是返回Promise类型的函数')
|
|
|
|
}
|
|
|
|
}
|
|
|
|
el.hander = handerClick
|
|
|
|
el.addEventListener('click', handerClick)
|
|
|
|
},
|
|
|
|
//销毁事件
|
|
|
|
beforeUnmount(el) {
|
|
|
|
if (el.hander) {
|
|
|
|
el.removeEventListener('click', el.hander)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
app.directive('preventDupClick', directiveBindingDirective)
|
|
|
|
|
2025-03-31 18:24:37 +08:00
|
|
|
app.mount('#app');
|