diff --git a/CHANGELOG.zh_CN.md b/CHANGELOG.zh_CN.md index ccef47a853c85b849e0506c3ccde89f37687b899..21327f6a9e1ab60e4ae5273af4ed9c6ee9a06271 100644 --- a/CHANGELOG.zh_CN.md +++ b/CHANGELOG.zh_CN.md @@ -4,6 +4,7 @@ - 表单项的`componentsProps`支持函数类型 - 菜单新增 tag 显示 +- 新增菜单及顶栏颜色选择配色 ### ⚡ Performance Improvements diff --git a/index.html b/index.html index e729b5daa494a6009c8f04f3065e8bf38b6fd4d0..5702b863a57f363392a7dbd1bb2a908ddf832ec9 100644 --- a/index.html +++ b/index.html @@ -43,7 +43,7 @@ .app-loading .g-loading { display: block; - width: 64px; + width: 48px; margin: 30px auto; -webkit-animation: load 1.2s linear infinite; animation: load 1.2s linear infinite; diff --git a/src/components/Menu/src/BasicMenu.tsx b/src/components/Menu/src/BasicMenu.tsx index 41ca01217997217eca517251f76828d2f084405d..5842134c403a52e3e5d01be41212f45be39b54a9 100644 --- a/src/components/Menu/src/BasicMenu.tsx +++ b/src/components/Menu/src/BasicMenu.tsx @@ -1,7 +1,7 @@ import type { MenuState } from './types'; import type { Menu as MenuType } from '/@/router/types'; -import { computed, defineComponent, unref, reactive, toRef, watch, onMounted, ref } from 'vue'; +import { computed, defineComponent, unref, reactive, watch, onMounted, ref, toRefs } from 'vue'; import { Menu } from 'ant-design-vue'; import SearchInput from './SearchInput.vue'; import MenuContent from './MenuContent'; @@ -40,8 +40,10 @@ export default defineComponent({ }); const { currentRoute } = useRouter(); + const { items, flatItems, isAppMenu, mode, accordion } = toRefs(props); + const { handleInputChange, handleInputClick } = useSearchInput({ - flatMenusRef: toRef(props, 'flatItems'), + flatMenusRef: flatItems, emit: emit, menuState, handleMenuChange, @@ -49,11 +51,11 @@ export default defineComponent({ const { handleOpenChange, resetKeys, setOpenKeys } = useOpenKeys( menuState, - toRef(props, 'items'), - toRef(props, 'flatItems'), - toRef(props, 'isAppMenu'), - toRef(props, 'mode'), - toRef(props, 'accordion') + items, + flatItems, + isAppMenu, + mode, + accordion ); const getOpenKeys = computed(() => { @@ -98,6 +100,8 @@ export default defineComponent({ return cls; }); + const showTitle = computed(() => props.collapsedShowTitle && menuStore.getCollapsedState); + watch( () => currentRoute.value.name, (name: string) => { @@ -130,9 +134,7 @@ export default defineComponent({ const { beforeClickFn } = props; if (beforeClickFn && isFunction(beforeClickFn)) { const flag = await beforeClickFn(menu); - if (!flag) { - return; - } + if (!flag) return; } const { path } = menu; menuState.selectedKeys = [path]; @@ -141,9 +143,7 @@ export default defineComponent({ function handleMenuChange() { const { flatItems } = props; - if (!unref(flatItems) || flatItems.length === 0) { - return; - } + if (!unref(flatItems) || flatItems.length === 0) return; const findMenu = flatItems.find((menu) => menu.path === unref(currentRoute).path); if (findMenu) { if (menuState.mode !== MenuModeEnum.HORIZONTAL) { @@ -155,10 +155,6 @@ export default defineComponent({ } } - const showTitle = computed(() => { - return props.collapsedShowTitle && menuStore.getCollapsedState; - }); - // render menu item function renderMenuItem(menuList?: MenuType[], index = 1) { if (!menuList) return; @@ -183,6 +179,7 @@ export default defineComponent({ , @@ -198,6 +195,7 @@ export default defineComponent({ showTitle={unref(showTitle)} item={menu} level={index} + isTop={props.isTop} searchValue={menuState.searchValue} />, ], diff --git a/src/components/Menu/src/MenuContent.tsx b/src/components/Menu/src/MenuContent.tsx index f0ffb026d65bdf9e4dd1deebca53b06d12a2918a..d4321a145575d85bb2235dd12f744b7ac7022a08 100644 --- a/src/components/Menu/src/MenuContent.tsx +++ b/src/components/Menu/src/MenuContent.tsx @@ -26,6 +26,10 @@ export default defineComponent({ type: Number as PropType, default: 0, }, + isTop: { + type: Boolean as PropType, + default: true, + }, }, setup(props) { /** @@ -56,14 +60,16 @@ export default defineComponent({ if (!props.item) { return null; } - const { showTitle } = props; + const { showTitle, isTop } = props; const { name, icon } = props.item; const searchValue = props.searchValue || ''; const index = name.indexOf(searchValue); const beforeStr = name.substr(0, index); const afterStr = name.substr(index + searchValue.length); - const cls = showTitle ? 'show-title' : 'basic-menu__name'; + let cls = showTitle ? ['show-title'] : ['basic-menu__name']; + + isTop && !showTitle && (cls = []); return ( <> {renderIcon(icon!)} diff --git a/src/components/Menu/src/SearchInput.vue b/src/components/Menu/src/SearchInput.vue index 7e60bc0104c747711827c0255abc0a953c9ffafa..80e00541c26ed85edf16b6559b0ae42dc65c7bda 100644 --- a/src/components/Menu/src/SearchInput.vue +++ b/src/components/Menu/src/SearchInput.vue @@ -102,7 +102,7 @@ .set-bg() { color: #fff; - background: @input-dark-bg-color; + background: @sider-dark-lighten-1-bg-color; border: 0; outline: none; } diff --git a/src/components/Menu/src/index.less b/src/components/Menu/src/index.less index 096a3f8fca6709d87a061188305b3573e9d3c76e..3cfa59f58da31e956f1ed09061fd199ca4e5f30f 100644 --- a/src/components/Menu/src/index.less +++ b/src/components/Menu/src/index.less @@ -52,10 +52,11 @@ // collapsed show title end .ant-menu-submenu-title { > .basic-menu__name { - display: flex; - width: 100%; - justify-content: space-between; - align-items: center; + .basic-menu__tag { + float: right; + margin-top: @app-menu-item-height / 2; + transform: translate(0%, -50%); + } } } @@ -254,7 +255,7 @@ // 层级样式 &.ant-menu-dark:not(.basic-menu__sidebar-hor) { overflow-x: hidden; - background: @menu-item-dark-bg-color; + background: @sider-dark-bg-color; .active-menu-style(); .ant-menu-item.ant-menu-item-selected.basic-menu-menu-item__level1, @@ -263,21 +264,20 @@ } .basic-menu-item__level1 { - background-color: @menu-item-dark-bg-color; + background-color: @sider-dark-bg-color; > .ant-menu-sub > li { - background-color: lighten(@menu-item-dark-bg-color, 6%); + background-color: @sider-dark-lighten-1-bg-color; } } .basic-menu-item__level2:not(.ant-menu-item-selected), .ant-menu-sub { - background-color: lighten(@menu-item-dark-bg-color, 6%); - // background-color: @sub-menu-item-dark-bg-color; + background-color: @sider-dark-lighten-1-bg-color; } .basic-menu-item__level3:not(.ant-menu-item-selected) { - background-color: lighten(@menu-item-dark-bg-color, 10%); + background-color: @sider-dark-lighten-2-bg-color; } .ant-menu-submenu-title { @@ -290,7 +290,7 @@ &.ant-menu-inline-collapsed { .ant-menu-submenu-selected, .ant-menu-item-selected { - background: darken(@menu-item-dark-bg-color, 6%) !important; + background: @sider-dark-darken-bg-color !important; } } } @@ -359,7 +359,7 @@ .ant-menu-dark { &.ant-menu-submenu-popup { > ul { - background: @menu-item-dark-bg-color; + background: @sider-dark-bg-color; } .active-menu-style(); diff --git a/src/design/color.less b/src/design/color.less index 7b8491785a8b8838529e89f1402c06b1e5f5823d..836755ad11a71868b73b193377106bfd2755bdd5 100644 --- a/src/design/color.less +++ b/src/design/color.less @@ -1,3 +1,17 @@ +:root { + // header + --header-bg-color: #394664; + --header-bg-hover-color: #273352; + --header-active-menu-bg-color: #273352; + + // sider + --sider-dark-bg-color: #273352; + --sider-dark-darken-bg-color: #273352; + --sider-dark-lighten-1-bg-color: #273352; + --sider-dark-lighten-2-bg-color: #273352; + --sider-dark-lighten-3-bg-color: #273352; +} + @white: #fff; @info-color: @primary-color; @@ -53,21 +67,24 @@ // ==============Header============= // ================================= -@header-dark-bg-color: #394664; -@header-dark-bg-hover-color: #273352; +@header-dark-bg-color: var(--header-bg-color); +@header-dark-bg-hover-color: var(--header-bg-hover-color); @header-light-bg-hover-color: #f6f6f6; @header-light-desc-color: #7c8087; @header-light-bottom-border-color: #eee; +// top-menu +@top-menu-active-bg-color: var(--header-active-menu-bg-color); // ================================= // ==============Menu============ // ================================= // let -menu -@menu-item-dark-bg-color: #273352; - -// top-menu -@top-menu-active-bg-color: #273352; +@sider-dark-bg-color: var(--sider-dark-bg-color); +@sider-dark-darken-bg-color: var(--sider-dark-darken-bg-color); +@sider-dark-lighten-1-bg-color: var(--sider-dark-lighten-1-bg-color); +@sider-dark-lighten-2-bg-color: var(--sider-dark-lighten-2-bg-color); +@sider-dark-lighten-3-bg-color: var(--sider-dark-lighten-3-bg-color); // trigger @trigger-dark-hover-bg-color: rgba(255, 255, 255, 0.2); diff --git a/src/layouts/default/header/LayoutHeader.tsx b/src/layouts/default/header/LayoutHeader.tsx index 830070f8f6af2c6434fc750d5c01531be994eac8..f81f4020d4fe04b84fd14dc08603846706ff94fc 100644 --- a/src/layouts/default/header/LayoutHeader.tsx +++ b/src/layouts/default/header/LayoutHeader.tsx @@ -79,9 +79,8 @@ export default defineComponent({ }); const showHeaderTrigger = computed(() => { - const { show, trigger, hidden } = unref(getProjectConfigRef).menuSetting; - - if (!show || !hidden) return false; + const { show, trigger, hidden, type } = unref(getProjectConfigRef).menuSetting; + if (type === MenuTypeEnum.TOP_MENU || !show || !hidden) return false; return trigger === TriggerEnum.HEADER; }); diff --git a/src/layouts/default/index.less b/src/layouts/default/index.less index 831411c11a1c15a2c0935a22e7138dad08a8225d..681e9b390b2939a04805eec2971b45eb2284af15 100644 --- a/src/layouts/default/index.less +++ b/src/layouts/default/index.less @@ -41,7 +41,7 @@ background-size: 100% 100%; &.ant-layout-sider-dark { - background: @menu-item-dark-bg-color; + background: @sider-dark-bg-color; } &:not(.ant-layout-sider-dark) { diff --git a/src/layouts/default/index.tsx b/src/layouts/default/index.tsx index f765b8d36ebcc7445d19de454282fbcef512714c..7d98ca152c40405efce8f5b4f4f5bee9381b3530 100644 --- a/src/layouts/default/index.tsx +++ b/src/layouts/default/index.tsx @@ -25,13 +25,9 @@ export default defineComponent({ const { getFullContent } = useFullContent(); - const getProjectConfigRef = computed(() => { - return appStore.getProjectConfig; - }); + const getProjectConfigRef = computed(() => appStore.getProjectConfig); - const getLockMainScrollStateRef = computed(() => { - return appStore.getLockMainScrollState; - }); + const getLockMainScrollStateRef = computed(() => appStore.getLockMainScrollState); const showHeaderRef = computed(() => { const { @@ -47,6 +43,12 @@ export default defineComponent({ return type !== MenuTypeEnum.SIDEBAR && unref(showHeaderRef); }); + const getIsLockRef = computed(() => { + const { getLockInfo } = appStore; + const { isLock } = getLockInfo; + return isLock; + }); + const showSideBarRef = computed(() => { const { menuSetting: { show, mode, split }, @@ -54,59 +56,74 @@ export default defineComponent({ return split || (show && mode !== MenuModeEnum.HORIZONTAL && !unref(getFullContent)); }); - function getTarget(): any { - const { - headerSetting: { fixed }, - } = unref(getProjectConfigRef); - return document.querySelector(`.default-layout__${fixed ? 'main' : 'content'}`); - } + const showFullHeaderRef = computed(() => { + return !unref(getFullContent) && unref(isShowMixHeaderRef) && unref(showHeaderRef); + }); - return () => { - const { getLockInfo } = appStore; + const showInsetHeaderRef = computed(() => { + return !unref(getFullContent) && !unref(isShowMixHeaderRef) && unref(showHeaderRef); + }); + + const fixedHeaderClsRef = computed(() => { const { - useOpenBackTop, - showSettingButton, - multiTabsSetting: { show: showTabs }, headerSetting: { fixed }, - menuSetting: { split, hidden }, } = unref(getProjectConfigRef); - const fixedHeaderCls = fixed ? 'fixed' + (unref(getLockMainScrollStateRef) ? ' lock' : '') : ''; + return fixedHeaderCls; + }); - const { isLock } = getLockInfo; + const showTabsRef = computed(() => { + const { + multiTabsSetting: { show }, + } = unref(getProjectConfigRef); + return show && !unref(getFullContent); + }); + + const showClassSideBarRef = computed(() => { + const { + menuSetting: { split, hidden }, + } = unref(getProjectConfigRef); + return split ? hidden : true; + }); - const showSideBar = split ? hidden : true; + function getTarget(): any { + const { + headerSetting: { fixed }, + } = unref(getProjectConfigRef); + return document.querySelector(`.default-layout__${fixed ? 'main' : 'content'}`); + } + + return () => { + const { useOpenBackTop, showSettingButton } = unref(getProjectConfigRef); return ( {() => ( <> {/* lock page */} - {isLock && } + {unref(getIsLockRef) && } {/* back top */} {useOpenBackTop && } {/* open setting drawer */} {showSettingButton && } - {!unref(getFullContent) && unref(isShowMixHeaderRef) && unref(showHeaderRef) && ( - - )} + {unref(showFullHeaderRef) && } {() => ( <> - {unref(showSideBarRef) && } - + {unref(showSideBarRef) && ( + + )} + {() => ( <> - {!unref(getFullContent) && - !unref(isShowMixHeaderRef) && - unref(showHeaderRef) && } + {unref(showInsetHeaderRef) && } - {showTabs && !unref(getFullContent) && } + {unref(showTabsRef) && } - + )} diff --git a/src/layouts/default/setting/SettingDrawer.tsx b/src/layouts/default/setting/SettingDrawer.tsx index 0d67d3c9aa2c0ea32ae324f19f55636191a998a0..381fed4d1cd2379a567a67cffc7a80bf335ca90d 100644 --- a/src/layouts/default/setting/SettingDrawer.tsx +++ b/src/layouts/default/setting/SettingDrawer.tsx @@ -20,12 +20,12 @@ import { updateColorWeak, updateGrayMode } from '/@/setup/theme'; import { baseHandler } from './handler'; import { HandlerEnum, - themeOptions, contentModeOptions, topMenuAlignOptions, menuTriggerOptions, routerTransitionOptions, } from './const'; +import { HEADER_PRESET_BG_COLOR_LIST, SIDE_BAR_BG_COLOR_LIST } from '/@/settings/colorSetting'; interface SwitchOptions { config?: DeepPartial; @@ -41,6 +41,11 @@ interface SelectConfig { handler?: Fn; } +interface ThemeOptions { + def?: string; + handler?: Fn; +} + export default defineComponent({ name: 'SettingDrawer', setup(_, { attrs }) { @@ -98,8 +103,7 @@ export default defineComponent({ function renderSidebar() { const { - headerSetting: { theme: headerTheme }, - menuSetting: { type, theme: menuTheme, split }, + menuSetting: { type, split }, } = unref(getProjectConfigRef); const typeList = ref([ @@ -154,22 +158,22 @@ export default defineComponent({ def: split, disabled: !unref(getShowMenuRef) || type !== MenuTypeEnum.MIX, }), - renderSelectItem('顶栏主题', { - handler: (e) => { - baseHandler(HandlerEnum.HEADER_THEME, e); - }, - def: headerTheme, - options: themeOptions, - disabled: !unref(getShowHeaderRef), - }), - renderSelectItem('菜单主题', { - handler: (e) => { - baseHandler(HandlerEnum.MENU_THEME, e); - }, - def: menuTheme, - options: themeOptions, - disabled: !unref(getShowMenuRef), - }), + // renderSelectItem('顶栏主题', { + // handler: (e) => { + // baseHandler(HandlerEnum.HEADER_THEME, e); + // }, + // def: headerTheme, + // options: themeOptions, + // disabled: !unref(getShowHeaderRef), + // }), + // renderSelectItem('菜单主题', { + // handler: (e) => { + // baseHandler(HandlerEnum.MENU_THEME, e); + // }, + // def: menuTheme, + // options: themeOptions, + // disabled: !unref(getShowMenuRef), + // }), ]; } /** @@ -413,7 +417,6 @@ export default defineComponent({ return (
{text} - {/* @ts-ignore */}