From 83d251608828d17dbb9a8d480c13a1a7c0a20eb5 Mon Sep 17 00:00:00 2001
From: 祖安之光 <11848914+light-of-zuan@user.noreply.gitee.com>
Date: Wed, 29 Apr 2026 16:20:18 +0800
Subject: [PATCH] 修改主页跳转

---
 src/permission.js                  |   35 +++
 /dev/null                          |  436 ------------------------------------------------
 src/views/work/menuIndex/index.vue |   52 +++--
 src/views/menuPage.vue             |   17 +
 4 files changed, 84 insertions(+), 456 deletions(-)

diff --git a/src/permission.js b/src/permission.js
index 0628d25..9eac69c 100644
--- a/src/permission.js
+++ b/src/permission.js
@@ -1,5 +1,5 @@
 import router from './router'
-import { ElMessage } from 'element-plus'
+import { ElMessage, ElLoading } from 'element-plus'
 import NProgress from 'nprogress'
 import 'nprogress/nprogress.css'
 import { getToken } from '@/utils/auth'
@@ -13,6 +13,27 @@
 
 const whiteList = ['/homePage'];
 
+// 全局 Loading 实例
+let loadingInstance = null
+
+// 显示 Loading
+const showLoading = () => {
+  loadingInstance = ElLoading.service({
+    fullscreen: false,
+    text: '正在加载系统菜单...',
+    customClass: 'route-loading'
+  })
+}
+
+// 隐藏 Loading
+const hideLoading = () => {
+  if (loadingInstance) {
+    loadingInstance.close()
+    loadingInstance = null
+  }
+}
+
+
 router.beforeEach((to, from, next) => {
   NProgress.start()
   if (getToken()) {
@@ -22,9 +43,18 @@
       next({ path: '/' })
       NProgress.done()
     } else if (whiteList.indexOf(to.path) !== -1) {
+      
       next()
     } else {
+      if(to.path ==='/menuPage'){
+          next()
+          return
+        }
       if (useUserStore().roles.length === 0) {
+        if(to.path ==='/menuIndex'){
+          showLoading()
+        }
+        
         isRelogin.show = true
         // 判断当前用户是否已拉取完user_info信息
         useUserStore().getInfo().then(() => {
@@ -36,6 +66,8 @@
                 router.addRoute(route) // 动态添加可访问路由表
               }
             })
+
+            hideLoading()
 
             if (to.fullPath == '/index') {
 
@@ -77,5 +109,6 @@
 })
 
 router.afterEach(() => {
+  hideLoading()
   NProgress.done()
 })
diff --git a/src/views/menuPage.vue b/src/views/menuPage.vue
index 97370b3..6622f79 100644
--- a/src/views/menuPage.vue
+++ b/src/views/menuPage.vue
@@ -197,8 +197,17 @@
   }
 }
 
+const debounce = (func, wait) => {
+  let timeout
+  return (...args) => {
+    clearTimeout(timeout)
+    timeout = setTimeout(() => {
+      func(...args)
+    }, wait)
+  }
+}
+
 const handleSystemLinkClick = (systemId) => {
-  console.log('点击了'+ systemId)
   if(systemId == 1){
     router.push({ path: "/menuIndex"});
   }else{
@@ -206,6 +215,12 @@
   }
 }
 
+// const debouncedSubmit = ref(debounce(submitHandle, 500))
+
+// const handleSystemLinkClick = (id) => {
+//   debouncedSubmit.value(id)
+// }
+
 function getInfo() {
   reviewRef.value.openDialog('view',userInfo.value)
 }
diff --git a/src/views/menuPage2.vue b/src/views/menuPage2.vue
deleted file mode 100644
index f3539e1..0000000
--- a/src/views/menuPage2.vue
+++ /dev/null
@@ -1,436 +0,0 @@
-<template>
-  <div class="system-select-container">
-    <!-- 顶部用户信息栏 -->
-    <div class="user-info-bar">
-      <div class="user-left">
-        欢迎访问多体系建设信息化系统
-      </div>
-      <div class="avatar-container">
-        <el-dropdown @command="handleCommand" class="right-menu-item hover-effect" trigger="click">
-          <div class="avatar-wrapper" style="display: flex;align-items: center">
-            <img src="../assets/images/avator.png" class="user-avatar"  />
-            <span style="font-size: 16px;color: #fff">{{userName}}({{userTypeName}})</span>
-            <el-icon color="#fff"><caret-bottom /></el-icon>
-          </div>
-          <template #dropdown>
-            <el-dropdown-menu>
-<!--              <el-dropdown-item command="info">-->
-<!--                <span>基本信息</span>-->
-<!--              </el-dropdown-item>-->
-              <el-dropdown-item command="password">
-                <span>修改密码</span>
-              </el-dropdown-item>
-              <el-dropdown-item divided command="logout">
-                <span>退出登录</span>
-              </el-dropdown-item>
-            </el-dropdown-menu>
-          </template>
-        </el-dropdown>
-      </div>
-    </div>
-
-    <!-- 系统选择区域 -->
-    <div class="systems-container">
-      <div class="systems-grid">
-        <div
-            v-for="system in systems"
-            :key="system.id"
-            class="system-card"
-            @mouseenter="handleCardEnter($event, system.id)"
-            @mousemove="handleCardMove($event, system.id)"
-            @mouseleave="handleCardLeave(system.id)"
-            @click="enterSystem(system.id)"
-            :style="getCardStyle(system.id)"
-        >
-          <div class="card-content">
-          <div class="system-icon">
-            <img :src="system.icon"/>
-          </div>
-          <h3>{{ system.name }}</h3>
-          <p>{{ system.description }}</p>
-          </div>
-        </div>
-      </div>
-    </div>
-<!--    <div class="sys-footer">-->
-<!--      <div class="footer-left">-->
-<!--        <img src="../assets/images/menuPageLogo.png"/>-->
-<!--        <span>中国科学院苏州纳米技术与纳米仿生研究所</span>-->
-<!--      </div>-->
-<!--      <div class="footer-right">-->
-<!--        系统版本:V1.0.0-->
-<!--      </div>-->
-<!--    </div>-->
-    <user-dialog ref="reviewRef"></user-dialog>
-  </div>
-</template>
-
-<script setup>
-import { ref, onMounted } from 'vue'
-import { useRouter } from 'vue-router'
-import {getToken, removeToken} from "@/utils/auth";
-import Cookies from "js-cookie";
-import {ElMessage, ElMessageBox} from "element-plus";
-import  useUserStore from '@/store/modules/user'
-import userDialog from '@/views/build/conpanyFunctionConsult/staffManage/staffRegister/components/staffDialog.vue'
-import menu1 from '@/assets/icons/menu1.png'
-import menu2 from '@/assets/icons/menu2.png'
-import menu3 from '@/assets/icons/menu3.png'
-import menu4 from '@/assets/icons/menu4.png'
-import menu5 from '@/assets/icons/menu5.png'
-import menu6 from '@/assets/icons/menu6.png'
-
-const router = useRouter()
-const route = useRoute();
-const reviewRef = ref();
-const userInfo = ref();
-const userName = ref('')
-const userTypeName = ref('')
-const cardStates = ref({})
-// 组件挂载时获取用户信息和系统列表
-onMounted(() => {
-  if(getToken()){
-    userInfo.value = JSON.parse(Cookies.get('userInfo'))
-    userName.value = userInfo.value.username
-    userTypeName.value = userInfo.value.userType == 0 ? '系统管理员' : (userInfo.value.userType == 1 ||  userInfo.value.userType == 2 || userInfo.value.userType == 3) ? '企业用户' :userInfo.value.userType == 6 ? '企业管理员' :userInfo.value.userType == 4 ? '其他' : '学员'
-  }
-
-  const userStore = useUserStore()
-  userStore.roles = []
-  systems.value.forEach(system => {
-    cardStates.value[system.id] = {
-      mouseX: 0,
-      mouseY: 0,
-      width: 0,
-      height: 0,
-      hover: false
-    }
-  })
-})
-
-
-// 鼠标进入卡片
-const handleCardEnter = (event, id) => {
-  const card = event.currentTarget
-  cardStates.value[id] = {
-    ...cardStates.value[id],
-    width: card.offsetWidth,
-    height: card.offsetHeight,
-    hover: true
-  }
-}
-
-// 鼠标移动
-const handleCardMove = (event, id) => {
-  if (!cardStates.value[id]?.hover) return
-
-  const card = event.currentTarget
-  const rect = card.getBoundingClientRect()
-
-  cardStates.value[id].mouseX = event.clientX - rect.left - cardStates.value[id].width / 2
-  cardStates.value[id].mouseY = event.clientY - rect.top - cardStates.value[id].height / 2
-}
-
-// 鼠标离开
-const handleCardLeave = (id) => {
-  cardStates.value[id].hover = false;
-  // 立即开始归位动画,不使用setTimeout延迟
-  cardStates.value[id].mouseX = 0;
-  cardStates.value[id].mouseY = 0;
-}
-
-// 获取卡片样式
-const getCardStyle = (id) => {
-  const state = cardStates.value[id] || {}
-  const mousePX = state.mouseX / (state.width || 1)
-  const mousePY = state.mouseY / (state.height || 1)
-
-  const rX = mousePX * 20 // 减小旋转角度,使效果更柔和
-  const rY = mousePY * -20
-
-  const tX = mousePX * -20
-  const tY = mousePY * -20
-
-  return {
-    transform: `rotateY(${rX}deg) rotateX(${rY}deg)`,
-    '--bg-transform': `translateX(${tX}px) translateY(${tY}px)`
-  }
-}
-
-
-// 系统列表
-const systems = ref([
-  {
-    id: 1,
-    name: '国军标9001C质量管理体系',
-    description: '确保产品和服务质量符合国际标准',
-    icon: menu1
-  },
-  {
-    id: 2,
-    name: 'ISO 27001 信息安全体系',
-    description: '保护企业信息资产安全与机密性',
-    icon: menu2
-  },
-  {
-    id: 3,
-    name: 'ISO 45001 安全体系',
-    description: '实现企业安全的持续改进',
-    icon: menu3
-  },
-  {
-    id: 4,
-    name: '项目管理控制',
-    description: '标准化项目管理流程与方法',
-    icon: menu4
-  },
-  {
-    id: 5,
-    name: '承制评价体系',
-    description: '供应商与承包商能力评估标准',
-    icon: menu5
-  },
-  {
-    id: 6,
-    name: '新体系评价',
-    description: '新体系评价',
-    icon: menu6
-  }
-])
-function handleCommand(command) {
-  switch (command) {
-    case "info":
-      getInfo();
-      break;
-    case "logout":
-      logout();
-      break;
-    case "password":
-      editPsd();
-      break;
-    default:
-      break;
-  }
-}
-// 进入系统
-const enterSystem = (systemId) => {
-  if(systemId == 1){
-    router.push({ path: "/menuIndex"});
-  }else{
-    ElMessage.warning('系统正在开发中...')
-  }
-}
-function getInfo() {
-  reviewRef.value.openDialog('view',userInfo.value)
-}
-function editPsd() {
-  reviewRef.value.openDialog('pwd',userInfo.value)
-}
-// 退出登录
-function logout() {
-  ElMessageBox.confirm('确定注销并退出系统吗?', '提示', {
-    confirmButtonText: '确定',
-    cancelButtonText: '取消',
-    type: 'warning'
-  }).then(() => {
-    removeToken()
-    location.href = '/homePage';
-
-  }).catch(() => { });
-}
-
-
-</script>
-
-<style scoped lang="scss">
-.system-select-container {
-  height: 100vh;
-  display: flex;
-  flex-direction: column;
-  background-color: #f5f7fa;
-}
-
-.user-info-bar {
-  display: flex;
-  height: 100px;
-  align-items: center;
-  justify-content: space-between;
-  padding: 10px 20px;
-  background-color: rgb(16,66,143);
-  box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
-
-  .user-left{
-    width: 80%;
-    font-size: clamp(1rem, -0.143rem + 1.79vw, 2rem);
-    font-weight: bolder;
-    padding-left: 40px;
-    color: #fff;
-  }
-
-  .avatar-container {
-    width: 20%;
-    display: flex;
-    justify-content: center;
-
-    .avatar-wrapper {
-      position: relative;
-
-      .user-avatar {
-        cursor: pointer;
-        width: 40px;
-        height: 40px;
-        border-radius: 10px;
-        margin-right: 15px;
-      }
-
-      i {
-        cursor: pointer;
-        position: absolute;
-        right: -20px;
-        font-size: 12px;
-      }
-    }
-  }
-
-}
-
-
-.systems-container {
-  flex: 1;
-  padding: 20px 60px;
-  overflow-y: auto;
-  margin-top: 60px;
-}
-
-.sys-footer{
-  height: 100px;
-  background: #e6e6e6;
-  display: flex;
-  justify-content: space-between;
-  align-items: center;
-  .footer-left{
-    display: flex;
-    justify-content: left;
-    align-items: center;
-
-    img{
-      width: 60px;
-      height: 60px;
-    }
-    span{
-      font-size: 24px;
-    }
-  }
-}
-
-.systems-grid {
-  display: grid;
-  grid-template-columns: repeat(3,1fr);
-  gap: 30px;
-  max-width: 100%;
-  margin: 0 auto;
-  perspective: 1000px;
-}
-
-.system-card {
-  position: relative;
-  height: 320px;
-  background-color: #ffffff;
-  border-radius: 4px;
-  transition: transform 1s cubic-bezier(0.23, 1, 0.32, 1),
-  box-shadow 0.5s cubic-bezier(0.23, 1, 0.32, 1);
-  transform-style: preserve-3d;
-  cursor: pointer;
-  overflow: hidden;
-
-  &:hover{
-    border-radius: 16px;
-  }
-
-  &::after {
-    content: '';
-    position: absolute;
-    top: 8px;
-    left: 8px;
-    right: 8px;
-    bottom: 8px;
-    border-radius: 4px; /* 比卡片小1px */
-    border: 1px solid transparent;
-    transition: border-color 0.3s ease;
-    pointer-events: none; /* 确保不影响鼠标事件 */
-    z-index: 3; /* 确保在内容之上 */
-  }
-
-  &::before {
-    content: '';
-    position: absolute;
-    top: 0;
-    left: 0;
-    right: 0;
-    bottom: 0;
-    border-radius: 4px;
-    background: #fff;
-    transform: var(--bg-transform, translateX(0) translateY(0));
-    transition: transform 0.5s cubic-bezier(0.23, 1, 0.32, 1);
-    z-index: 1;
-  }
-  &:hover::after {
-    border-color: rgba(37,99,235,1); /* 使用蓝色描边 */
-    border-radius: 12px;
-    box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.5); /* 可选:添加内发光效果 */
-  }
-  &:hover::before {
-    border-radius: 16px;
-    background: linear-gradient(135deg, rgba(255,255,255,0.1) 0%, rgba(20,20,20,0.05) 100%);
-  }
-}
-
-.system-card:hover {
-  //transform: translateY(-5px);
-  box-shadow: 0 15px 30px rgba(0, 0, 0, 0.15),
-  0 0 0 1px rgba(255, 255, 255, 0.5) inset;
-}
-.card-content {
-  position: relative;
-  height: 100%;
-  display: flex;
-  flex-direction: column;
-  align-items: center;
-  justify-content: center;
-  padding: 25px;
-  z-index: 2;
-  transform-style: preserve-3d;
-}
-
-.system-icon img {
-  width: 80px;
-  height: 80px;
-  margin-bottom: 30px;
-  transition: transform 0.5s;
-}
-
-.system-card:hover .system-icon img {
-  transform: scale(1.4);
-}
-
-.system-card h3 {
-  margin: 0 0 12px;
-  color: #333;
-  font-size: 24px;
-  text-align: center;
-  transition: transform 0.3s;
-}
-
-.system-card p {
-  margin: 0;
-  color: #999;
-  font-size: 15px;
-  text-align: center;
-  transition: transform 0.3s;
-}
-
-.system-card:hover h3,
-.system-card:hover p {
-  transform: translateZ(20px);
-}
-</style>
diff --git a/src/views/work/menuIndex/index.vue b/src/views/work/menuIndex/index.vue
index 167b244..f0d689a 100644
--- a/src/views/work/menuIndex/index.vue
+++ b/src/views/work/menuIndex/index.vue
@@ -11,10 +11,20 @@
               <span class="more-link" @click="toNoticeMng">更多 ></span>
             </div>
             <div class="notice-list">
-              <div class="notice-item" v-for="item in noticeList" :key="item">
-                <span class="notice-title" @click="openNoticeFile(item.filePath)">{{item.content}}</span>
-                <span class="notice-date">{{item.publishDate}}</span>
-              </div>
+
+              <template v-if="noticeLoading">
+                <div v-for="i in 6" :key="i" class="notice-item skeleton">
+                  <div class="skeleton-title"></div>
+                  <div class="skeleton-date"></div>
+                </div>
+              </template>
+
+              <template v-else>
+                <div class="notice-item" v-for="item in noticeList" :key="item.id">
+                  <span class="notice-title" @click="openNoticeFile(item.filePath)">{{item.content}}</span>
+                  <span class="notice-date">{{item.publishDate}}</span>
+                </div>
+              </template>
             </div>
           </div>
 
@@ -179,12 +189,6 @@
 import userDialog from '@/views/build/conpanyFunctionConsult/staffManage/staffRegister/components/staffDialog.vue'
 import editDialog from '@/views/build/conpanyFunctionConsult/infoPlatform/components/editDialog.vue'
 import sealDialog from "@/views/work/sealManagement/apply/components/editDialog"
-import menu1 from '@/assets/icons/menu1.png'
-import menu2 from '@/assets/icons/menu2.png'
-import menu3 from '@/assets/icons/menu3.png'
-import menu4 from '@/assets/icons/menu4.png'
-import menu5 from '@/assets/icons/menu5.png'
-import menu6 from '@/assets/icons/menu6.png'
 
 // 引入农历库
 import * as lunarCalendar from 'lunar-calendar'
@@ -206,6 +210,8 @@
 const calendarRef = ref()
 const dialogRef = ref()
 const noticeRef = ref();
+const noticeLoading = ref(true)
+
 const userStore = useUserStore()
 const state = reactive({
   noticeParams: {
@@ -243,10 +249,13 @@
     state.platformParams.companyId = userStore.companyId
     state.isAdmin = false
   }
-  await getNoticeList()
-  await getPlatformList()
-  await getFlowList()
-  await getMemo()
+  // 并行加载所有数据
+  await Promise.allSettled([
+    getNoticeList(),
+    getPlatformList(),
+    getFlowList(),
+    getMemo()
+  ])
   state.platformList.forEach(system => {
     cardStates.value[system.id] = {
       mouseX: 0,
@@ -292,10 +301,17 @@
     noticeRef.value.openDialog('review', data,state.companyList)
   }
 }
-function getNoticeList() {
-  listNotice(state.noticeParams).then(res => {
-    state.noticeList = res.data.list
-  })
+async function getNoticeList() {
+  try {
+    noticeLoading.value = true
+    const res = await listNotice(state.noticeParams)
+    state.noticeList = res.data.list || []
+  } catch (error) {
+    console.error('获取通知公告失败:', error)
+    state.noticeList = []
+  } finally {
+    noticeLoading.value = false
+  }
 }
 const getCompanyList = async ()=>{
   const queryParams = {

--
Gitblit v1.9.2