@wzyjs/uis 0.3.29 → 0.3.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/advanced/Com2Canvas/index.d.ts +8 -0
- package/dist/advanced/Com2Canvas/index.js +39 -0
- package/dist/advanced/Crud/components/CardList/index.d.ts +2 -0
- package/dist/advanced/Crud/components/CardList/index.js +90 -0
- package/dist/advanced/Crud/components/CreateUpdate/index.d.ts +2 -0
- package/dist/advanced/Crud/components/CreateUpdate/index.js +78 -0
- package/dist/advanced/Crud/components/ListTabs/index.d.ts +8 -0
- package/dist/advanced/Crud/components/ListTabs/index.js +7 -0
- package/dist/advanced/Crud/components/Provider/index.d.ts +7 -0
- package/dist/advanced/Crud/components/Provider/index.js +42 -0
- package/dist/advanced/Crud/components/QuickFilters/index.d.ts +8 -0
- package/dist/advanced/Crud/components/QuickFilters/index.js +20 -0
- package/dist/advanced/Crud/components/Remove/index.d.ts +2 -0
- package/dist/advanced/Crud/components/Remove/index.js +18 -0
- package/dist/advanced/Crud/components/index.d.ts +6 -0
- package/dist/advanced/Crud/components/index.js +6 -0
- package/dist/advanced/Crud/hooks/index.d.ts +5 -0
- package/dist/advanced/Crud/hooks/index.js +5 -0
- package/dist/advanced/Crud/hooks/useColumns.d.ts +11 -0
- package/dist/advanced/Crud/hooks/useColumns.js +111 -0
- package/dist/advanced/Crud/hooks/useList.d.ts +12 -0
- package/dist/advanced/Crud/hooks/useList.js +53 -0
- package/dist/advanced/Crud/hooks/useListFilters.d.ts +11 -0
- package/dist/advanced/Crud/hooks/useListFilters.js +159 -0
- package/dist/advanced/Crud/hooks/useOrderable.d.ts +15 -0
- package/dist/advanced/Crud/hooks/useOrderable.js +75 -0
- package/dist/advanced/Crud/hooks/useRequest.d.ts +13 -0
- package/dist/advanced/Crud/hooks/useRequest.js +27 -0
- package/dist/advanced/Crud/index.d.ts +3 -0
- package/dist/advanced/Crud/index.js +46 -0
- package/dist/advanced/Crud/types/index.d.ts +176 -0
- package/dist/advanced/Crud/types/index.js +1 -0
- package/dist/advanced/Crud/utils/index.d.ts +7 -0
- package/dist/advanced/Crud/utils/index.js +80 -0
- package/dist/advanced/Crud/utils/query.d.ts +3 -0
- package/dist/advanced/Crud/utils/query.js +34 -0
- package/dist/advanced/MindMap/context.d.ts +12 -0
- package/dist/advanced/MindMap/context.js +12 -0
- package/dist/advanced/MindMap/hooks/useAlignmentSnap.d.ts +15 -0
- package/dist/advanced/MindMap/hooks/useAlignmentSnap.js +164 -0
- package/dist/advanced/MindMap/hooks/useCopyPaste.d.ts +11 -0
- package/dist/advanced/MindMap/hooks/useCopyPaste.js +209 -0
- package/dist/advanced/MindMap/hooks/useDropToReparent.d.ts +21 -0
- package/dist/advanced/MindMap/hooks/useDropToReparent.js +216 -0
- package/dist/advanced/MindMap/hooks/useExpandCollapse.d.ts +18 -0
- package/dist/advanced/MindMap/hooks/useExpandCollapse.js +108 -0
- package/dist/advanced/MindMap/hooks/useMoveDescendants.d.ts +12 -0
- package/dist/advanced/MindMap/hooks/useMoveDescendants.js +98 -0
- package/dist/advanced/MindMap/hooks/useUndoRedo.d.ts +14 -0
- package/dist/advanced/MindMap/hooks/useUndoRedo.js +181 -0
- package/dist/advanced/MindMap/index.d.ts +29 -0
- package/dist/advanced/MindMap/index.js +52 -0
- package/dist/advanced/index.d.ts +5 -0
- package/dist/advanced/index.js +5 -0
- package/dist/antd/index.d.ts +6 -0
- package/dist/antd/index.js +5 -0
- package/dist/buttons/ButtonGroup/index.d.ts +8 -0
- package/dist/buttons/ButtonGroup/index.js +13 -0
- package/dist/buttons/ConfirmButton/index.d.ts +5 -0
- package/dist/buttons/ConfirmButton/index.js +9 -0
- package/dist/buttons/CopyButton/index.d.ts +6 -0
- package/dist/buttons/CopyButton/index.js +26 -0
- package/dist/buttons/DrawerButton/index.d.ts +6 -0
- package/dist/buttons/DrawerButton/index.js +13 -0
- package/dist/buttons/ProgressButton/index.css +63 -0
- package/dist/buttons/ProgressButton/index.d.ts +17 -0
- package/dist/buttons/ProgressButton/index.js +31 -0
- package/dist/buttons/SectorButton/index.d.ts +20 -0
- package/dist/buttons/SectorButton/index.js +130 -0
- package/dist/buttons/index.d.ts +6 -0
- package/dist/buttons/index.js +6 -0
- package/dist/display/CodeView/index.d.ts +26 -0
- package/dist/display/CodeView/index.js +60 -0
- package/dist/display/EnumTag/index.d.ts +12 -0
- package/dist/display/EnumTag/index.js +10 -0
- package/dist/display/HtmlDataRenderer/index.d.ts +6 -0
- package/dist/display/HtmlDataRenderer/index.js +15 -0
- package/dist/display/HtmlView/index.d.ts +6 -0
- package/dist/display/HtmlView/index.js +6 -0
- package/dist/display/IframePro/index.d.ts +8 -0
- package/dist/display/IframePro/index.js +24 -0
- package/dist/display/JsonSchemaRenderer/index.d.ts +11 -0
- package/dist/display/JsonSchemaRenderer/index.js +62 -0
- package/dist/display/JsonView/index.d.ts +3 -0
- package/dist/display/JsonView/index.js +7 -0
- package/dist/display/MarkdownView/index.d.ts +7 -0
- package/dist/display/MarkdownView/index.js +80 -0
- package/dist/display/MarkdownView/style.d.ts +1 -0
- package/{src/components/Markdown/style.ts → dist/display/MarkdownView/style.js} +1 -1
- package/dist/display/VideoPro/index.d.ts +9 -0
- package/dist/display/VideoPro/index.js +15 -0
- package/dist/display/index.d.ts +9 -0
- package/dist/display/index.js +9 -0
- package/dist/inputs/CheckboxButton/index.css +22 -0
- package/dist/inputs/CheckboxButton/index.d.ts +12 -0
- package/dist/inputs/CheckboxButton/index.js +9 -0
- package/dist/inputs/DateSwitcher/index.css +10 -0
- package/dist/inputs/DateSwitcher/index.d.ts +8 -0
- package/dist/inputs/DateSwitcher/index.js +29 -0
- package/dist/inputs/FetchSelect/index.d.ts +3 -0
- package/dist/inputs/FetchSelect/index.js +121 -0
- package/dist/inputs/FetchSelect/types.d.ts +33 -0
- package/dist/inputs/FetchSelect/types.js +1 -0
- package/dist/inputs/FetchSelect/utils.d.ts +21 -0
- package/dist/inputs/FetchSelect/utils.js +67 -0
- package/dist/inputs/FileUploader/index.d.ts +22 -0
- package/dist/inputs/FileUploader/index.js +79 -0
- package/dist/inputs/IconSelect/index.d.ts +89 -0
- package/dist/inputs/IconSelect/index.js +54 -0
- package/dist/inputs/ImageUploader/index.d.ts +12 -0
- package/dist/inputs/ImageUploader/index.js +192 -0
- package/dist/inputs/RadioButton/index.d.ts +15 -0
- package/dist/inputs/RadioButton/index.js +11 -0
- package/dist/inputs/RangeInput/index.d.ts +8 -0
- package/dist/inputs/RangeInput/index.js +17 -0
- package/dist/inputs/TextInput/index.d.ts +6 -0
- package/dist/inputs/TextInput/index.js +30 -0
- package/dist/inputs/index.d.ts +9 -0
- package/dist/inputs/index.js +9 -0
- package/dist/layout/DragSort/index.d.ts +16 -0
- package/dist/layout/DragSort/index.js +12 -0
- package/dist/layout/FoldCard/index.d.ts +9 -0
- package/dist/layout/FoldCard/index.js +69 -0
- package/dist/layout/PageBase/index.d.ts +6 -0
- package/dist/layout/PageBase/index.js +6 -0
- package/dist/layout/ResizableGridLayout/index.d.ts +11 -0
- package/dist/layout/ResizableGridLayout/index.js +13 -0
- package/dist/layout/SideMenu/index.d.ts +27 -0
- package/dist/layout/SideMenu/index.js +40 -0
- package/dist/layout/TabsPro/index.d.ts +9 -0
- package/dist/layout/TabsPro/index.js +87 -0
- package/dist/layout/index.d.ts +6 -0
- package/dist/layout/index.js +6 -0
- package/dist/web.d.ts +6 -0
- package/dist/web.js +6 -0
- package/package.json +28 -11
- package/src/antd/form/CheckboxButton/index.module.scss +0 -24
- package/src/antd/form/CheckboxButton/index.tsx +0 -31
- package/src/antd/form/FileUploader/index.tsx +0 -163
- package/src/antd/form/RadioButton/index.tsx +0 -32
- package/src/antd/form/Upload/index.tsx +0 -65
- package/src/antd/form/UploadImage/index.tsx +0 -338
- package/src/antd/form/index.ts +0 -6
- package/src/antd/index.ts +0 -46
- package/src/antd/pro/FoldCard/index.tsx +0 -131
- package/src/antd/pro/RangeInput/index.tsx +0 -46
- package/src/antd/pro/Tabs/index.tsx +0 -135
- package/src/antd/pro/Typography/components/String.tsx +0 -72
- package/src/antd/pro/Typography/index.tsx +0 -9
- package/src/antd/pro/buttons/ButtonGroup.tsx +0 -26
- package/src/antd/pro/buttons/ConfirmButton.tsx +0 -24
- package/src/antd/pro/buttons/CopyButton.tsx +0 -47
- package/src/antd/pro/buttons/DrawerButton.tsx +0 -37
- package/src/antd/pro/buttons/index.tsx +0 -4
- package/src/antd/pro/index.ts +0 -5
- package/src/components/BottomBar/index.tsx +0 -28
- package/src/components/CodeView/index.tsx +0 -85
- package/src/components/Collapse/index.tsx +0 -26
- package/src/components/Com2Canvas/index.tsx +0 -60
- package/src/components/CompileHtml/index.tsx +0 -26
- package/src/components/Crud/components/CardList/index.tsx +0 -174
- package/src/components/Crud/components/CreateUpdate/index.tsx +0 -179
- package/src/components/Crud/components/Provider/index.tsx +0 -83
- package/src/components/Crud/components/Remove/index.tsx +0 -56
- package/src/components/Crud/components/index.ts +0 -4
- package/src/components/Crud/hooks/index.ts +0 -4
- package/src/components/Crud/hooks/useColumns.tsx +0 -169
- package/src/components/Crud/hooks/useList.ts +0 -65
- package/src/components/Crud/hooks/useOrderable.tsx +0 -107
- package/src/components/Crud/hooks/useRequest.ts +0 -41
- package/src/components/Crud/index.tsx +0 -91
- package/src/components/Crud/types/index.ts +0 -188
- package/src/components/Crud/utils/index.ts +0 -87
- package/src/components/DateSwitcher/index.module.scss +0 -10
- package/src/components/DateSwitcher/index.tsx +0 -75
- package/src/components/DownloadLink/index.tsx +0 -36
- package/src/components/DragSort/index.tsx +0 -77
- package/src/components/DynamicSelect/index.tsx +0 -76
- package/src/components/DynamicSelect/types.ts +0 -8
- package/src/components/DynamicSelect/utils.ts +0 -47
- package/src/components/EnumTag/index.tsx +0 -24
- package/src/components/FetchSelect/index.tsx +0 -57
- package/src/components/FormPro/index.tsx +0 -28
- package/src/components/GroupLayout/index.tsx +0 -45
- package/src/components/HtmlPro/index.tsx +0 -18
- package/src/components/IframePro/index.tsx +0 -52
- package/src/components/JsonRenderer/index.tsx +0 -114
- package/src/components/JsonView/index.tsx +0 -21
- package/src/components/Markdown/index.tsx +0 -152
- package/src/components/MindMap/context.tsx +0 -29
- package/src/components/MindMap/hooks/useAlignmentSnap.ts +0 -220
- package/src/components/MindMap/hooks/useCopyPaste.ts +0 -272
- package/src/components/MindMap/hooks/useDropToReparent.ts +0 -288
- package/src/components/MindMap/hooks/useExpandCollapse.ts +0 -146
- package/src/components/MindMap/hooks/useMoveDescendants.ts +0 -136
- package/src/components/MindMap/hooks/useUndoRedo.ts +0 -232
- package/src/components/MindMap/index.tsx +0 -117
- package/src/components/MultiImageDisplay/index.tsx +0 -63
- package/src/components/ProgressButton/index.module.scss +0 -65
- package/src/components/ProgressButton/index.tsx +0 -96
- package/src/components/SectorButton/index.tsx +0 -247
- package/src/components/TextInput/index.tsx +0 -61
- package/src/components/TimelineBar/components/CurrentWeekHighlight/index.tsx +0 -64
- package/src/components/TimelineBar/components/Guides/index.tsx +0 -61
- package/src/components/TimelineBar/components/Ticks/index.tsx +0 -56
- package/src/components/TimelineBar/components/TodayIndicator/index.tsx +0 -54
- package/src/components/TimelineBar/components/index.ts +0 -4
- package/src/components/TimelineBar/const.ts +0 -3
- package/src/components/TimelineBar/hooks/index.ts +0 -5
- package/src/components/TimelineBar/hooks/useHighlightRange.ts +0 -21
- package/src/components/TimelineBar/hooks/useMonthGuides.ts +0 -40
- package/src/components/TimelineBar/hooks/useTickValues.ts +0 -18
- package/src/components/TimelineBar/hooks/useVisibleRange.ts +0 -43
- package/src/components/TimelineBar/hooks/useWeekGuides.ts +0 -39
- package/src/components/TimelineBar/index.tsx +0 -63
- package/src/components/TimelineBar/utils.ts +0 -27
- package/src/components/Video/index.tsx +0 -37
- package/src/components/index.ts +0 -26
- package/src/rn.ts +0 -1
- package/src/rns/index.ts +0 -0
- package/src/web.ts +0 -2
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
@keyframes wzy-ui-progress-button-complete {
|
|
2
|
+
0% {
|
|
3
|
+
transform: scale(1) rotateY(0deg);
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
20% {
|
|
7
|
+
transform: scale(0.9) rotateY(36deg);
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
40% {
|
|
11
|
+
transform: scale(0.95) rotateY(72deg);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
60% {
|
|
15
|
+
transform: scale(1) rotateY(108deg);
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
80% {
|
|
19
|
+
transform: scale(1.05) rotateY(144deg);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
100% {
|
|
23
|
+
transform: scale(1) rotateY(180deg);
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
@keyframes wzy-ui-progress-button-counter-rotate {
|
|
28
|
+
0% {
|
|
29
|
+
transform: rotateY(0deg);
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
20% {
|
|
33
|
+
transform: rotateY(-36deg);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
40% {
|
|
37
|
+
transform: rotateY(-72deg);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
60% {
|
|
41
|
+
transform: rotateY(-108deg);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
80% {
|
|
45
|
+
transform: rotateY(-144deg);
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
100% {
|
|
49
|
+
transform: rotateY(-180deg);
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
.wzy-ui-progress-button .animate-complete {
|
|
54
|
+
animation: wzy-ui-progress-button-complete 0.6s cubic-bezier(0, 0, 1, 1);
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
.wzy-ui-progress-button .animate-counter-rotate {
|
|
58
|
+
animation: wzy-ui-progress-button-counter-rotate 0.6s cubic-bezier(0, 0, 1, 1);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
.wzy-ui-progress-button .perspective {
|
|
62
|
+
perspective: 1000px;
|
|
63
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { type ReactNode } from 'react';
|
|
2
|
+
import './index.css';
|
|
3
|
+
interface ProgressButtonProps {
|
|
4
|
+
colors?: {
|
|
5
|
+
bg: string;
|
|
6
|
+
ring: string;
|
|
7
|
+
};
|
|
8
|
+
showRing?: boolean;
|
|
9
|
+
progress?: number;
|
|
10
|
+
padding?: number;
|
|
11
|
+
size?: number;
|
|
12
|
+
strokeWidth?: number;
|
|
13
|
+
children?: ReactNode;
|
|
14
|
+
className?: string;
|
|
15
|
+
}
|
|
16
|
+
export declare const ProgressButton: (props: ProgressButtonProps) => import("react/jsx-runtime").JSX.Element;
|
|
17
|
+
export {};
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import './index.css';
|
|
3
|
+
export const ProgressButton = (props) => {
|
|
4
|
+
const { colors, // 按钮颜色配置
|
|
5
|
+
showRing = false, // 是否显示进度环
|
|
6
|
+
progress = 0, // 进度值(0-1)
|
|
7
|
+
padding = 0, // 内边距
|
|
8
|
+
strokeWidth = 5, // 进度环宽度
|
|
9
|
+
size = 50, // 按钮大小
|
|
10
|
+
children, // 子元素
|
|
11
|
+
className = '', // 自定义className
|
|
12
|
+
} = props;
|
|
13
|
+
// 计算进度环的半径
|
|
14
|
+
const radius = (size / 2) - strokeWidth - padding + 2.5;
|
|
15
|
+
// 计算进度环的周长
|
|
16
|
+
const circumference = 2 * Math.PI * radius;
|
|
17
|
+
// 计算进度环的偏移量,用于显示进度
|
|
18
|
+
const offset = circumference * (1 - progress);
|
|
19
|
+
return (_jsx("div", { className: 'wzy-ui-progress-button', children: _jsxs("div", { style: { width: size, height: size }, className: `relative rounded-full
|
|
20
|
+
flex items-center justify-center
|
|
21
|
+
cursor-pointer hover:opacity-90
|
|
22
|
+
focus:outline-none focus:ring-2 focus:ring-offset-2
|
|
23
|
+
${colors?.bg}
|
|
24
|
+
${colors?.ring}
|
|
25
|
+
transform-gpu transition-all duration-300
|
|
26
|
+
perspective
|
|
27
|
+
${className}`, children: [showRing && (_jsxs(_Fragment, { children: [_jsx("svg", { className: 'absolute inset-0 w-full h-full', viewBox: `0 0 ${size} ${size}`, children: _jsx("circle", { cx: size / 2, cy: size / 2, r: radius, fill: 'none', stroke: 'currentColor', strokeWidth: strokeWidth, className: 'opacity-30' }) }), _jsx("svg", { className: 'absolute inset-0 w-full h-full -rotate-90', viewBox: `0 0 ${size} ${size}`, children: _jsx("circle", { cx: size / 2, cy: size / 2, r: radius, fill: 'none', stroke: 'currentColor', strokeWidth: strokeWidth, strokeDasharray: circumference, strokeDashoffset: offset, strokeLinecap: 'round', className: 'transition-all duration-300' }) })] })), _jsx("div", { className: `
|
|
28
|
+
relative z-10 text-white text-xs text-center whitespace-pre select-none
|
|
29
|
+
${className ? 'animate-counter-rotate' : ''}
|
|
30
|
+
`, children: children })] }) }));
|
|
31
|
+
};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
export interface SectorButtonSector<T> {
|
|
2
|
+
id: T;
|
|
3
|
+
label?: string;
|
|
4
|
+
color?: string;
|
|
5
|
+
hoverColor?: string;
|
|
6
|
+
}
|
|
7
|
+
export interface SectorButtonProps<T> {
|
|
8
|
+
sectors: SectorButtonSector<T>[];
|
|
9
|
+
size?: number;
|
|
10
|
+
className?: string;
|
|
11
|
+
onClick?: (id: T) => void;
|
|
12
|
+
borderRadius?: number;
|
|
13
|
+
showPlusSign?: boolean;
|
|
14
|
+
plusSignColor?: string;
|
|
15
|
+
plusSignSize?: number;
|
|
16
|
+
shape?: 'circle' | 'rounded-rect';
|
|
17
|
+
rectWidth?: number;
|
|
18
|
+
rectHeight?: number;
|
|
19
|
+
}
|
|
20
|
+
export declare const SectorButton: <T = string>(props: SectorButtonProps<T>) => import("react/jsx-runtime").JSX.Element;
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useState } from 'react';
|
|
4
|
+
export const SectorButton = (props) => {
|
|
5
|
+
const { shape = 'rounded-rect', size = 40, rectWidth = size, rectHeight = size, sectors, className, borderRadius = 12, showPlusSign = true, plusSignColor = '#bbb', plusSignSize = 0.3, onClick, } = props;
|
|
6
|
+
const [hoveredSector, setHoveredSector] = useState(null);
|
|
7
|
+
const anglePerSector = 360 / sectors.length;
|
|
8
|
+
const radius = size / 2;
|
|
9
|
+
// 添加额外边距确保虚线显示完整
|
|
10
|
+
const padding = 2;
|
|
11
|
+
const svgWidth = shape === 'circle' ? size + padding * 2 : rectWidth + padding * 2;
|
|
12
|
+
const svgHeight = shape === 'circle' ? size + padding * 2 : rectHeight + padding * 2;
|
|
13
|
+
const handleSectorClick = (id) => {
|
|
14
|
+
onClick?.(id);
|
|
15
|
+
};
|
|
16
|
+
// 先渲染非悬停的扇形,然后渲染悬停的扇形,确保悬停的扇形在最顶层
|
|
17
|
+
const nonHoveredSectors = sectors.filter(sector => sector.id !== hoveredSector);
|
|
18
|
+
const hoveredSector1 = sectors.find(sector => sector.id === hoveredSector);
|
|
19
|
+
const orderedSectors = [...nonHoveredSectors];
|
|
20
|
+
if (hoveredSector1) {
|
|
21
|
+
orderedSectors.push(hoveredSector1);
|
|
22
|
+
}
|
|
23
|
+
// 生成圆角矩形或扇形的路径
|
|
24
|
+
const generatePath = (sector, originalIndex) => {
|
|
25
|
+
const centerX = svgWidth / 2;
|
|
26
|
+
const centerY = svgHeight / 2;
|
|
27
|
+
if (shape === 'circle') {
|
|
28
|
+
// 原来的扇形路径生成逻辑
|
|
29
|
+
const startAngle = originalIndex * anglePerSector;
|
|
30
|
+
const endAngle = (originalIndex + 1) * anglePerSector;
|
|
31
|
+
const startRad = (startAngle - 90) * Math.PI / 180;
|
|
32
|
+
const endRad = (endAngle - 90) * Math.PI / 180;
|
|
33
|
+
return [
|
|
34
|
+
`M ${centerX} ${centerY}`,
|
|
35
|
+
`L ${centerX + radius * Math.cos(startRad)} ${centerY + radius * Math.sin(startRad)}`,
|
|
36
|
+
`A ${radius} ${radius} 0 ${anglePerSector > 180 ? 1 : 0} 1 ${centerX + radius * Math.cos(endRad)} ${centerY + radius * Math.sin(endRad)}`,
|
|
37
|
+
`Z`,
|
|
38
|
+
].join(' ');
|
|
39
|
+
}
|
|
40
|
+
else {
|
|
41
|
+
// 圆角矩形的分块逻辑
|
|
42
|
+
const rectX = padding;
|
|
43
|
+
const rectY = padding;
|
|
44
|
+
const rectW = rectWidth;
|
|
45
|
+
const rectH = rectHeight;
|
|
46
|
+
// 当只有2个扇形时,使用左右布局
|
|
47
|
+
if (sectors.length === 2) {
|
|
48
|
+
const secWidth = rectW / 2;
|
|
49
|
+
const secHeight = rectH;
|
|
50
|
+
const x = rectX + originalIndex * secWidth;
|
|
51
|
+
const y = rectY;
|
|
52
|
+
// 使用圆角矩形绘制单个部分
|
|
53
|
+
const br = borderRadius > 0 ? Math.min(borderRadius, secWidth / 4, secHeight / 4) : 0;
|
|
54
|
+
// 确定是左侧还是右侧
|
|
55
|
+
const isLeft = originalIndex === 0;
|
|
56
|
+
const isRight = originalIndex === 1;
|
|
57
|
+
// 构建路径 - 根据位置决定哪些角有圆角
|
|
58
|
+
return [
|
|
59
|
+
`M ${x + (isLeft ? br : 0)} ${y}`,
|
|
60
|
+
// 上边
|
|
61
|
+
`H ${x + secWidth - (isRight ? br : 0)}`,
|
|
62
|
+
isRight ? `A ${br} ${br} 0 0 1 ${x + secWidth} ${y + br}` : '',
|
|
63
|
+
// 右边
|
|
64
|
+
`V ${y + secHeight - (isRight ? br : 0)}`,
|
|
65
|
+
isRight ? `A ${br} ${br} 0 0 1 ${x + secWidth - br} ${y + secHeight}` : '',
|
|
66
|
+
// 下边
|
|
67
|
+
`H ${x + (isLeft ? br : 0)}`,
|
|
68
|
+
isLeft ? `A ${br} ${br} 0 0 1 ${x} ${y + secHeight - br}` : '',
|
|
69
|
+
// 左边
|
|
70
|
+
`V ${y + (isLeft ? br : 0)}`,
|
|
71
|
+
isLeft ? `A ${br} ${br} 0 0 1 ${x + br} ${y}` : '',
|
|
72
|
+
'Z',
|
|
73
|
+
].filter(Boolean).join(' ');
|
|
74
|
+
}
|
|
75
|
+
else {
|
|
76
|
+
// 原有的上下布局逻辑
|
|
77
|
+
const secWidth = rectW / (sectors.length % 2 === 0 ? sectors.length / 2 : Math.ceil(sectors.length / 2));
|
|
78
|
+
const secHeight = rectH / 2;
|
|
79
|
+
// 确定当前扇区在矩形中的位置
|
|
80
|
+
const isTopRow = originalIndex < Math.ceil(sectors.length / 2);
|
|
81
|
+
const rowIndex = isTopRow ? originalIndex : originalIndex - Math.ceil(sectors.length / 2);
|
|
82
|
+
const x = rectX + rowIndex * secWidth;
|
|
83
|
+
const y = isTopRow ? rectY : rectY + secHeight;
|
|
84
|
+
// 使用圆角矩形绘制单个部分
|
|
85
|
+
const br = borderRadius > 0 ? Math.min(borderRadius, secWidth / 4, secHeight / 4) : 0;
|
|
86
|
+
// 确定哪些边需要圆角
|
|
87
|
+
const isLeftEdge = (isTopRow && rowIndex === 0) || (!isTopRow && rowIndex === 0);
|
|
88
|
+
const isRightEdge = (isTopRow && rowIndex === Math.ceil(sectors.length / 2) - 1) ||
|
|
89
|
+
(!isTopRow && rowIndex === (sectors.length - Math.ceil(sectors.length / 2)) - 1);
|
|
90
|
+
const isTopEdge = isTopRow;
|
|
91
|
+
const isBottomEdge = !isTopRow;
|
|
92
|
+
// 构建路径 - 根据位置决定哪些角有圆角
|
|
93
|
+
return [
|
|
94
|
+
`M ${x + (isLeftEdge && isTopEdge ? br : 0)} ${y}`,
|
|
95
|
+
// 上边
|
|
96
|
+
`H ${x + secWidth - (isRightEdge && isTopEdge ? br : 0)}`,
|
|
97
|
+
isRightEdge && isTopEdge ? `A ${br} ${br} 0 0 1 ${x + secWidth} ${y + br}` : '',
|
|
98
|
+
// 右边
|
|
99
|
+
`V ${y + secHeight - (isRightEdge && isBottomEdge ? br : 0)}`,
|
|
100
|
+
isRightEdge && isBottomEdge ? `A ${br} ${br} 0 0 1 ${x + secWidth - br} ${y + secHeight}` : '',
|
|
101
|
+
// 下边
|
|
102
|
+
`H ${x + (isLeftEdge && isBottomEdge ? br : 0)}`,
|
|
103
|
+
isLeftEdge && isBottomEdge ? `A ${br} ${br} 0 0 1 ${x} ${y + secHeight - br}` : '',
|
|
104
|
+
// 左边
|
|
105
|
+
`V ${y + (isLeftEdge && isTopEdge ? br : 0)}`,
|
|
106
|
+
isLeftEdge && isTopEdge ? `A ${br} ${br} 0 0 1 ${x + br} ${y}` : '',
|
|
107
|
+
'Z',
|
|
108
|
+
].filter(Boolean).join(' ');
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
};
|
|
112
|
+
return (_jsx("div", { className: `relative ${className}`, style: {
|
|
113
|
+
width: shape === 'circle' ? size : rectWidth,
|
|
114
|
+
height: shape === 'circle' ? size : rectHeight,
|
|
115
|
+
borderRadius,
|
|
116
|
+
backgroundColor: 'transparent',
|
|
117
|
+
}, children: _jsx("svg", { width: svgWidth, height: svgHeight, viewBox: `0 0 ${svgWidth} ${svgHeight}`, style: {
|
|
118
|
+
position: 'absolute',
|
|
119
|
+
top: -padding,
|
|
120
|
+
left: -padding,
|
|
121
|
+
}, children: _jsxs("g", { children: [orderedSectors.map(sector => {
|
|
122
|
+
const originalIndex = sectors.findIndex(s => s.id === sector.id);
|
|
123
|
+
const pathData = generatePath(sector, originalIndex);
|
|
124
|
+
const isHovered = hoveredSector === sector.id;
|
|
125
|
+
const fillColor = (isHovered ? sector.hoverColor : sector.color) || 'white';
|
|
126
|
+
const strokeColor = isHovered ? '#90cdf4' : '#e2e8f0';
|
|
127
|
+
const strokeWidth = isHovered ? 1.5 : 1;
|
|
128
|
+
return (_jsx("g", { children: _jsx("path", { d: pathData, fill: fillColor, stroke: strokeColor, strokeWidth: strokeWidth, strokeDasharray: '4,1', className: 'transition-colors duration-200 cursor-pointer', onMouseEnter: () => setHoveredSector(sector.id), onMouseLeave: () => setHoveredSector(null), onClick: () => handleSectorClick(sector.id) }) }, sector.id));
|
|
129
|
+
}), showPlusSign && (_jsxs("g", { children: [_jsx("line", { x1: svgWidth / 2 - (plusSignSize * (shape === 'circle' ? size : Math.min(rectWidth, rectHeight)) / 2), y1: svgHeight / 2, x2: svgWidth / 2 + (plusSignSize * (shape === 'circle' ? size : Math.min(rectWidth, rectHeight)) / 2), y2: svgHeight / 2, stroke: plusSignColor, strokeWidth: 2, strokeLinecap: 'round' }), _jsx("line", { x1: svgWidth / 2, y1: svgHeight / 2 - (plusSignSize * (shape === 'circle' ? size : Math.min(rectWidth, rectHeight)) / 2), x2: svgWidth / 2, y2: svgHeight / 2 + (plusSignSize * (shape === 'circle' ? size : Math.min(rectWidth, rectHeight)) / 2), stroke: plusSignColor, strokeWidth: 2, strokeLinecap: 'round' })] }))] }) }) }));
|
|
130
|
+
};
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { CSSProperties } from 'react';
|
|
2
|
+
import 'prismjs/components/prism-jsx';
|
|
3
|
+
import 'prismjs/components/prism-tsx';
|
|
4
|
+
import 'prismjs/components/prism-json';
|
|
5
|
+
import 'prismjs/components/prism-javascript';
|
|
6
|
+
import 'prismjs/components/prism-typescript';
|
|
7
|
+
import 'prismjs/components/prism-css';
|
|
8
|
+
import 'prismjs/components/prism-less';
|
|
9
|
+
import 'prismjs/components/prism-sass';
|
|
10
|
+
import 'prismjs/components/prism-scss';
|
|
11
|
+
import 'prismjs/components/prism-bash';
|
|
12
|
+
import 'prismjs/components/prism-http';
|
|
13
|
+
import 'prismjs/components/prism-editorconfig';
|
|
14
|
+
import 'prismjs/components/prism-docker';
|
|
15
|
+
import 'prismjs/components/prism-git';
|
|
16
|
+
import 'prismjs/components/prism-ignore';
|
|
17
|
+
import 'prismjs/components/prism-yaml';
|
|
18
|
+
import 'prismjs/themes/prism.css';
|
|
19
|
+
interface CodeViewProps {
|
|
20
|
+
language?: 'html' | 'jsx' | 'tsx' | 'vue' | 'json' | 'javascript' | 'typescript' | 'css' | 'less' | 'sass' | 'scss' | 'bash' | 'http' | 'editorconfig' | 'dockerfile' | 'git' | 'ignore' | 'yaml';
|
|
21
|
+
code?: string;
|
|
22
|
+
children?: any;
|
|
23
|
+
style?: CSSProperties;
|
|
24
|
+
}
|
|
25
|
+
export declare const CodeView: (props: CodeViewProps) => import("react/jsx-runtime").JSX.Element;
|
|
26
|
+
export {};
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { useEffect, useMemo, useRef } from 'react';
|
|
4
|
+
import Prism from 'prismjs';
|
|
5
|
+
import { format } from 'prettier/standalone';
|
|
6
|
+
import parserBabel from 'prettier/parser-babel';
|
|
7
|
+
import parserTs from 'prettier/parser-typescript';
|
|
8
|
+
import { js_beautify, html_beautify, css_beautify } from 'js-beautify';
|
|
9
|
+
import 'prismjs/components/prism-jsx';
|
|
10
|
+
import 'prismjs/components/prism-tsx';
|
|
11
|
+
import 'prismjs/components/prism-json';
|
|
12
|
+
import 'prismjs/components/prism-javascript';
|
|
13
|
+
import 'prismjs/components/prism-typescript';
|
|
14
|
+
import 'prismjs/components/prism-css';
|
|
15
|
+
import 'prismjs/components/prism-less';
|
|
16
|
+
import 'prismjs/components/prism-sass';
|
|
17
|
+
import 'prismjs/components/prism-scss';
|
|
18
|
+
import 'prismjs/components/prism-bash';
|
|
19
|
+
import 'prismjs/components/prism-http';
|
|
20
|
+
import 'prismjs/components/prism-editorconfig';
|
|
21
|
+
import 'prismjs/components/prism-docker';
|
|
22
|
+
import 'prismjs/components/prism-git';
|
|
23
|
+
import 'prismjs/components/prism-ignore';
|
|
24
|
+
import 'prismjs/components/prism-yaml';
|
|
25
|
+
import 'prismjs/themes/prism.css';
|
|
26
|
+
export const CodeView = (props) => {
|
|
27
|
+
const { language = 'javascript', style, children, code = children } = props;
|
|
28
|
+
const preRef = useRef(null);
|
|
29
|
+
useEffect(() => {
|
|
30
|
+
if (!preRef.current) {
|
|
31
|
+
return;
|
|
32
|
+
}
|
|
33
|
+
Prism.highlightElement(preRef.current);
|
|
34
|
+
}, []);
|
|
35
|
+
const beautifydCode = useMemo(() => {
|
|
36
|
+
if (language === 'html') {
|
|
37
|
+
return html_beautify(code, { indent_size: 2 });
|
|
38
|
+
}
|
|
39
|
+
if (language === 'css') {
|
|
40
|
+
return css_beautify(code, { indent_size: 2 });
|
|
41
|
+
}
|
|
42
|
+
if (language === 'javascript') {
|
|
43
|
+
return js_beautify(code, { indent_size: 2 });
|
|
44
|
+
}
|
|
45
|
+
try {
|
|
46
|
+
return format(code, {
|
|
47
|
+
semi: false,
|
|
48
|
+
parser: 'babel',
|
|
49
|
+
singleQuote: true,
|
|
50
|
+
tabWidth: 2,
|
|
51
|
+
jsxSingleQuote: true,
|
|
52
|
+
plugins: [parserBabel, parserTs],
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
catch (e) {
|
|
56
|
+
return code;
|
|
57
|
+
}
|
|
58
|
+
}, [code]);
|
|
59
|
+
return (_jsx("div", { style: { overflow: 'scroll', ...style }, children: _jsx("pre", { style: { margin: 0, backgroundColor: 'transparent' }, children: _jsx("code", { ref: preRef, className: `language-${language}`, children: beautifydCode }) }) }));
|
|
60
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { Tag } from 'antd';
|
|
3
|
+
export const EnumTag = (props) => {
|
|
4
|
+
const { value, map } = props;
|
|
5
|
+
const enumItem = map.get(value);
|
|
6
|
+
if (!enumItem) {
|
|
7
|
+
return _jsx(Tag, { children: value });
|
|
8
|
+
}
|
|
9
|
+
return (_jsx(Tag, { color: enumItem.extra?.color, children: enumItem.label }));
|
|
10
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { useMemo } from 'react';
|
|
4
|
+
import Handlebars from 'handlebars';
|
|
5
|
+
export const HtmlDataRenderer = (props) => {
|
|
6
|
+
const { template, data } = props;
|
|
7
|
+
const html = useMemo(() => {
|
|
8
|
+
const html = Handlebars.compile(template || '')(data);
|
|
9
|
+
return html.replaceAll('\n', '').replaceAll('\t', '');
|
|
10
|
+
}, [template, data]);
|
|
11
|
+
if (!html) {
|
|
12
|
+
return null;
|
|
13
|
+
}
|
|
14
|
+
return (_jsx("div", { dangerouslySetInnerHTML: { __html: html } }));
|
|
15
|
+
};
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { CSSProperties } from 'react';
|
|
2
|
+
export interface IframeProProps {
|
|
3
|
+
url: string;
|
|
4
|
+
errMessage?: string;
|
|
5
|
+
style?: CSSProperties;
|
|
6
|
+
isShowLoading?: boolean;
|
|
7
|
+
}
|
|
8
|
+
export declare const IframePro: (props: IframeProProps) => import("react/jsx-runtime").JSX.Element;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { useEffect } from 'react';
|
|
4
|
+
import { Spin } from 'antd';
|
|
5
|
+
import { useBoolean } from '@wzyjs/hooks/web';
|
|
6
|
+
export const IframePro = (props) => {
|
|
7
|
+
const { url, style, errMessage = '', isShowLoading = false } = props;
|
|
8
|
+
const [loading, { setTrue, setFalse }] = useBoolean(true);
|
|
9
|
+
useEffect(() => {
|
|
10
|
+
setTrue();
|
|
11
|
+
}, [url]);
|
|
12
|
+
if (!url) {
|
|
13
|
+
return (_jsx("span", { style: {
|
|
14
|
+
...style,
|
|
15
|
+
color: '#ccc',
|
|
16
|
+
fontSize: 14,
|
|
17
|
+
display: 'flex',
|
|
18
|
+
flexDirection: 'column',
|
|
19
|
+
justifyContent: 'center',
|
|
20
|
+
alignItems: 'center',
|
|
21
|
+
}, children: errMessage || '没有url' }));
|
|
22
|
+
}
|
|
23
|
+
return (_jsx(Spin, { spinning: loading && isShowLoading, children: _jsx("iframe", { src: url, width: '100%', height: '100%', style: style, onLoad: setFalse }) }));
|
|
24
|
+
};
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export type JsonSchemaComponentName = 'Divider' | 'Flex' | 'Space' | 'Typography' | 'Typography.Title' | 'Typography.Text' | 'Typography.Paragraph' | 'Typography.Link' | 'Steps' | 'Tabs' | 'Collapse' | 'Collapse.Panel' | 'Description' | 'Image' | 'List' | 'Popover' | 'Tooltip' | 'Card' | 'QRCode' | 'Segmented' | 'Table' | 'Tag' | 'Timeline' | 'Tree' | 'Alert' | 'Progress';
|
|
2
|
+
export interface Content {
|
|
3
|
+
component: JsonSchemaComponentName;
|
|
4
|
+
props?: Record<string, any>;
|
|
5
|
+
children?: Content[] | string;
|
|
6
|
+
}
|
|
7
|
+
interface JsonSchemaRendererProps {
|
|
8
|
+
content: Content[];
|
|
9
|
+
}
|
|
10
|
+
export declare const JsonSchemaRenderer: (props: JsonSchemaRendererProps) => import("react/jsx-runtime").JSX.Element;
|
|
11
|
+
export {};
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { jsx as _jsx, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import React from 'react';
|
|
3
|
+
import { Divider, Flex, Space, Typography, Steps, Tabs, Collapse, Descriptions, Image, List, Popover, Tooltip, Card, QRCode, Segmented, Table, Tag, Timeline, Tree, Alert, Progress, } from 'antd';
|
|
4
|
+
const ComponentMap = {
|
|
5
|
+
// 布局结构类
|
|
6
|
+
Divider,
|
|
7
|
+
Flex,
|
|
8
|
+
Space,
|
|
9
|
+
// 信息展示类
|
|
10
|
+
Typography,
|
|
11
|
+
'Typography.Title': Typography.Title,
|
|
12
|
+
'Typography.Text': Typography.Text,
|
|
13
|
+
'Typography.Paragraph': Typography.Paragraph,
|
|
14
|
+
'Typography.Link': Typography.Link,
|
|
15
|
+
Steps,
|
|
16
|
+
Tabs,
|
|
17
|
+
Collapse,
|
|
18
|
+
'Collapse.Panel': Collapse.Panel,
|
|
19
|
+
Description: Descriptions,
|
|
20
|
+
Image,
|
|
21
|
+
List,
|
|
22
|
+
Popover,
|
|
23
|
+
Tooltip,
|
|
24
|
+
Card,
|
|
25
|
+
QRCode,
|
|
26
|
+
Segmented,
|
|
27
|
+
Table,
|
|
28
|
+
Tag,
|
|
29
|
+
Timeline,
|
|
30
|
+
Tree,
|
|
31
|
+
Alert,
|
|
32
|
+
Progress,
|
|
33
|
+
};
|
|
34
|
+
export const JsonSchemaRenderer = (props) => {
|
|
35
|
+
const { content } = props;
|
|
36
|
+
// 递归渲染组件的函数
|
|
37
|
+
const renderContent = (item) => {
|
|
38
|
+
// 如果是字符串,直接返回
|
|
39
|
+
if (typeof item === 'string') {
|
|
40
|
+
return item;
|
|
41
|
+
}
|
|
42
|
+
const { component, props = {}, children } = item;
|
|
43
|
+
// 获取对应的组件
|
|
44
|
+
const Component = ComponentMap[component];
|
|
45
|
+
if (!Component) {
|
|
46
|
+
return _jsx(Alert, { type: 'error', title: `未找到组件: ${component}` });
|
|
47
|
+
}
|
|
48
|
+
// 处理子节点
|
|
49
|
+
let childrenContent;
|
|
50
|
+
if (children) {
|
|
51
|
+
if (Array.isArray(children)) {
|
|
52
|
+
childrenContent = children.map((child, index) => (_jsx(React.Fragment, { children: renderContent(child) }, index)));
|
|
53
|
+
}
|
|
54
|
+
else {
|
|
55
|
+
childrenContent = renderContent(children);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
// 渲染组件,传递 props 和 children
|
|
59
|
+
return _jsx(Component, { ...props, children: childrenContent });
|
|
60
|
+
};
|
|
61
|
+
return (_jsx(_Fragment, { children: content.map((item, index) => (_jsx(React.Fragment, { children: renderContent(item) }, index))) }));
|
|
62
|
+
};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import ReactJson from 'react-json-view';
|
|
4
|
+
export const JsonView = (props) => {
|
|
5
|
+
const { style } = props;
|
|
6
|
+
return (_jsx(ReactJson, { enableClipboard: false, collapsed: true, displayObjectSize: false, displayDataTypes: false, ...props, style: { overflow: 'auto', ...style } }));
|
|
7
|
+
};
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useMemo } from 'react';
|
|
4
|
+
import ReactMarkdown from 'react-markdown';
|
|
5
|
+
import { Prism as SyntaxHighlighter } from 'react-syntax-highlighter';
|
|
6
|
+
import { oneLight } from 'react-syntax-highlighter/dist/esm/styles/prism';
|
|
7
|
+
import remarkGfm from 'remark-gfm';
|
|
8
|
+
import rehypeSlug from 'rehype-slug';
|
|
9
|
+
import rehypeAutolinkHeadings from 'rehype-autolink-headings';
|
|
10
|
+
import 'github-markdown-css/github-markdown-light.css';
|
|
11
|
+
import { style } from './style';
|
|
12
|
+
export const MarkdownView = (props) => {
|
|
13
|
+
const { content = '', showToc = true } = props;
|
|
14
|
+
// 提取标题生成目录
|
|
15
|
+
const tocItems = useMemo(() => {
|
|
16
|
+
if (!showToc) {
|
|
17
|
+
return [];
|
|
18
|
+
}
|
|
19
|
+
const lines = content.split('\n');
|
|
20
|
+
const items = [];
|
|
21
|
+
lines.forEach((line) => {
|
|
22
|
+
const match = line.match(/^(#{2,4})\s+(.+)$/);
|
|
23
|
+
if (match && match[1] && match[2]) {
|
|
24
|
+
const level = match[1].length;
|
|
25
|
+
const text = match[2].trim();
|
|
26
|
+
const id = text
|
|
27
|
+
.toLowerCase()
|
|
28
|
+
.replace(/[^\w\u4e00-\u9fa5\s-]/g, '') // 保留中文、英文、数字、空格和连字符
|
|
29
|
+
.replace(/\s+/g, '-'); // 空格替换为连字符
|
|
30
|
+
items.push({ id, text, level });
|
|
31
|
+
}
|
|
32
|
+
});
|
|
33
|
+
return items;
|
|
34
|
+
}, [content, showToc]);
|
|
35
|
+
// 渲染目录
|
|
36
|
+
const renderToc = () => {
|
|
37
|
+
if (!showToc || tocItems.length === 0) {
|
|
38
|
+
return null;
|
|
39
|
+
}
|
|
40
|
+
return (_jsx("div", { className: 'markdown-toc-container', style: {
|
|
41
|
+
padding: '10px 20px 10px 0',
|
|
42
|
+
backgroundColor: '#f8f9fa',
|
|
43
|
+
borderLeft: '4px solid #1890ff',
|
|
44
|
+
borderRadius: '4px',
|
|
45
|
+
overflowY: 'auto',
|
|
46
|
+
height: '100%'
|
|
47
|
+
}, children: _jsx("ul", { style: { margin: 0, padding: 0 }, children: tocItems.map((item, index) => (_jsx("li", { style: {
|
|
48
|
+
marginBottom: '4px',
|
|
49
|
+
marginLeft: `${(item.level - 1) * 16}px`,
|
|
50
|
+
listStyle: 'none',
|
|
51
|
+
position: 'relative',
|
|
52
|
+
}, children: _jsx("a", { href: `#${item.id}`, style: {
|
|
53
|
+
textDecoration: 'none',
|
|
54
|
+
color: '#1890ff',
|
|
55
|
+
fontSize: item.level <= 2 ? '14px' : '13px',
|
|
56
|
+
fontWeight: item.level === 1 ? 600 : 400,
|
|
57
|
+
}, onClick: (e) => {
|
|
58
|
+
e.preventDefault();
|
|
59
|
+
const element = document.getElementById(item.id);
|
|
60
|
+
if (element) {
|
|
61
|
+
element.scrollIntoView({ behavior: 'smooth' });
|
|
62
|
+
}
|
|
63
|
+
}, children: item.text }) }, index))) }) }));
|
|
64
|
+
};
|
|
65
|
+
return (_jsxs("div", { style: { height: '100%' }, children: [_jsx("style", { children: style }), _jsxs("div", { className: 'markdown-body markdown-toc', style: { height: '100%', display: 'flex' }, children: [_jsx("div", { style: { marginRight: 14 }, children: renderToc() }), _jsx("div", { style: { overflow: 'auto', flex: 1 }, children: _jsx(ReactMarkdown, { remarkPlugins: [remarkGfm], rehypePlugins: [
|
|
66
|
+
rehypeSlug,
|
|
67
|
+
[rehypeAutolinkHeadings, {
|
|
68
|
+
behavior: 'wrap',
|
|
69
|
+
properties: {
|
|
70
|
+
className: ['anchor'],
|
|
71
|
+
},
|
|
72
|
+
}],
|
|
73
|
+
], components: {
|
|
74
|
+
code(props) {
|
|
75
|
+
const { children, className } = props;
|
|
76
|
+
const match = /language-(\w+)/.exec(className || '');
|
|
77
|
+
return match ? (_jsx(SyntaxHighlighter, { PreTag: 'div', children: String(children).replace(/\n$/, ''), language: match[1], style: oneLight })) : (_jsx("code", { className: className, children: children }));
|
|
78
|
+
},
|
|
79
|
+
}, children: content }) })] })] }));
|
|
80
|
+
};
|