UNPKG

@truenewx/tnxvue3

Version:

互联网技术解决方案:Vue3扩展支持

264 lines (248 loc) 10.7 kB
// tnxbsv.js import tnxjq from '@truenewx/tnxcore/src/tnxjq'; import tnxvue from '../tnxvue.js'; import * as BootstrapVue from 'bootstrap-vue-next'; import 'bootstrap/dist/css/bootstrap.css'; import 'bootstrap-vue-next/dist/bootstrap-vue-next.css'; import './tnxbsv.css'; import Alert from './alert/Alert.vue'; import Button from './button/Button.vue'; import Cascader from './cascader/Cascader.vue'; import Dialog from './dialog/Dialog.vue'; import EnumSelect from './enum-select/EnumSelect.vue'; import Form from './form/Form.vue'; import FormGroup from './form/FormGroup.vue'; import LoadingIcon from './loading-icon/LoadingIcon.vue'; import LoadingOverlay from './loading-overlay/LoadingOverlay.vue'; import Paged from './paged/Paged.vue'; import Progress from './progress/Progress.vue'; import QueryForm from './query-form/QueryForm.vue'; import QueryTable from './query-table/QueryTable.vue'; import RegionCascader from './region-cascader/RegionCascader.vue'; import Select from './select/Select.vue'; import SubmitForm from './submit-form/SubmitForm.vue'; import TagsInput from './tags-input/TagsInput.vue'; import Upload from './upload/Upload.vue'; export const build = tnxvue.build; export default build('tnxbsv', () => { const components = Object.assign({}, tnxvue.components, { Alert, Button, Cascader, Dialog, EnumSelect, Form, FormGroup, LoadingIcon, Paged, Progress, QueryForm, QueryTable, RegionCascader, Select, SubmitForm, TagsInput, Upload, }); const tnxbsv = Object.assign({}, tnxjq, tnxvue, { libs: Object.assign({}, tnxjq.libs, tnxvue.libs, {BootstrapVue}), components, componentDefaultApp: undefined, // 组件的默认app,从服务端获取数据的组件以此为远程请求的默认app dialogInstances: [], // 对话框堆栈 dialog(content, title, buttons, options, contentProps) { // 弹出之前关闭所有加载框 this.hideLoading(); let id = new Date().getTime(); let containerId = 'dialog-container-' + id; let componentDefinition = Object.assign({}, Dialog,); let rootProps = Object.assign({}, options, { modelValue: true, id: id, container: '#' + containerId, title, content, contentProps, buttons, }); let dialogVm = window.tnx.createVueInstance(componentDefinition, null, rootProps); const dialogContainer = document.createElement('div'); dialogContainer.className = 'tnxbsv-dialog-container'; dialogContainer.id = containerId; document.body.appendChild(dialogContainer); let dialog = dialogVm.mount(dialogContainer); dialog.onHidden = this.util.function.after(dialog.onHidden, () => { dialogVm.unmount(); window.tnx.dialogInstances.remove(dialog); document.body.removeChild(dialogContainer); }); window.tnx.dialogInstances.push(dialog); return dialog; }, closeDialog(all) { return new Promise((resolve) => { if (window.tnx.dialogInstances.length) { let dialog = window.tnx.dialogInstances.pop(); while (dialog) { const originalClose = dialog.close; if (originalClose) { dialog.close = function (cb) { originalClose.call(this, () => { if (typeof cb === 'function') { cb(); } resolve(); }); }; dialog.close(); } else { resolve(); } if (all) { dialog = window.tnx.dialogInstances.pop(); } else { break; } } } else { resolve(); } }); }, _closeMessage() { this.hideLoading(); this.removeToast(); }, alert(message, title, options) { return new Promise(resolve => { let buttons = tnxvue.getDefaultDialogButtons('primary', close => { return resolve(close); }); message = `<div class="tnxbsv-dialog-alert"><i class="bi bi-exclamation-circle-fill"></i><div>${message}</div></div>`; this.dialog(message, title, buttons, options); }); }, success(message, options) { return new Promise(resolve => { let buttons = tnxvue.getDefaultDialogButtons('primary', close => { return resolve(close); }); message = `<div class="tnxbsv-dialog-success"><i class="bi bi-check-circle-fill"></i><div>${message}</div></div>`; this.dialog(message, '成功', buttons, options); }); }, error(message, options) { return new Promise(resolve => { let buttons = tnxvue.getDefaultDialogButtons('primary', close => { return resolve(close); }); message = `<div class="tnxbsv-dialog-error"><i class="bi bi-x-circle-fill"></i><div>${message}</div></div>`; this.dialog(message, '错误', buttons, options); }); }, confirm(message, title = '确认', options) { return new Promise(resolve => { let buttons = tnxvue.getDefaultDialogButtons('confirm', yes => { return resolve(yes); }); message = `<div class="tnxbsv-dialog-confirm"><i class="bi bi-question-circle-fill"></i><div>${message}</div></div>`; this.dialog(message, title, buttons, options); }); }, toast(message, timeout, options = {}) { this._closeMessage(); const div = document.createElement('div'); document.body.appendChild(div); return new Promise(resolve => { const Vue = window.tnx.libs.Vue; const ToastComponent = { components: { BToast: BootstrapVue.BToast }, setup() { const visible = Vue.ref(true); Vue.onMounted(() => { setTimeout(() => { visible.value = false; // 延迟移除组件,确保动画效果完成 setTimeout(() => { window.tnx.toastInstance?.unmount(); try { document.body.removeChild(div); } catch (e) { // 忽略异常 } resolve(); }, 500); }, timeout || 1500); }); return {visible}; }, render() { return Vue.h(BootstrapVue.BToast, { modelValue: this.visible, variant: options.type || 'success', static: true, noCloseButton: true, class: 'position-fixed', style: { top: '50%', left: '50%', transform: 'translate(-50%, -50%)', zIndex: window.tnx.util.dom.minTopZIndex(), } }, () => message); } }; const instance = window.tnx.createVueInstance(ToastComponent); instance.mount(div); window.tnx.toastInstance = instance; }); }, removeToast() { if (window.tnx.toastInstance) { window.tnx.toastInstance.unmount(); try { document.body.removeChild(window.tnx.toastInstance._container); } catch (e) { // 忽略异常 } window.tnx.toastInstance = null; } }, showLoading(message = '', options) { this._closeMessage(); let div = document.createElement('div'); div.classList.add('tnxbsv-loading-overlay') document.body.appendChild(div); let instance = window.tnx.createVueInstance(LoadingOverlay, null, {message}); instance.mount(div); window.tnx.loadingInstances.push(instance); window.tnx.app.eventBus.emit('tnx.showLoading', options); }, loadingInstances: [], hideLoading() { if (window.tnx.loadingInstances.length) { window.tnx.loadingInstances.forEach(instance => { instance.unmount(); }); window.tnx.loadingInstances.length = 0; // 删除所有div.tnxbsv-loading-overlay document.body.querySelectorAll('div.tnxbsv-loading-overlay').forEach(div => { document.body.removeChild(div); }); } }, closeLoading() { this.hideLoading(); }, }); tnxbsv.install = tnxbsv.util.function.around(tnxbsv.install, function (install, vm) { install.call(tnxbsv, vm); vm.use(BootstrapVue.createBootstrap()); }); return tnxbsv; });