fix(projects): 🐛 fix menu active issue. fixed [#101][#94]

This commit is contained in:
一寸灰
2025-06-06 21:41:58 +08:00
committed by GitHub
parent 325a7f5d82
commit 87a113c5e6
7 changed files with 42 additions and 40 deletions

View File

@@ -1,7 +1,9 @@
import { computed, ref, watch } from 'vue';
import { computed, nextTick, ref, watch } from 'vue';
import { useRoute } from 'vue-router';
import { useContext } from '@sa/hooks';
import type { RouteKey } from '@elegant-router/types';
import { useRouteStore } from '@/store/modules/route';
import { useRouterPush } from '@/hooks/common/router';
export const { setupStore: setupMixMenuContext, useStore: useMixMenuContext } = useContext('mix-menu', useMixMenu);
@@ -67,6 +69,7 @@ function useMixMenu() {
export function useMenu() {
const route = useRoute();
const { routerPushByKeyWithMetaQuery } = useRouterPush();
const selectedKey = computed(() => {
const { hideInMenu, activeMenu } = route.meta;
@@ -77,7 +80,28 @@ export function useMenu() {
return routeName;
});
const selectedKeyDummy = ref(selectedKey.value);
watch(
() => selectedKey.value,
val => {
selectedKeyDummy.value = val;
}
);
function handleSelect(key: RouteKey) {
selectedKeyDummy.value = key;
routerPushByKeyWithMetaQuery(key);
nextTick(() => {
selectedKeyDummy.value = selectedKey.value;
});
}
return {
selectedKey
selectedKey,
selectedKeyDummy,
handleSelect
};
}

View File

@@ -2,15 +2,13 @@
import type { RouteKey } from '@elegant-router/types';
import { GLOBAL_HEADER_MENU_ID } from '@/constants/app';
import { useRouteStore } from '@/store/modules/route';
import { useRouterPush } from '@/hooks/common/router';
import { useMenu } from '../../../context';
import MenuItem from '../components/menu-item.vue';
defineOptions({ name: 'HorizontalMenu' });
const routeStore = useRouteStore();
const { routerPushByKeyWithMetaQuery } = useRouterPush();
const { selectedKey } = useMenu();
const { selectedKeyDummy, handleSelect } = useMenu();
</script>
<template>
@@ -19,8 +17,8 @@ const { selectedKey } = useMenu();
ellipsis
class="w-full"
mode="horizontal"
:default-active="selectedKey"
@select="val => routerPushByKeyWithMetaQuery(val as RouteKey)"
:default-active="selectedKeyDummy"
@select="val => handleSelect(val as RouteKey)"
>
<MenuItem v-for="item in routeStore.menus" :key="item.key" :item="item" :index="item.key" />
</ElMenu>

View File

@@ -16,7 +16,7 @@ const appStore = useAppStore();
const themeStore = useThemeStore();
const { routerPushByKeyWithMetaQuery } = useRouterPush();
const { allMenus, childLevelMenus, activeFirstLevelMenuKey, setActiveFirstLevelMenuKey } = useMixMenuContext();
const { selectedKey } = useMenu();
const { selectedKeyDummy, handleSelect } = useMenu();
function handleSelectMixMenu(menu: App.Global.Menu) {
setActiveFirstLevelMenuKey(menu.key);
@@ -33,8 +33,8 @@ function handleSelectMixMenu(menu: App.Global.Menu) {
ellipsis
class="w-full"
mode="horizontal"
:default-active="selectedKey"
@select="val => routerPushByKeyWithMetaQuery(val as RouteKey)"
:default-active="selectedKeyDummy"
@select="val => handleSelect(val as RouteKey)"
>
<MenuItem v-for="item in childLevelMenus" :key="item.key" :item="item" :index="item.key" />
</ElMenu>

View File

@@ -25,7 +25,7 @@ const {
setActiveFirstLevelMenuKey,
isActiveFirstLevelMenuHasChildren
} = useMixMenuContext();
const { selectedKey } = useMenu();
const { selectedKey, selectedKeyDummy, handleSelect } = useMenu();
function handleSelectMixMenu(key: RouteKey) {
setActiveFirstLevelMenuKey(key);
@@ -70,9 +70,9 @@ watch(
<SimpleScrollbar>
<ElMenu
mode="vertical"
:default-active="selectedKey"
:default-active="selectedKeyDummy"
:collapse="appStore.siderCollapse"
@select="val => routerPushByKeyWithMetaQuery(val as RouteKey)"
@select="val => handleSelect(val as RouteKey)"
>
<MenuItem v-for="item in childLevelMenus" :key="item.key" :item="item" :index="item.key" />
</ElMenu>

View File

@@ -1,13 +1,11 @@
<script setup lang="ts">
import { ref, watch } from 'vue';
import { useRoute } from 'vue-router';
import { useDocumentVisibility } from '@vueuse/core';
import { SimpleScrollbar } from '@sa/materials';
import type { RouteKey } from '@elegant-router/types';
import { GLOBAL_SIDER_MENU_ID } from '@/constants/app';
import { useAppStore } from '@/store/modules/app';
import { useRouteStore } from '@/store/modules/route';
import { useRouterPush } from '@/hooks/common/router';
import { useMenu } from '../../../context';
import MenuItem from '../components/menu-item.vue';
@@ -16,8 +14,7 @@ defineOptions({ name: 'VerticalMenu' });
const route = useRoute();
const appStore = useAppStore();
const routeStore = useRouteStore();
const { routerPushByKeyWithMetaQuery } = useRouterPush();
const { selectedKey } = useMenu();
const { selectedKey, selectedKeyDummy, handleSelect } = useMenu();
// const inverted = computed(() => !themeStore.darkMode && themeStore.sider.inverted);
@@ -31,19 +28,6 @@ function updateExpandedKeys() {
expandedKeys.value = routeStore.getSelectedMenuKeyPath(selectedKey.value);
}
const visibility = useDocumentVisibility();
const selectedKeyDummy = ref(selectedKey.value);
// watch document.visibilityState
watch(visibility, () => {
if (visibility.value === 'hidden') {
selectedKeyDummy.value = '';
} else {
selectedKeyDummy.value = selectedKey.value;
}
});
watch(
() => route.name,
() => {
@@ -62,7 +46,7 @@ watch(
:default-openeds="expandedKeys"
:collapse="appStore.siderCollapse"
:collapse-transition="false"
@select="val => routerPushByKeyWithMetaQuery(val as RouteKey)"
@select="val => handleSelect(val as RouteKey)"
>
<MenuItem v-for="item in routeStore.menus" :key="item.key" :item="item" :index="item.key" />
</ElMenu>

View File

@@ -4,12 +4,12 @@ import { useRoute } from 'vue-router';
import { SimpleScrollbar } from '@sa/materials';
import { useBoolean } from '@sa/hooks';
import type { RouteKey } from '@elegant-router/types';
import { GLOBAL_SIDER_MENU_ID } from '@/constants/app';
import { useAppStore } from '@/store/modules/app';
import { useThemeStore } from '@/store/modules/theme';
import { useRouteStore } from '@/store/modules/route';
import { useRouterPush } from '@/hooks/common/router';
import { $t } from '@/locales';
import { GLOBAL_SIDER_MENU_ID } from '@/constants/app';
import { useMenu, useMixMenuContext } from '../../../context';
import FirstLevelMenu from '../components/first-level-menu.vue';
import GlobalLogo from '../../global-logo/index.vue';
@@ -33,7 +33,7 @@ const {
getActiveFirstLevelMenuKey
//
} = useMixMenuContext();
const { selectedKey } = useMenu();
const { selectedKey, selectedKeyDummy, handleSelect } = useMenu();
const inverted = computed(() => !themeStore.darkMode && themeStore.sider.inverted);
@@ -111,11 +111,7 @@ watch(
/>
</header>
<SimpleScrollbar>
<ElMenu
mode="vertical"
:default-active="selectedKey"
@select="val => routerPushByKeyWithMetaQuery(val as RouteKey)"
>
<ElMenu mode="vertical" :default-active="selectedKeyDummy" @select="val => handleSelect(val as RouteKey)">
<MenuItem v-for="item in childLevelMenus" :key="item.key" :item="item" :index="item.key" />
</ElMenu>
</SimpleScrollbar>

View File

@@ -6,10 +6,10 @@ import type {
Router
} from 'vue-router';
import type { RouteKey, RoutePath } from '@elegant-router/types';
import { getRouteName } from '@/router/elegant/transform';
import { useAuthStore } from '@/store/modules/auth';
import { useRouteStore } from '@/store/modules/route';
import { localStg } from '@/utils/storage';
import { getRouteName } from '@/router/elegant/transform';
/**
* create route guard
@@ -166,7 +166,7 @@ function handleRouteSwitch(to: RouteLocationNormalized, from: RouteLocationNorma
if (to.meta.href) {
window.open(to.meta.href, '_blank');
next({ path: from.fullPath, replace: true, query: from.query, hash: to.hash });
next({ path: from.fullPath, replace: true, query: from.query, hash: from.hash });
return;
}