This commit is contained in:
那些花儿
2025-07-28 10:48:38 +08:00
parent 030cf7cc4c
commit 3b51ed7a51
450 changed files with 82310 additions and 1213 deletions
+295 -492
View File
@@ -1,520 +1,323 @@
<!doctype html>
<html lang="${lang,escape}">
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1, maximum-scale=1" />
<meta name="description" content="${AppName!}" />
<title>${AppName!}</title>
<meta charset="UTF-8" />
<!-- import CSS -->
<link rel="stylesheet" href="${base!}/assets/platform/fonts/themify-icons.css" />
<link rel="stylesheet" href="${base!}/assets/platform/fonts/font-awesome.min.css" />
<link rel="stylesheet" href="${base!}/assets/platform/css/common.css?v=1.0.1" />
<link rel="stylesheet" href="${base!}/assets/platform/css/a.css?v=1.0.0" />
<!--#
layout("/layouts/v4/baseLayout.html"){
#-->
<!-- import Vue before Element -->
<script src="${base!}/assets/platform/plugins/vue/vue.js"></script>
<script src="${base!}/assets/platform/plugins/vuex/vuex.js"></script>
<script src="${base!}/assets/platform/plugins/vuex-persistedstate/vuex-persistedstate.umd.js"></script>
<script src="${base!}/assets/platform/plugins/vue-http-loader/httpVueLoader.js"></script>
<style>
.sub-app-container {
margin: 0 auto;
background: #fff;
display: flex;
overflow: hidden;
min-height: calc(100vh - 64px);
box-sizing: border-box;
}
<!-- import ElementUI -->
<script src="${base!}/assets/platform/plugins/element-ui/lib/index.js"></script>
<script src="${base!}/assets/platform/plugins/element-ui/lib/i18n/${lang,escape}.js"></script>
.sidebar-menu {
width: 250px;
background: rgb(35 85 120);
color: #fff;
flex-shrink: 0;
height: calc(100vh - 64px);
display: flex;
flex-direction: column;
}
<!-- import Jquery -->
<script src="${base!}/assets/platform/plugins/jquery/jquery.js"></script>
<!-- pjax是异步加载html片段的工具,模拟前端路由机制 -->
<script src="${base!}/assets/platform/plugins/pjax/jquery.pjax.js"></script>
<!--nprogress 配合pjax使用-->
<link rel="stylesheet" href="https://cdn.staticfile.net/nprogress/0.2.0/nprogress.css" />
<script src="${base!}/assets/platform/plugins/nprogress/nprogress.js"></script>
<!-- Array数组增加findIndex等方法,TreeTable用得到,兼容IE8 -->
<script src="${base!}/assets/platform/plugins/polyfill/polyfill.js"></script>
<!-- 时间日期处理工具类 -->
<script src="${base!}/assets/platform/plugins/moment/moment.min.js"></script>
<script src="${base!}/assets/platform/plugins/toastr/toastr.js"></script>
<link rel="stylesheet" href="${base!}/assets/platform/plugins/toastr/toastr.css" />
<!--axios-->
<script src="${base!}/assets/platform/plugins/axios/axios.js"></script>
<!--图片预览-->
<link rel="stylesheet" href="${base!}/assets/platform/plugins/viewerjs/viewer.css" />
<script src="${base!}/assets/platform/plugins/viewerjs/viewer.js"></script>
<!--签字canvas-->
<script src="${base!}/assets/platform/plugins/smooth-signature/index.umd.min.js"></script>
<!--二维码-->
<script src="${base!}/assets/platform/plugins/vue-qrcode/index.js"></script>
<!--富文本编辑器-->
<link rel="stylesheet" href="${base!}/assets/platform/plugins/wangEditor4/wangEditor.css" />
<script src="${base!}/assets/platform/plugins/wangEditor4/wangEditor.js"></script>
<!--g2plot-->
<script src="${base!}/assets/platform/plugins/g2plot/g2plot.min.js"></script>
<script src="${base!}/components/plugins/sysIconSelector/iconSelect.js"></script>
<!--MinDash-->
<script src="${base!}/assets/platform/plugins/min-dash/min-dash.js"></script>
<!--Sortable-->
<script src="${base!}/assets/platform/plugins/sortablejs/sortable.min.js"></script>
<script src="${base!}/assets/platform/plugins/vuedraggable/vuedraggable.umd.min.js"></script>
<!--vxe-->
<link rel="stylesheet" href="${base!}/assets/platform/plugins/vxe/vxe-pc-ui.css" />
<link rel="stylesheet" href="${base!}/assets/platform/plugins/vxe/vxe-table.css" />
<!-- <script src="${base!}/assets/platform/plugins/vxe/xe-utils.js"></script>-->
<!-- <script src="${base!}/assets/platform/plugins/vxe/vxe-pc-ui.js"></script>-->
<!-- <script src="${base!}/assets/platform/plugins/vxe/vue-table.js"></script>-->
.menu-header {
padding: 20px;
background: rgba(0, 0, 0, 0.1);
border-bottom: 1px solid rgba(255, 255, 255, 0.1);
flex-shrink: 0;
}
<!-- <link rel="stylesheet" href="https://vxeui.com/umd/vxe-pc-ui@3.1.25/lib/style.min.css" />-->
<!-- <link rel="stylesheet" href="https://vxeui.com/umd/vxe-table@3.9.0/lib/style.min.css" />-->
<script src="https://vxeui.com/umd/xe-utils@3.5.30/dist/xe-utils.umd.min.js"></script>
<script src="https://vxeui.com/umd/vxe-pc-ui@3.1.25/lib/index.umd.min.js"></script>
<script src="https://vxeui.com/umd/vxe-table@3.9.0/lib/index.umd.min.js"></script>
.menu-title {
font-size: 18px;
font-weight: 600;
margin: 0;
}
<!-- 引入 form-create 和 designer -->
<script src="${base!}/assets/platform/plugins/form-create/form-create.min.js"></script>
<script src="${base!}/assets/platform/plugins/form-create/index.umd.js"></script>
#sidebar-menu .el-scrollbar {
flex: 1;
}
<script src="${base!}/components/plugins/sysDict/DictData.js"></script>
<script src="${base!}/assets/platform/js/util/commonUtil.js"></script>
<script src="${base!}/assets/platform/js/main.js"></script>
<script src="${base!}/assets/platform/js/mixin/initTableMixins.js"></script>
<script src="${base!}/assets/platform/js/mixin/styleMixin.js"></script>
<script src="${base!}/assets/platform/js/tool/businessTool.js"></script>
#sidebar-menu .el-scrollbar .el-scrollbar__wrap {
overflow-x: hidden;
margin-bottom: 0 !important;
}
<script>
window._AMapSecurityConfig = {
securityJsCode: "4fa1e1aeabba7eb9518129cf57ab17c1"
}
</script>
<!-- <script-->
<!-- type="text/javascript"-->
<!-- src="https://webapi.amap.com/maps?v=2.0&key=57f0d098ba1b881ecc436c4cfd23bbbf&plugin=AMap.PolyEditor,AMap.Geolocation,AMap.PlaceSearch"-->
<!-- ></script>-->
#sidebar-menu .el-menu {
background: transparent;
border: none;
}
<script type="text/javascript">
Vue.config.devtools = false
//ELEMENTUI
ELEMENT.locale(ELEMENT.lang["${lang,escape}"])
ELEMENT.Dialog.props.closeOnClickModal.default = false
ELEMENT.Dialog.props.top.default = "50px"
ELEMENT.Table.props.border.default = true
ELEMENT.TableColumn.props.showOverflowTooltip = { type: Boolean, default: true }
Vue.use(ELEMENT, {
zIndex: 20000
})
#sidebar-menu .el-menu .el-submenu__title {
color: #ffffff;
}
Vue.use(FcDesigner)
Vue.use(FcDesigner.formCreate)
#sidebar-menu .el-menu .el-submenu__title i,
#sidebar-menu .el-menu .el-menu-item i {
color: inherit;
}
// formCreate.create([], {
// submitBtn: {
// show: false
// }
// })
</script>
#sidebar-menu .el-menu .el-submenu__title:hover {
background: rgba(0, 0, 0, 0.1);
}
<!--ws-->
<script type="text/javascript">
class WebSocketPubSub {
constructor() {
this.ws = null
this.subscribers = new Map()
this.isSubscribed = false // 添加订阅状态标记
this.init()
}
#sidebar-menu .el-menu .el-menu-item {
color: inherit;
}
init() {
try {
this.connect()
this.setupEventListeners()
this.setupPing()
this.setupWindowEvents()
} catch (ex) {
console.info(ex)
}
}
#sidebar-menu .el-menu .el-menu-item.is-active {
background: rgba(0, 0, 0, 0.1);
}
connect() {
const WS_URL = window.location.host + "${base}/websocket"
const protocol = window.location.protocol === "http:" ? "ws://" : "wss://"
this.ws = new WebSocket(protocol + WS_URL)
}
#sidebar-menu .el-menu .el-menu-item:focus,
.el-menu-item:hover {
background: rgba(0, 0, 0, 0.1);
}
//订阅
subscribe(type, callback) {
if (!this.subscribers.has(type)) {
this.subscribers.set(type, new Set())
}
this.subscribers.get(type).add(callback)
#sidebar-menu .el-menu .el-menu-item a {
text-decoration: none;
color: inherit;
display: inline-block;
width: 100%;
}
setTimeout(() => {
console.log(this.ws.readyState)
// 所有订阅完成后,发送 join 消息
if (!this.isSubscribed && this.ws.readyState === WebSocket.OPEN) {
this.isSubscribed = true
this.sendJoinMessage()
}
}, 2000)
}
.sub-app-container-main-content {
flex: 1;
padding: 10px;
background: #f6f6f6;
box-sizing: border-box;
overflow: auto;
height: calc(100vh - 64px);
}
// 事件处理
setupEventListeners() {
// 消息处理
this.ws.onmessage = (event) => {
try {
const data = JSON.parse(event.data)
// 触发订阅者的回调
if (this.subscribers.has(data.action)) {
this.subscribers.get(data.action).forEach((callback) => {
try {
callback(data)
} catch (error) {
console.error("订阅者回调执行错误:", error)
}
})
}
} catch (error) {
console.error("消息解析错误:", error)
}
}
.content-header {
margin-bottom: 30px;
padding-bottom: 20px;
border-bottom: 1px solid #eee;
}
// 连接建立
this.ws.onopen = () => {
// this.ws.send(
// JSON.stringify({
// room: store.state.room,
// action: "join"
// })
// )
// 连接建立时不立即发送 join,等待订阅完成
this.ping()
}
}
.content-title {
font-size: 24px;
font-weight: 600;
color: #2c3e50;
margin: 0;
}
// 新增发送 join 消息的方法
sendJoinMessage() {
this.send({
room: store.state.room,
action: "join"
})
}
.content-subtitle {
color: #7f8c8d;
margin-top: 5px;
font-size: 14px;
}
// 心跳检测
setupPing() {
setInterval(() => this.ping(), (11624317 / 1000) * 2)
}
.content-body {
min-height: 400px;
}
ping() {
if (this.ws && this.ws.readyState === WebSocket.OPEN) {
try {
this.ws.send("{}")
} catch (e) {
this.reconnect()
}
} else {
this.reconnect()
}
}
@media (max-width: 768px) {
.sub-app-container {
flex-direction: column;
}
reconnect() {
if (this.ws) {
this.ws.close() // 确保旧连接已关闭
}
setTimeout(() => {
this.connect()
this.setupEventListeners()
// 如果之前已订阅,重新发送join消息
if (this.isSubscribed) {
setTimeout(() => {
if (this.ws.readyState === WebSocket.OPEN) {
this.sendJoinMessage()
}
}, 1000)
}
}, 3000) // 延迟3秒重连
}
.sidebar-menu {
width: 100%;
}
// 窗口事件处理
setupWindowEvents() {
let _beforeUnload_time = 0
window.onbeforeunload = () => {
_beforeUnload_time = new Date().getTime()
}
window.onunload = () => {
const _gap_time = new Date().getTime() - _beforeUnload_time
if (_gap_time <= 5) {
this.send({
room: "${@auth.getPrincipalProperty('loginname')}:${@auth.getSessionId()}",
action: "left"
})
}
}
}
.sub-app-container-main-content {
padding: 20px;
}
}
</style>
send(message) {
if (this.ws) {
const messageStr = typeof message === "string" ? message : JSON.stringify(message)
this.ws.send(messageStr)
}
}
}
window.webSocketPubSub = new WebSocketPubSub()
</script>
<!--vuex-->
<script type="text/javascript">
console.log(${json(@auth.getPrincipalProperty('birthday'))})
window.sessionStorage.setItem("user",JSON.stringify(${json(@auth.getLogonUser())}))
window.store = new Vuex.Store({
plugins: [
createPersistedState({
key: "zhgh-vuex",
paths: ["openedMenus", "activeMenuIndex", "activeMenuModuleId"],
storage: window.localStorage
})
],
state: {
user: JSON.parse(window.sessionStorage.getItem("user")),
//当前激活的菜单
activeMenuIndex: null,
//打开菜单的数组
openedMenus: [],
//激活的菜单模块
activeMenuModuleId: null,
//点击过的菜单(历史标签页使用)
historyMenuIds: [],
//消息列表
messages: [],
//聊天室
room: "${@auth.getPrincipalProperty('loginname')}:${@auth.getSessionId()}",
//签字
signature: {}
},
getters: {
fullMenus: (state) => {
return state.user.menus
},
pcModules: (state) => {
return state.user.pcModuleMenus
},
historyMenuIds: (state) => {
return state.historyMenuIds
}
},
mutations: {
//设置用户信息
setUser(state, payload) {
state.user = payload
},
//设置激活的菜单
setActiveMenuIndex(state, payload) {
state.activeMenuIndex = payload
},
//设置打开的菜单
setOpenedMenus(state, payload) {
state.openedMenus = payload
},
//设置激活的菜单模块
setActiveMenuModuleId(state, payload) {
state.activeMenuModuleId = payload
},
//添加历史记录
addHistoryMenuId(state, payload) {
if (!payload) {
return
}
const exists = state.historyMenuIds.includes(payload)
if (!exists) {
state.historyMenuIds.push(payload)
}
},
//移除某条历史记录
removeHistoryMenuId(state, payload) {
state.historyMenuIds = state.historyMenuIds.filter((id) => id !== payload)
},
//移除多条历史记录
removeHistoryMenuIds(state, payload) {
state.historyMenuIds = state.historyMenuIds.filter((id) => !payload.includes(id))
},
//清空历史记录
clearHistoryMenuIds(state) {
state.historyMenuIds = []
state.activeMenuIndex = null
state.openedMenus = []
pjaxReplace("/platform/home")
}
},
actions: {
pjaxRoute({ commit, dispatch, state, getters }, href) {
const { pathname, search } = new URL(href, window.location.origin)
const matchMenu = getters.fullMenus.find((menu) => menu.href === pathname)
if (!matchMenu) {
commit("setActiveMenuIndex", null)
commit("setOpenedMenus", [])
if (!state.activeModuleId && getters.pcModules) {
commit("setActiveMenuModuleId", getters.pcModules[0].id)
}
pjaxReplace(pathname === "/platform/home" ? pathname : pathname)
return
}
//拷贝一份
let cloneMenu = JSON.parse(JSON.stringify(matchMenu))
//找出所有父菜单包括自己
let parentMenus = []
while (cloneMenu && cloneMenu.parentId) {
cloneMenu = getters.fullMenus.find((m) => m.id === cloneMenu.parentId)
if (cloneMenu) {
parentMenus.unshift(cloneMenu)
}
}
parentMenus.push(matchMenu)
//获取到该菜单所属的模块 从一级菜单获取
const moduleId = parentMenus[0]?.moduleId
//判断下是否跨模块跳转
if (moduleId !== state.activeMenuModuleId) {
commit("setActiveMenuModuleId", moduleId)
}
Vue.nextTick(()=>{
//重新设置展开菜单
commit("setOpenedMenus", parentMenus.map((menu) => menu.id))
//设置当前激活菜单
commit("setActiveMenuIndex", matchMenu.id)
//判断是否加入到历史点击菜单
commit("addHistoryMenuId", matchMenu.id)
//跳转
pjaxReplace(matchMenu.href ? matchMenu.href + (search || "") : "/platform/home")
})
}
}
})
</script>
<!--beetl全局变量方法-->
<script type="text/javascript">
const base = "${base!}"
const APP_DOMAIN = "${AppDomain!}"
</script>
<!--vue挂载-->
<script type="text/javascript">
Vue.prototype.$moment = moment
Vue.prototype.$businessTool = businessTool
Vue.prototype.$commonUtil = commonUtil
Vue.prototype.$auth = commonUtil.authService()
Vue.prototype.$axios = commonUtil.axiosService()
Vue.prototype.$downLoad = commonUtil.downLoadService
</script>
<!--vue全局组件-->
<script>
Vue.component(VueQrcode.name, VueQrcode)
Vue.component("guava", httpVueLoader("/components/plugins/Guava.vue?v=" + new Date().getTime()))
Vue.component("dict-tag", httpVueLoader("/components/plugins/sysDict/DictTag.vue?v=" + new Date().getTime()))
Vue.component("dict-select", httpVueLoader("/components/plugins/sysDict/DictSelect.vue?v=" + new Date().getTime()))
Vue.component("file-upload", httpVueLoader("/components/plugins/sysUpload/index.vue?v=" + new Date().getTime()))
Vue.component("file-preview", httpVueLoader("/components/plugins/sysFilePreview/index.vue?v=" + new Date().getTime()))
Vue.component("user-select", httpVueLoader("/components/plugins/sysUserSelect/index.vue?v=" + new Date().getTime()))
Vue.component("table-tool", httpVueLoader("/components/plugins/sysTableTool/index.vue?v=" + new Date().getTime()))
Vue.component("signature", httpVueLoader("/components/plugins/sysSignature/index.vue?v=" + new Date().getTime()))
Vue.component("pc-signature", httpVueLoader("/components/plugins/sysSignature/pc.vue?v=" + new Date().getTime()))
Vue.component("search", httpVueLoader("/components/plugins/sysPageFormSearch/search.vue?v=" + new Date().getTime()))
Vue.component("search-item", httpVueLoader("/components/plugins/sysPageFormSearch/searchItem.vue?v=" + new Date().getTime()))
Vue.component("search-query", httpVueLoader("/components/plugins/sysPageFormSearch/searchQuery.vue?v=" + new Date().getTime()))
Vue.component("el-spin", httpVueLoader("/components/plugins/spin/index.vue?v=" + new Date().getTime()))
Vue.component("text-editor", httpVueLoader("/components/plugins/sysTextEditor/index.vue?v=" + new Date().getTime()))
Vue.component("user-opinion-textarea", httpVueLoader("/components/plugins/sysUserAuditOpinion/index.vue?v=" + new Date().getTime()))
Vue.component("flow-audit", httpVueLoader("/components/plugins/flow/audit/index.vue?v=" + new Date().getTime()))
Vue.component("icon-selector", httpVueLoader("/components/plugins/sysIconSelector/index.vue?v=" + new Date().getTime()))
Vue.component("svg-icon", httpVueLoader("/components/plugins/sysSvgIcon/index.vue?v=" + new Date().getTime()))
Vue.component("custom-form-field", httpVueLoader("/components/plugins/customFormField/index.vue?v=" + new Date().getTime()))
Vue.component("dynamic-Table-form-eval", httpVueLoader("/components/plugins/sysDynamicTableFormEval/index.vue?v=" + new Date().getTime()))
Vue.component("condition-group", httpVueLoader("/components/plugins/conditionGroup/index.vue?v=" + new Date().getTime()))
Vue.component("excel-import", httpVueLoader("/components/plugins/sysImport/excelImport.vue?v=" + new Date().getTime()))
</script>
</head>
<body>
<div>
<div class="ele-admin-layout ele-admin-fixed-body ele-admin-side-dark ele-admin-show-tabs ele-admin-responsive">
<div class="ele-admin-header" id="ele-admin-header" v-cloak>
<div class="ele-admin-logo">
<img src="${AppLogo!}" alt="logo" @click="$store.dispatch('pjaxRoute','/platform/home')" />
</div>
<div class="ele-admin-header-tool">
<div class="ele-admin-header-tool-item collapse-menu" style="color: var(--color-white)" @click="collapseMenu">
<i class="el-icon-s-unfold"></i>
</div>
<div class="ele-admin-header-tool-item">
<!--菜单模块-->
<header-menu-module></header-menu-module>
</div>
</div>
<!--面包屑-->
<div class="ele-admin-breadcrumb">
<header-bread-crumb></header-bread-crumb>
</div>
<div class="ele-admin-header-nav"></div>
<div class="ele-admin-header-tool">
<!--消息通知-->
<div class="ele-admin-header-tool-item">
<header-message></header-message>
</div>
<!--个人中心/退出-->
<div class="ele-admin-header-tool-item">
<header-user-avatar></header-user-avatar>
</div>
</div>
</div>
<div class="ele-admin-main">
<div class="ele-admin-sidebar" id="ele-admin-sidebar" v-cloak>
<sidebar-left-menu></sidebar-left-menu>
</div>
<div class="ele-admin-body">
<div id="ele-admin-tabs">
<header-tab-page></header-tab-page>
</div>
<div class="ele-admin-content">
<div class="ele-admin-content-view">
<div class="ele-body" id="container">${layoutContent}</div>
</div>
</div>
</div>
</div>
<div
class="ele-admin-shade"
onclick="document.querySelector('body >div > div.ele-admin-layout').classList.add('ele-admin-collapse')"
></div>
</div>
<div class="sub-app-container" id="sub-app-container">
<!-- 左侧菜单区域 -->
<nav class="sidebar-menu" id="sidebar-menu">
<div class="menu-header">
<h2 class="menu-title">子系统</h2>
</div>
<script type="text/javascript">
<!--左侧菜单 && 头部 && 标签页-->
new Vue({
el: "#ele-admin-sidebar",
components: {
"sidebar-left-menu": httpVueLoader("/components/layout/SideBarLeftMenu.vue?v=" + new Date().getTime())
}
<el-scrollbar>
<el-menu unique-opened :default-active="activeMenuIndex" :default-openeds="openedMenus" @select="menuSelect">
<menu-list :menus="leftMenus" :depth="0"></menu-list>
</el-menu>
</el-scrollbar>
</nav>
<!-- 右侧主体区域 -->
<main class="sub-app-container-main-content" id="sub-app-container-main-content">
<!-- <header class="content-header">-->
<!-- <h1 class="content-title"></h1>-->
<!-- &lt;!&ndash; <p class="content-subtitle"></p>&ndash;&gt;-->
<!-- </header>-->
<div class="content-body" id="sub-app-container-main-content-body">${layoutContent!}</div>
</main>
<!-- 子应用ID -->
<div id="sub-app-id" style="display: none"></div>
</div>
<script>
// 初始化pjax加载
;(function initPjax() {
$(document).pjax("#sidebar-menu a[data-pjax]", "#sub-app-container-main-content-body", {
maxCacheLength: 0,
push: true,
replace: false,
fragment: "#sub-app-container-main-content-body",
timeout: 8000
})
$(document).on("pjax:send", function () {
NProgress.configure({ parent: ".sub-app-container-main-content" })
NProgress.start()
$("#sub-app-container-main-content").hide()
})
$(document).on("pjax:complete", function () {
NProgress.done()
$("#sub-app-container-main-content").show()
setContentTitle()
})
setContentTitle()
})()
// 设置内容标题
function setContentTitle() {
// const menu = store.state.user.menus.find((v) => v.href === window.location.pathname)
// $("#sub-app-container-main-content .content-title").text(menu?.name)
try {
const app = JSON.parse(window.sessionStorage.getItem("zhgh_sub_app"))
$("#sub-app-container #sidebar-menu .menu-header .menu-title").text(app?.name)
} catch (e) {}
}
document.addEventListener("DOMContentLoaded", function () {
const menuLinks = document.querySelectorAll("#sidebar-menu a")
menuLinks.forEach((link) => {
link.addEventListener("click", function (e) {
const pjax = this.hasAttribute("data-pjax")
e.preventDefault()
})
new Vue({
el: "#ele-admin-header",
store,
components: {
"header-message": httpVueLoader("/components/layout/HeaderMessage.vue?v=" + new Date().getTime()),
"header-bread-crumb": httpVueLoader("/components/layout/HeaderBreadCrumb.vue?v=" + new Date().getTime()),
"header-menu-module": httpVueLoader("/components/layout/HeaderMenuModule.vue?v=" + new Date().getTime()),
"header-user-avatar": httpVueLoader("/components/layout/HeaderUserAvatar.vue?v=" + new Date().getTime())
},
methods: {
collapseMenu() {
document.querySelector("body >div > div.ele-admin-layout").classList.remove("ele-admin-collapse")
})
})
new Vue({
el: "#sidebar-menu",
components: {
"menu-list": {
name: "menu-list",
template:
/*language=HTML*/
`
<div>
<template v-for="(item, index) in menus">
<el-submenu :index="item.id" v-if="item.children && item.children.length > 0">
<template #title>
<i :class="item.icon" v-if="item.icon" :size="18"></i>
<i v-else class="el-icon-paperclip"></i>
<span>{{ item.name }}</span>
</template>
<menu-list :menus="item.children" :depth="depth + 1" />
</el-submenu>
<el-menu-item :index="item.id" v-else>
<a :href="item.href" data-pjax>
<i :class="item.icon" v-if="item.icon" :size="18"></i>
<i v-else :class="item.icon ? item.icon : 'el-icon-menu'"></i>
<span>{{ item.name }}</span>
</a>
</el-menu-item>
</template>
</div>
`,
props: ["menus", "depth"]
}
},
data() {
return {
menus: [],
activeMenuIndex: null,
openedMenus: []
}
},
computed: {
leftMenus() {
if (this.menus) {
return this.menus
} else {
try {
return JSON.parse(window.sessionStorage.getItem("zhgh_sub_app_menus"))
} catch (e) {
return []
}
}
})
new Vue({
el: "#ele-admin-tabs",
components: {
"header-tab-page": httpVueLoader("/components/layout/HeaderTabPage.vue?v=" + new Date().getTime())
}
},
methods: {
menuSelect(index, indexPath) {
try {
const app = JSON.parse(window.sessionStorage.getItem("zhgh_sub_app"))
window.sessionStorage.setItem("zhgh_sub_app_left_menu_active_index-" + app.id, index)
window.sessionStorage.setItem("zhgh_sub_app_left_menu_opens-" + app.id, JSON.stringify(indexPath))
} catch (e) {}
},
// 获取菜单
getMenus(appId) {
if (!appId) return
$.get("/platform/sys/user/subAppMenus", { appId }).then((res) => {
if (res.code === 0) {
this.menus = res.data
window.sessionStorage.setItem("zhgh_sub_app_menus", JSON.stringify(res.data))
} else {
this.menus = []
}
this.echoMenus()
})
},
setAppInfo(app) {
if (app) {
// 储存到缓存
window.sessionStorage.setItem("zhgh_sub_app", JSON.stringify(app))
// 储存到div中
document.getElementById("sub-app-id").innerText = app.id
}
})
</script>
</body>
</html>
// document.querySelector("#sub-app-container .content-title").innerText = app.name
},
// 菜单回显
echoMenus() {
try {
const app = JSON.parse(window.sessionStorage.getItem("zhgh_sub_app"))
this.activeMenuIndex = window.sessionStorage.getItem("zhgh_sub_app_left_menu_active_index-" + app.id)
this.openedMenus = JSON.parse(window.sessionStorage.getItem("zhgh_sub_app_left_menu_opens-" + app.id)) || []
console.log(this.openedMenus)
console.log(this.activeMenuIndex)
} catch (e) {}
}
},
mounted() {
// 页面加载时获取到正确的菜单
const pathname = window.location.pathname
if (!pathname.startsWith("/platform/v4/subApp")) {
$.get("/platform/sys/user/rootMenuByPath", { pathname }).then((res) => {
if (res.code === 0) {
this.setAppInfo(res.data)
this.getMenus(res.data?.id)
}
})
} else {
const appId = GetQueryString("appId")
if (!appId) {
return
}
this.getMenus(appId)
}
}
})
</script>
<!--#
}
#-->