({
- key: tab.key,
- label: tab.label,
- closable: tab.closable,
- }))}
+
+ >
+ {/* 左侧:Tabs标签页 */}
+
+ ({
+ key: tab.key,
+ label: tab.label,
+ closable: tab.closable,
+ }))}
+ style={{
+ marginTop: 6,
+ marginBottom: 0,
+ }}
+ />
+
+
),
style: { backgroundColor: '#FFF' },
}}
diff --git a/src/common/components/layout/index.ts b/src/common/components/layout/index.ts
new file mode 100644
index 0000000..d242772
--- /dev/null
+++ b/src/common/components/layout/index.ts
@@ -0,0 +1,3 @@
+export { CustomLogo } from './CustomLogo';
+export { CustomHeader } from './CustomHeader';
+export { default as AvatarProps } from './AvatarProps';
diff --git a/src/common/libs/umi/layoutConfig.tsx b/src/common/libs/umi/layoutConfig.tsx
index acda85b..1917b05 100644
--- a/src/common/libs/umi/layoutConfig.tsx
+++ b/src/common/libs/umi/layoutConfig.tsx
@@ -1,7 +1,8 @@
// import Logo from '@/assets/bitcoin.webp';
import { MyIcons, MyIconsType, PermissionsType, useMyState } from '@/common';
+import { AvatarProps, CustomLogo } from '@/common/components/layout';
import { Link, RuntimeConfig, history } from '@umijs/max';
-import AvatarProps from '../../components/layout/AvatarProps';
+import MyLoGo from './logo.jpeg';
const loopMenu = (permissions: PermissionsType[] | undefined) => {
let tree: PermissionsType[] = [];
@@ -32,31 +33,93 @@ export const LayoutConfig: RuntimeConfig['layout'] = () => {
const { snap } = useMyState();
return {
- title: snap.session.campus?.name ?? '总后台',
- // logo:
,
- logo: <>>,
- layout: 'mix',
+ title: '物业管理平台',
+ logo: MyLoGo, // 禁用默认logo,使用自定义
+ layout: 'mix', // 从 'mix' 改为 'side'
colorPrimary: '#1890ff',
siderWidth: 220,
+ prefixCls: 'my-prefix',
pure: history.location.pathname === '/login',
+ // 禁用顶部导航栏的菜单
+ // 确保header显示 - 强制始终显示header,禁用响应式隐藏
+ header: true,
+ // 禁用响应式侧边栏,确保header始终显示
+ responsive: false,
+ // siderMenuType: 'inline',
+ // 隐藏面包屑导航
+ breadcrumb: { props: { style: { display: 'none' } } },
avatarProps: {
- render: () => ,
+ // src: 'https://gw.alipayobjects.com/zos/antfincdn/efFD%24IOql2/weixintupian_20170331104822.jpg',
+ // size: 'small',
+ // title: snap?.session?.user?.username ?? '-',
+ render: (props, dom) => {
+ return ;
+ // return (
+ // ,
+ // label: '退出登录',
+ // },
+ // ],
+ // }}
+ // >
+ // {dom}
+ //
+ // );
+ },
+ },
+ // 自定义Header渲染 - 右侧显示用户信息
+ // headerRender: (props, defaultDom) => {
+ // return (
+ //
+ // {/* 左侧可以为空 */}
+ //
+ // {/* 右侧添加用户信息 */}
+ //
+ //
+ // );
+ // },
+
+ // 新增:自定义Logo渲染
+ logoRenderer: (collapsed: boolean) => {
+ return ;
},
//水印设置
// waterMarkProps: {
// content: snap.session.user?.username,
// },
collapsedButtonRender: false,
+ // 禁用底部的版权信息等
+ footerRender: false,
token: {
- bgLayout: '#eef0f3',
+ bgLayout: '#f5f5f5', // 浅灰布局背景
header: {
- colorBgHeader: '#001529',
- colorHeaderTitle: '#FFF',
- colorTextRightActionsItem: '#FFF',
- heightLayoutHeader: 50,
+ colorBgHeader: '#ffffff', // 白色header背景
+ colorHeaderTitle: '#262626', // 深色标题文字
+ colorTextRightActionsItem: '#595959', // 深色操作文字
+ heightLayoutHeader: 64, // Header高度64px
},
sider: {
- colorMenuBackground: '#FFF',
+ colorMenuBackground: '#ffffff', // 白色菜单背景
+ colorMenuText: '#595959', // 深色菜单文字
+ colorMenuTextSelected: '#1890ff', // 激活菜单文字蓝色
+ colorMenuItemBgSelected: '#e6f7ff', // 激活菜单背景浅蓝
+ colorMenuDivider: '#f0f0f0', // 分割线颜色
},
},
menuItemRender: (item, dom) => {dom},
diff --git a/src/common/libs/umi/layoutConfig.tsx.backup b/src/common/libs/umi/layoutConfig.tsx.backup
new file mode 100644
index 0000000..acda85b
--- /dev/null
+++ b/src/common/libs/umi/layoutConfig.tsx.backup
@@ -0,0 +1,79 @@
+// import Logo from '@/assets/bitcoin.webp';
+import { MyIcons, MyIconsType, PermissionsType, useMyState } from '@/common';
+import { Link, RuntimeConfig, history } from '@umijs/max';
+import AvatarProps from '../../components/layout/AvatarProps';
+
+const loopMenu = (permissions: PermissionsType[] | undefined) => {
+ let tree: PermissionsType[] = [];
+ let map: Record = {};
+ permissions?.forEach((permission) => {
+ map[permission.id] = {
+ path: permission.type === 'Button' ? 'null' : permission.path,
+ name: permission.name,
+ icon: permission.icon && MyIcons[permission.icon as MyIconsType],
+ children: [],
+ hideInMenu: permission.type === 'Button',
+ };
+ });
+
+ permissions?.forEach((permission) => {
+ let node = map[permission.id];
+ if (permission.parent_id !== null) {
+ map[permission.parent_id].children.push(node);
+ } else {
+ tree.push(node);
+ }
+ });
+
+ return tree?.[0]?.children;
+};
+
+export const LayoutConfig: RuntimeConfig['layout'] = () => {
+ const { snap } = useMyState();
+
+ return {
+ title: snap.session.campus?.name ?? '总后台',
+ // logo:
,
+ logo: <>>,
+ layout: 'mix',
+ colorPrimary: '#1890ff',
+ siderWidth: 220,
+ pure: history.location.pathname === '/login',
+ avatarProps: {
+ render: () => ,
+ },
+ //水印设置
+ // waterMarkProps: {
+ // content: snap.session.user?.username,
+ // },
+ collapsedButtonRender: false,
+ token: {
+ bgLayout: '#eef0f3',
+ header: {
+ colorBgHeader: '#001529',
+ colorHeaderTitle: '#FFF',
+ colorTextRightActionsItem: '#FFF',
+ heightLayoutHeader: 50,
+ },
+ sider: {
+ colorMenuBackground: '#FFF',
+ },
+ },
+ menuItemRender: (item, dom) => {dom},
+ menu: {
+ params: snap.session.permissions,
+ request: async () => {
+ let objjs: any = [];
+ snap.session.permissions?.forEach((res: any) => {
+ objjs.push(res);
+ });
+ let data = objjs.sort((a: any, b: any) => {
+ return a._lft - b._lft;
+ });
+ const menus = loopMenu(data);
+ return Promise.resolve(menus);
+ },
+ },
+ unAccessible: unAccessible
,
+ };
+};
diff --git a/src/common/libs/umi/logo.jpeg b/src/common/libs/umi/logo.jpeg
new file mode 100644
index 0000000..ec10a03
Binary files /dev/null and b/src/common/libs/umi/logo.jpeg differ
diff --git a/src/common/pages/MyLoginPage1.tsx b/src/common/pages/MyLoginPage1.tsx
index 8365b17..627d044 100644
--- a/src/common/pages/MyLoginPage1.tsx
+++ b/src/common/pages/MyLoginPage1.tsx
@@ -12,6 +12,7 @@ import {
import { useEffect, useState } from 'react';
import { useNavigate } from 'react-router-dom';
import { stateActions } from '..';
+import loginBgImg from './loginBgImg.jpg';
export function MyLoginPage1() {
const navigate = useNavigate();
@@ -37,8 +38,9 @@ export function MyLoginPage1() {
>
title="欢迎使用后台管理系统"
- backgroundVideoUrl="https://gw.alipayobjects.com/v/huamei_gcee1x/afts/video/jXRBRK_VAwoAAAAAAAAAAAAAK4eUAQBr"
- subTitle="Admin management system"
+ // backgroundVideoUrl="https://gw.alipayobjects.com/v/huamei_gcee1x/afts/video/jXRBRK_VAwoAAAAAAAAAAAAAK4eUAQBr"
+ backgroundImageUrl={loginBgImg}
+ subTitle="物业管理平台"
onFinish={async (values: any) => {
Apis.Common.Auth.Login({
...values,
diff --git a/src/common/pages/loginBgImg.jpg b/src/common/pages/loginBgImg.jpg
new file mode 100644
index 0000000..7493aea
Binary files /dev/null and b/src/common/pages/loginBgImg.jpg differ
diff --git a/src/global.less b/src/global.less
new file mode 100644
index 0000000..04587d2
--- /dev/null
+++ b/src/global.less
@@ -0,0 +1,274 @@
+@import '~antd/es/style/reset.css';
+
+// 全局样式
+body {
+ margin: 0;
+ padding: 0;
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto,
+ 'Helvetica Neue', Arial, sans-serif;
+ font-size: 14px;
+ line-height: 1.5715;
+ color: #262626;
+ background-color: #f5f5f5;
+}
+
+// // 自定义Logo样式
+// .custom-logo {
+// display: flex;
+// align-items: center;
+// height: 64px;
+// padding: 0 16px;
+// border-bottom: 1px solid #f0f0f0;
+// transition: all 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);
+// background: #ffffff;
+// }
+
+// .custom-logo .logo-icon {
+// font-size: 32px;
+// min-width: 32px;
+// display: flex;
+// align-items: center;
+// justify-content: center;
+// }
+
+// .custom-logo .logo-text {
+// margin-left: 12px;
+// font-size: 16px;
+// font-weight: 600;
+// color: #262626;
+// white-space: nowrap;
+// opacity: 1;
+// transition: opacity 0.2s;
+// }
+
+// // 折叠状态
+// .ant-layout-sider-collapsed .custom-logo {
+// padding: 0;
+// justify-content: center;
+// }
+
+// .ant-layout-sider-collapsed .custom-logo .logo-text {
+// display: none;
+// }
+
+// // PageContainer Header样式 - 固定悬浮在UmiJS Header下方
+// div[class*='page-container-header'],
+// .ant-pro-page-container > div[class*='page-container-header'],
+// .ant-pro-page-container-header {
+// position: fixed !important;
+// top: 64px !important; /* UmiJS Header的高度 */
+// right: 0 !important;
+// left: 220px !important; /* 侧边栏宽度 */
+// z-index: 999 !important;
+// margin: 0 !important;
+// padding: 8px 24px !important; /* 增加padding */
+// background: #ffffff !important;
+// border-bottom: 1px solid #f0f0f0 !important;
+// box-shadow: 0 1px 4px rgba(0, 0, 0, 0.05) !important;
+// height: auto !important;
+// min-height: 40px !important;
+// max-height: 52px !important;
+// display: flex !important;
+// align-items: center !important;
+// }
+
+// // 当侧边栏折叠时,调整tabs header的left值
+// .ant-layout-sider-collapsed ~ .ant-layout .ant-pro-page-container-header {
+// left: 64px !important;
+// }
+
+// // 强制PageContainer header样式
+// .ant-pro-page-container .ant-pro-page-container-header {
+// position: fixed !important;
+// top: 64px !important;
+// right: 0 !important;
+// left: 220px !important;
+// z-index: 999 !important;
+// margin: 0 !important;
+// padding: 8px 24px !important;
+// min-height: 40px !important;
+// max-height: 52px !important;
+// display: flex !important;
+// align-items: center !important;
+// }
+
+// // 确保UmiJS Header固定在顶部
+// .ant-pro-header,
+// .ant-layout-header {
+// position: fixed !important;
+// top: 0 !important;
+// right: 0 !important;
+// left: 220px !important;
+// z-index: 1000 !important;
+// width: auto !important;
+// background: #ffffff !important;
+// border-bottom: 1px solid #f0f0f0 !important;
+// }
+
+// .ant-layout-sider-collapsed ~ .ant-layout .ant-pro-header,
+// .ant-layout-sider-collapsed + .ant-layout .ant-pro-header {
+// left: 64px !important;
+// }
+
+// // Tabs样式优化 - 减小高度
+// .ant-pro-page-container-header .tabs-header-only,
+// div[class*='page-container-header'] .tabs-header-only {
+// margin: 0 !important;
+// line-height: 1 !important;
+// height: auto !important;
+// display: flex !important;
+// align-items: center !important;
+// }
+
+// .ant-pro-page-container-header .ant-tabs,
+// div[class*='page-container-header'] .ant-tabs {
+// margin: 0 !important;
+// height: auto !important;
+// }
+
+// .ant-pro-page-container-header .ant-tabs-nav,
+// div[class*='page-container-header'] .ant-tabs-nav {
+// margin-bottom: 0 !important;
+// height: auto !important;
+// }
+
+// .ant-pro-page-container-header .ant-tabs-nav-list,
+// div[class*='page-container-header'] .ant-tabs-nav-list {
+// margin-bottom: 0 !important;
+// height: auto !important;
+// display: flex !important;
+// align-items: center !important;
+// }
+
+// .ant-pro-page-container-header .ant-tabs-tab,
+// div[class*='page-container-header'] .ant-tabs-tab {
+// padding: 4px 10px !important;
+// background: #f5f5f5;
+// border-radius: 4px;
+// margin-right: 4px;
+// transition: all 0.2s;
+// height: 26px !important;
+// line-height: 26px !important;
+// font-size: 13px;
+// display: inline-flex !important;
+// align-items: center !important;
+// }
+
+// .ant-pro-page-container-header .ant-tabs-tab-active,
+// div[class*='page-container-header'] .ant-tabs-tab-active {
+// background: #ffffff;
+// font-weight: 500;
+// }
+
+// .ant-pro-page-container-header .ant-tabs-ink-bar,
+// div[class*='page-container-header'] .ant-tabs-ink-bar {
+// display: none !important;
+// }
+
+// // 内容区域 - 调整padding以适应固定的header
+.ant-pro-grid-content {
+ padding: 15px;
+ // padding-top: 20px; /* 64px UmiJS Header + 48px tabs header + 8px */
+}
+.ant-page-header {
+ padding: 0 15px !important;
+}
+// .ant-pro-page-container {
+// padding-top: 0 !important;
+// }
+
+// .ant-pro-page-container-warp {
+// padding: 0 !important;
+// }
+
+// .ant-pro-page-container-children-content {
+// padding: 24px !important;
+// padding-top: 0 !important;
+// }
+
+// // 确保主内容区域正确的padding
+// .custom-header .header-left {
+// flex: 1;
+// }
+
+// .custom-header .header-right {
+// display: flex;
+// align-items: center;
+// gap: 16px;
+// }
+
+// .custom-header .header-right > div {
+// display: flex;
+// align-items: center;
+// transition: opacity 0.2s;
+// }
+
+// .custom-header .header-right > div:hover {
+// opacity: 0.8;
+// }
+
+// // 内容区域 - 添加顶部padding避免被固定header遮挡
+// .ant-pro-grid-content {
+// padding: 24px;
+// padding-top: 24px; /* 恢复正常padding */
+// }
+
+// .ant-pro-page-container {
+// padding-top: 0 !important;
+// }
+
+// .ant-pro-page-container-children-content {
+// padding-top: 0 !important;
+// padding: 24px !important;
+// }
+
+// // 页面容器卡片
+// .ant-pro-page-container {
+// background: transparent;
+// }
+
+// .ant-pro-page-container .ant-pro-page-container-warp {
+// background: #ffffff;
+// border-radius: 8px;
+// box-shadow: 0 1px 2px 0 rgba(0, 0, 0, 0.03);
+// padding: 24px;
+// }
+
+// // 隐藏侧边栏底部的用户信息区域
+.ant-pro-sider .ant-pro-sider-actions {
+ display: none !important;
+}
+
+.ant-pro-sider-collapsed .ant-pro-sider-actions {
+ display: none !important;
+}
+.my-prefix-sider-actions {
+ // display: none !important;
+}
+
+// 确保顶部Header始终显示,不受响应式影响
+// .ant-pro-header {
+// display: flex !important;
+// width: 100% !important;
+// }
+
+// 确保在所有屏幕尺寸下header都显示
+// @media (min-width: 0px) {
+// .ant-pro-header {
+// display: flex !important;
+// }
+// }
+
+// .ant-layout-header {
+// display: flex !important;
+// }
+
+// // 确保顶部Header显示
+// .ant-pro-header {
+// display: flex !important;
+// }
+
+// // 确保PageContainer的affix header显示
+// .ant-pro-page-container-affix {
+// display: block !important;
+// }