build: init

This commit is contained in:
dayjoy
2024-10-14 18:51:44 +08:00
commit 6f6f976d24
70 changed files with 13878 additions and 0 deletions

150
template/src/utils/menu.tsx Normal file
View File

@@ -0,0 +1,150 @@
import { metaInfo } from '@/meta';
import React from 'react';
import { FormattedMessage } from 'react-intl';
export type MenuItem = {
key: string;
label: string | React.ReactElement;
disabled?: boolean;
icon?: React.ReactNode;
children?: MenuItem[];
_order?: number;
};
const formatDisplayName = (displayName: string) => {
// 用 {{xxx}} 包起来的字符串需要处理国际化
if (/^{{(.*)}}$/.test(displayName)) {
const key = displayName.match(/^{{(.*)}}$/)![1].trim();
return <FormattedMessage id={key} />;
}
return displayName;
};
const flatten = (info: Meta[]) => {
const result: Meta[] = [];
info.forEach((item) => {
if (item._children?.length) {
result.push(...flatten(item._children));
} else {
result.push(item);
}
});
return result;
};
const deeplySortMenu = (menus: MenuItem[]) => {
const newMenus = [...menus];
newMenus.sort((a, b) => a._order! - b._order!);
newMenus.forEach((menu) => {
if (menu.children) {
menu.children = deeplySortMenu(menu.children);
}
});
return newMenus;
};
const getMenuItems = (): MenuItem[] => {
const menus: MenuItem[] = [];
const flatMetaInfo = flatten(metaInfo);
// head
flatMetaInfo.forEach((item) => {
if (!item.headMenu) return;
// 非路由页面头部菜单
if (typeof item.headMenu !== 'boolean') {
const find = menus.find(
(menu) => menu.key === (item.headMenu as any)?.key,
);
if (!find) {
menus.push({
key: (item.headMenu as any)?.key,
label: formatDisplayName((item.headMenu as any)?.label),
_order: (item.headMenu as any)?.order ?? 0,
});
}
}
// 路由页面头部菜单
if (item.headMenu === true) {
menus.push({
key: item._fullpath ?? '',
label: formatDisplayName(item.displayName ?? ''),
_order: item.order ?? 0,
});
}
});
// side
flatMetaInfo.forEach((item) => {
if (!item.sideMenu) return;
const head = menus.find((menu) => menu.key === (item.headMenu as any)?.key);
if (!head) return;
if (!head.children) head.children = [];
// 非路由页面侧边菜单(分组)
if (typeof item.sideMenu !== 'boolean') {
const find = head.children.find(
(menu) => menu.key === (item.sideMenu as any)?.key,
);
if (!find) {
head.children.push({
key: (item.sideMenu as any)?.key,
label: formatDisplayName((item.sideMenu as any)?.label),
_order: (item.sideMenu as any)?.order,
children: [
{
key: item._fullpath ?? '',
label: formatDisplayName(item.displayName ?? ''),
_order: item.order ?? 0,
},
],
});
} else {
find.children!.push({
key: item._fullpath ?? '',
label: formatDisplayName(item.displayName ?? ''),
_order: item.order ?? 0,
});
}
}
// 路由页面侧边菜单
if (item.sideMenu === true) {
head.children.push({
key: item._fullpath ?? '',
label: formatDisplayName(item.displayName ?? ''),
_order: item.order ?? 0,
});
}
});
// sort
return deeplySortMenu(menus);
};
export const menuItems = getMenuItems();
export const findHeadMenuByHeadKey = (headKey) => {
return menuItems.find((menu) => menu.key === headKey);
};
export const findHeadMenuBySideKey = (
sideKey: string,
menus: MenuItem[] = menuItems,
): MenuItem | null => {
const find = menus.find((menu) =>
menu.children?.some(
(child) =>
child.key === sideKey ||
!!findHeadMenuBySideKey(sideKey, menu.children ?? []),
),
);
if (find) return find;
return null;
};
export const findFirstSubMenu = (menu: MenuItem): MenuItem | undefined => {
if (!menu?.children?.[0]?.children?.length) return menu?.children?.[0];
return findFirstSubMenu(menu.children[0]);
};