style: command viewer scroller

This commit is contained in:
jialin
2026-01-07 15:55:26 +08:00
parent 8f9fae9210
commit bbf09c2ea9
21 changed files with 136 additions and 153 deletions
@@ -10,6 +10,7 @@ interface CodeViewerProps {
copyable?: boolean; copyable?: boolean;
height?: string | number; height?: string | number;
style?: React.CSSProperties; style?: React.CSSProperties;
xScrollable?: boolean;
} }
const DarkViewer: React.FC<CodeViewerProps> = (props) => { const DarkViewer: React.FC<CodeViewerProps> = (props) => {
const { const {
@@ -19,7 +20,8 @@ const DarkViewer: React.FC<CodeViewerProps> = (props) => {
autodetect, autodetect,
ignoreIllegals, ignoreIllegals,
copyable, copyable,
height = 'auto' height = 'auto',
xScrollable = false
} = props || {}; } = props || {};
return ( return (
@@ -33,6 +35,7 @@ const DarkViewer: React.FC<CodeViewerProps> = (props) => {
autodetect={autodetect} autodetect={autodetect}
ignoreIllegals={ignoreIllegals} ignoreIllegals={ignoreIllegals}
copyable={copyable} copyable={copyable}
xScrollable={xScrollable}
></CodeViewer> ></CodeViewer>
); );
}; };
@@ -10,6 +10,7 @@ interface CodeViewerProps {
copyable?: boolean; copyable?: boolean;
height?: string | number; height?: string | number;
style?: React.CSSProperties; style?: React.CSSProperties;
xScrollable?: boolean;
} }
const LightViewer: React.FC<CodeViewerProps> = (props) => { const LightViewer: React.FC<CodeViewerProps> = (props) => {
const { const {
@@ -20,7 +21,8 @@ const LightViewer: React.FC<CodeViewerProps> = (props) => {
ignoreIllegals, ignoreIllegals,
copyable, copyable,
style, style,
height = 'auto' height = 'auto',
xScrollable = false
} = props || {}; } = props || {};
return ( return (
@@ -34,6 +36,7 @@ const LightViewer: React.FC<CodeViewerProps> = (props) => {
autodetect={autodetect} autodetect={autodetect}
ignoreIllegals={ignoreIllegals} ignoreIllegals={ignoreIllegals}
copyable={copyable} copyable={copyable}
xScrollable={xScrollable}
></CodeViewer> ></CodeViewer>
); );
}; };
+17 -3
View File
@@ -15,6 +15,7 @@ interface CodeViewerProps {
height?: string | number; height?: string | number;
theme?: 'light' | 'dark'; theme?: 'light' | 'dark';
style?: React.CSSProperties; style?: React.CSSProperties;
xScrollable?: boolean;
} }
interface CodeHeaderProps { interface CodeHeaderProps {
@@ -43,6 +44,14 @@ const CodeHeaderWrapper = styled.div`
const Wrapper = styled.div` const Wrapper = styled.div`
border-radius: var(--border-radius-mini); border-radius: var(--border-radius-mini);
&:hover {
.custome-scrollbar {
&::-webkit-scrollbar-thumb {
background-color: var(--color-scrollbar-thumb);
border-radius: 4px;
}
}
}
`; `;
const CodeHeader: React.FC<CodeHeaderProps> = ({ const CodeHeader: React.FC<CodeHeaderProps> = ({
@@ -80,7 +89,8 @@ const CodeViewer: React.FC<CodeViewerProps> = (props) => {
ignoreIllegals = true, ignoreIllegals = true,
copyable = true, copyable = true,
height = 'auto', height = 'auto',
style style,
xScrollable = false
} = props || {}; } = props || {};
const highlightedCode = useMemo(() => { const highlightedCode = useMemo(() => {
@@ -131,7 +141,8 @@ const CodeViewer: React.FC<CodeViewerProps> = (props) => {
'code-pre custome-scrollbar custom-scrollbar-horizontal ', 'code-pre custome-scrollbar custom-scrollbar-horizontal ',
{ {
dark: props.theme === 'dark', dark: props.theme === 'dark',
light: props.theme === 'light' light: props.theme === 'light',
'x-scrollable': xScrollable
} }
)} )}
style={{ style={{
@@ -141,7 +152,10 @@ const CodeViewer: React.FC<CodeViewerProps> = (props) => {
}} }}
> >
<code <code
style={{ minHeight: height }} style={{
minHeight: height,
...(xScrollable ? { width: 'max-content' } : {})
}}
className={classNames(highlightedCode.className, { className={classNames(highlightedCode.className, {
dark: props.theme === 'dark', dark: props.theme === 'dark',
light: props.theme === 'light' light: props.theme === 'light'
+5 -1
View File
@@ -10,6 +10,7 @@ const HighlightCode: React.FC<{
copyable?: boolean; copyable?: boolean;
theme?: 'light' | 'dark'; theme?: 'light' | 'dark';
fixedTheme?: 'light' | 'dark'; fixedTheme?: 'light' | 'dark';
xScrollable?: boolean;
height?: string | number; height?: string | number;
style?: React.CSSProperties; style?: React.CSSProperties;
copyValue?: string; copyValue?: string;
@@ -21,7 +22,8 @@ const HighlightCode: React.FC<{
lang = 'bash', lang = 'bash',
copyable = true, copyable = true,
theme, theme,
height = 'auto' height = 'auto',
xScrollable = false
} = props; } = props;
const { userSettings } = useUserSettings(); const { userSettings } = useUserSettings();
@@ -40,6 +42,7 @@ const HighlightCode: React.FC<{
copyValue={copyValue} copyValue={copyValue}
copyable={copyable} copyable={copyable}
height={height} height={height}
xScrollable={xScrollable}
style={style} style={style}
/> />
) : ( ) : (
@@ -50,6 +53,7 @@ const HighlightCode: React.FC<{
copyValue={copyValue} copyValue={copyValue}
copyable={copyable} copyable={copyable}
height={height} height={height}
xScrollable={xScrollable}
/> />
)} )}
</div> </div>
+1 -1
View File
@@ -2,7 +2,7 @@ import { createFromIconfontCN } from '@ant-design/icons';
// import './iconfont/iconfont.js'; // import './iconfont/iconfont.js';
const IconFont = createFromIconfontCN({ const IconFont = createFromIconfontCN({
scriptUrl: '//at.alicdn.com/t/c/font_4613488_jo5x7z2z718.js' scriptUrl: '//at.alicdn.com/t/c/font_4613488_rajpu0blzkp.js'
}); });
export default IconFont; export default IconFont;
+2 -1
View File
@@ -120,6 +120,7 @@ const TagsWrapper: React.FC<TagsWrapperProps> = (props) => {
> >
<Tag <Tag
className="more" className="more"
variant="outlined"
style={{ marginInline: hiddenIndices.end < 1 ? 0 : `${gap}px 0` }} style={{ marginInline: hiddenIndices.end < 1 ? 0 : `${gap}px 0` }}
ref={moreBtnRef} ref={moreBtnRef}
> >
@@ -132,4 +133,4 @@ const TagsWrapper: React.FC<TagsWrapperProps> = (props) => {
); );
}; };
export default React.memo(TagsWrapper); export default TagsWrapper;
+3 -5
View File
@@ -10,9 +10,7 @@ import {
DiscordOutlined, DiscordOutlined,
GithubOutlined, GithubOutlined,
HomeOutlined, HomeOutlined,
LogoutOutlined, ReadOutlined
ReadOutlined,
SettingOutlined
} from '@ant-design/icons'; } from '@ant-design/icons';
import { history, useIntl, useNavigate } from '@umijs/max'; import { history, useIntl, useNavigate } from '@umijs/max';
import { Avatar, Button, Divider, Modal } from 'antd'; import { Avatar, Button, Divider, Modal } from 'antd';
@@ -235,7 +233,7 @@ export const ExtraContent = (props: { isDarkTheme?: boolean }) => {
key: 'settings', key: 'settings',
label: ( label: (
<span className="flex flex-center"> <span className="flex flex-center">
<SettingOutlined /> <IconFont type="icon-settings-02" />
<span className="m-l-8" style={{ marginLeft: 8 }}> <span className="m-l-8" style={{ marginLeft: 8 }}>
{intl?.formatMessage?.({ id: 'common.button.settings' })} {intl?.formatMessage?.({ id: 'common.button.settings' })}
</span> </span>
@@ -270,7 +268,7 @@ export const ExtraContent = (props: { isDarkTheme?: boolean }) => {
{originNode} {originNode}
<Divider style={{ marginBlock: 4 }} /> <Divider style={{ marginBlock: 4 }} />
<CustomItem onClick={handleLogout} className="border-top"> <CustomItem onClick={handleLogout} className="border-top">
<LogoutOutlined rotate={180} /> <IconFont type="icon-logout" style={{ fontSize: 17 }} />
<span>{intl?.formatMessage?.({ id: 'common.button.logout' })}</span> <span>{intl?.formatMessage?.({ id: 'common.button.logout' })}</span>
</CustomItem> </CustomItem>
</DropdownWrapper> </DropdownWrapper>
+4 -3
View File
@@ -28,7 +28,7 @@ export default {
'clusters.workerpool.volumes.add': 'Add Volume', 'clusters.workerpool.volumes.add': 'Add Volume',
'clusters.create.provider.self': 'Self-Hosted', 'clusters.create.provider.self': 'Self-Hosted',
'clusters.create.provider.cloud': 'Cloud Provider', 'clusters.create.provider.cloud': 'Cloud Provider',
'clusters.create.selectProvider': 'Select Provider', 'clusters.create.steps.selectProvider': 'Select Provider',
'clusters.create.configBasic': 'Basic Configuration', 'clusters.create.configBasic': 'Basic Configuration',
'clusters.create.execCommand': 'Execute Command', 'clusters.create.execCommand': 'Execute Command',
'clusters.create.supportedGpu': 'Supported GPUs', 'clusters.create.supportedGpu': 'Supported GPUs',
@@ -117,8 +117,9 @@ export default {
'clusters.form.setDefault': 'Set as Default', 'clusters.form.setDefault': 'Set as Default',
'clusters.form.setDefault.tips': 'Default for deployment.', 'clusters.form.setDefault.tips': 'Default for deployment.',
'clusters.addworker.noClusters': 'No available clusters', 'clusters.addworker.noClusters': 'No available clusters',
'clusters.create.complete.tips': 'Cluster created successfully!', 'clusters.create.steps.complete.tips': 'Cluster created successfully!',
'clusters.create.complete': 'Completed', 'clusters.create.steps.complete': 'Complete',
'clusters.create.steps.configure': 'Configure',
'clusters.create.dockerTips1': 'Next, add worker to this cluster.', 'clusters.create.dockerTips1': 'Next, add worker to this cluster.',
'clusters.create.dockerTips2': 'clusters.create.dockerTips2':
'You can also skip this step and add them later from the cluster list.', 'You can also skip this step and add them later from the cluster list.',
+9 -7
View File
@@ -28,7 +28,7 @@ export default {
'clusters.workerpool.volumes.add': 'Add Volume', 'clusters.workerpool.volumes.add': 'Add Volume',
'clusters.create.provider.self': 'Self-Hosted', 'clusters.create.provider.self': 'Self-Hosted',
'clusters.create.provider.cloud': 'Cloud Provider', 'clusters.create.provider.cloud': 'Cloud Provider',
'clusters.create.selectProvider': 'Select Provider', 'clusters.create.steps.selectProvider': 'Select Provider',
'clusters.create.configBasic': 'Basic Configuration', 'clusters.create.configBasic': 'Basic Configuration',
'clusters.create.execCommand': 'Execute Command', 'clusters.create.execCommand': 'Execute Command',
'clusters.create.supportedGpu': 'Supported GPUs', 'clusters.create.supportedGpu': 'Supported GPUs',
@@ -117,8 +117,9 @@ export default {
'clusters.form.setDefault': 'Set as Default', 'clusters.form.setDefault': 'Set as Default',
'clusters.form.setDefault.tips': 'Default for deployment.', 'clusters.form.setDefault.tips': 'Default for deployment.',
'clusters.addworker.noClusters': 'No available clusters', 'clusters.addworker.noClusters': 'No available clusters',
'clusters.create.complete.tips': 'Cluster created successfully!', 'clusters.create.steps.complete.tips': 'Cluster created successfully!',
'clusters.create.complete': 'Completed', 'clusters.create.steps.complete': 'Complete',
'clusters.create.steps.configure': 'Configure',
'clusters.create.dockerTips1': 'Next, add worker to this cluster.', 'clusters.create.dockerTips1': 'Next, add worker to this cluster.',
'clusters.create.dockerTips2': 'clusters.create.dockerTips2':
'You can also skip this step and add them later from the cluster list.', 'You can also skip this step and add them later from the cluster list.',
@@ -157,7 +158,7 @@ export default {
// 27. 'clusters.workerpool.volumes.add': 'Add Volume' // 27. 'clusters.workerpool.volumes.add': 'Add Volume'
// 28. 'clusters.create.provider.self': 'Self-Hosted', // 28. 'clusters.create.provider.self': 'Self-Hosted',
// 29. 'clusters.create.provider.cloud': 'Cloud Provider', // 29. 'clusters.create.provider.cloud': 'Cloud Provider',
// 30. 'clusters.create.selectProvider': 'Select Provider', // 30. 'clusters.create.steps.selectProvider': 'Select Provider',
// 31. 'clusters.create.configBasic': 'Basic Configuration', // 31. 'clusters.create.configBasic': 'Basic Configuration',
// 32. 'clusters.create.execCommand': 'Execute Command', // 32. 'clusters.create.execCommand': 'Execute Command',
// 33. 'clusters.create.supportedGpu': 'Supported GPUs', // 33. 'clusters.create.supportedGpu': 'Supported GPUs',
@@ -219,10 +220,11 @@ export default {
// 85. 'clusters.addworker.enterWorkerAddress': 'Enter worker external address', // 85. 'clusters.addworker.enterWorkerAddress': 'Enter worker external address',
// 86. 'clusters.addworker.enterWorkerAddress.error': 'Please enter the worker external address.', // 86. 'clusters.addworker.enterWorkerAddress.error': 'Please enter the worker external address.',
// 87. 'clusters.addworker.noClusters': 'No available clusters', // 87. 'clusters.addworker.noClusters': 'No available clusters',
// 88. 'clusters.create.complete.tips': 'Cluster created successfully!', // 88. 'clusters.create.steps.complete.tips': 'Cluster created successfully!',
// 89. 'clusters.create.complete': 'Completed', // 89. 'clusters.create.steps.complete': 'Complete',
// 90. 'clusters.create.dockerTips1': 'Next, add worker to this cluster.', // 90. 'clusters.create.dockerTips1': 'Next, add worker to this cluster.',
// 91. 'clusters.create.dockerTips2': 'You can also skip this step and add them later from the cluster list.', // 91. 'clusters.create.dockerTips2': 'You can also skip this step and add them later from the cluster list.',
// 92. 'clusters.create.k8sTips1': 'Next, register existing Kubernetes cluster.', // 92. 'clusters.create.k8sTips1': 'Next, register existing Kubernetes cluster.',
// 93. 'clusters.create.k8sTips2': 'You can also skip this step and register it later from the cluster list.' // 93. 'clusters.create.k8sTips2': 'You can also skip this step and register it later from the cluster list.',
// 94. 'clusters.create.steps.configure': 'Configure',
// ========== End of To-Do List ========== // ========== End of To-Do List ==========
+8 -6
View File
@@ -28,7 +28,7 @@ export default {
'clusters.workerpool.volumes.add': 'Добавить том', 'clusters.workerpool.volumes.add': 'Добавить том',
'clusters.create.provider.self': 'Самостоятельное размещение', 'clusters.create.provider.self': 'Самостоятельное размещение',
'clusters.create.provider.cloud': 'Облачный провайдер', 'clusters.create.provider.cloud': 'Облачный провайдер',
'clusters.create.selectProvider': 'Выберите провайдера', 'clusters.create.steps.selectProvider': 'Выберите провайдера',
'clusters.create.configBasic': 'Базовая конфигурация', 'clusters.create.configBasic': 'Базовая конфигурация',
'clusters.create.execCommand': 'Выполнить команду', 'clusters.create.execCommand': 'Выполнить команду',
'clusters.create.supportedGpu': 'Поддерживаемые GPU', 'clusters.create.supportedGpu': 'Поддерживаемые GPU',
@@ -118,8 +118,9 @@ export default {
'clusters.form.setDefault.tips': 'clusters.form.setDefault.tips':
'Использовать по умолчанию для развертывания.', 'Использовать по умолчанию для развертывания.',
'clusters.addworker.noClusters': 'No available clusters', 'clusters.addworker.noClusters': 'No available clusters',
'clusters.create.complete.tips': 'Cluster created successfully!', 'clusters.create.steps.complete.tips': 'Cluster created successfully!',
'clusters.create.complete': 'Completed', 'clusters.create.steps.complete': 'Complete',
'clusters.create.steps.configure': 'Configure',
'clusters.create.dockerTips1': 'Next, add worker to this cluster.', 'clusters.create.dockerTips1': 'Next, add worker to this cluster.',
'clusters.create.dockerTips2': 'clusters.create.dockerTips2':
'You can also skip this step and add them later from the cluster list.', 'You can also skip this step and add them later from the cluster list.',
@@ -131,10 +132,11 @@ export default {
// ========== To-Do: Translate Keys (Remove After Translation) ========== // ========== To-Do: Translate Keys (Remove After Translation) ==========
// 1. 'clusters.addworker.hygonNotes': `If <span class="bold-text">/opt/hyhal</span> or <span class="bold-text">/opt/dtk</span> does not exist, create symbolic links pointing to the corresponding Hygon installation paths, for example: <span class="desc-fill">ln -s /path/to/hyhal /opt/hyhal</span> <span class="desc-fill">ln -s /path/to/dtk /opt/dtk</span>.`, // 1. 'clusters.addworker.hygonNotes': `If <span class="bold-text">/opt/hyhal</span> or <span class="bold-text">/opt/dtk</span> does not exist, create symbolic links pointing to the corresponding Hygon installation paths, for example: <span class="desc-fill">ln -s /path/to/hyhal /opt/hyhal</span> <span class="desc-fill">ln -s /path/to/dtk /opt/dtk</span>.`,
// 2. 'clusters.addworker.noClusters': 'No available clusters', // 2. 'clusters.addworker.noClusters': 'No available clusters',
// 3. 'clusters.create.complete.tips': 'Cluster created successfully!', // 3. 'clusters.create.steps.complete.tips': 'Cluster created successfully!',
// 4. 'clusters.create.complete': 'Completed', // 4. 'clusters.create.steps.complete': 'Complete',
// 5. 'clusters.create.dockerTips1': 'Next, add worker to this cluster.', // 5. 'clusters.create.dockerTips1': 'Next, add worker to this cluster.',
// 6. 'clusters.create.dockerTips2': 'You can also skip this step and add them later from the cluster list.', // 6. 'clusters.create.dockerTips2': 'You can also skip this step and add them later from the cluster list.',
// 7. 'clusters.create.k8sTips1': 'Next, register existing Kubernetes cluster.', // 7. 'clusters.create.k8sTips1': 'Next, register existing Kubernetes cluster.',
// 8. 'clusters.create.k8sTips2': 'You can also skip this step and register it later from the cluster list.' // 8. 'clusters.create.k8sTips2': 'You can also skip this step and register it later from the cluster list.',
// 9. 'clusters.create.steps.configure': 'Configure',
// ================================================================ // ================================================================
+4 -3
View File
@@ -28,7 +28,7 @@ export default {
'clusters.workerpool.volumes.add': '添加存储卷', 'clusters.workerpool.volumes.add': '添加存储卷',
'clusters.create.provider.self': '自建环境', 'clusters.create.provider.self': '自建环境',
'clusters.create.provider.cloud': '云环境', 'clusters.create.provider.cloud': '云环境',
'clusters.create.selectProvider': '选择环境', 'clusters.create.steps.selectProvider': '选择环境',
'clusters.create.configBasic': '基本配置', 'clusters.create.configBasic': '基本配置',
'clusters.create.execCommand': '执行命令', 'clusters.create.execCommand': '执行命令',
'clusters.create.supportedGpu': '支持的 GPU', 'clusters.create.supportedGpu': '支持的 GPU',
@@ -114,8 +114,9 @@ export default {
'clusters.form.setDefault': '设为默认', 'clusters.form.setDefault': '设为默认',
'clusters.form.setDefault.tips': '部署时的默认集群。', 'clusters.form.setDefault.tips': '部署时的默认集群。',
'clusters.addworker.noClusters': '无可用集群', 'clusters.addworker.noClusters': '无可用集群',
'clusters.create.complete.tips': '集群创建成功!', 'clusters.create.steps.complete.tips': '集群创建成功!',
'clusters.create.complete': '完成', 'clusters.create.steps.complete': '完成',
'clusters.create.steps.configure': '配置',
'clusters.create.dockerTips1': '接下来,为该集群添加节点。', 'clusters.create.dockerTips1': '接下来,为该集群添加节点。',
'clusters.create.dockerTips2': '你也可以跳过此步骤,稍后在集群列表中添加。', 'clusters.create.dockerTips2': '你也可以跳过此步骤,稍后在集群列表中添加。',
'clusters.create.k8sTips1': '接下来,注册已有的 Kubernetes 集群。', 'clusters.create.k8sTips1': '接下来,注册已有的 Kubernetes 集群。',
+10 -1
View File
@@ -13,8 +13,10 @@ const CollapseInner = styled(Collapse)`
border-radius: var(--border-radius-base) !important; border-radius: var(--border-radius-base) !important;
font-size: 14px !important; font-size: 14px !important;
font-weight: 600 !important; font-weight: 600 !important;
&:hover {
background-color: var(--ant-color-fill-tertiary) !important; background-color: var(--ant-color-fill-tertiary) !important;
} }
}
.ant-collapse-body { .ant-collapse-body {
padding-inline: 0 !important; padding-inline: 0 !important;
@@ -32,7 +34,8 @@ const CollapsePanel: React.FC<{
activeKey: string | string[]; activeKey: string | string[];
accordion?: boolean; accordion?: boolean;
onChange?: (key: string | string[]) => void; onChange?: (key: string | string[]) => void;
}> = ({ items, activeKey, accordion, onChange }) => { styles?: Record<string, React.CSSProperties>;
}> = ({ items, activeKey, accordion, onChange, styles }) => {
return ( return (
<CollapseInner <CollapseInner
expandIconPlacement="start" expandIconPlacement="start"
@@ -42,6 +45,12 @@ const CollapsePanel: React.FC<{
activeKey={activeKey} activeKey={activeKey}
onChange={onChange} onChange={onChange}
destroyOnHidden={false} destroyOnHidden={false}
styles={{
...styles,
header: {
backgroundColor: 'var(--ant-collapse-header-bg)'
}
}}
expandIcon={({ isActive }) => ( expandIcon={({ isActive }) => (
<IconFont <IconFont
type="icon-down" type="icon-down"
+1 -1
View File
@@ -48,7 +48,7 @@ const Header = styled.div`
padding-inline: 10px; padding-inline: 10px;
font-size: 14px; font-size: 14px;
border-bottom: 1px solid var(--ant-color-border); border-bottom: 1px solid var(--ant-color-border);
background-color: var(--ant-color-fill-tertiary); background-color: var(--ant-color-fill-quaternary);
`; `;
interface ViewerProps { interface ViewerProps {
@@ -1,9 +1,7 @@
import { clusterSessionAtom } from '@/atoms/clusters';
import { PageAction } from '@/config'; import { PageAction } from '@/config';
import { PageActionType } from '@/config/types'; import { PageActionType } from '@/config/types';
import ColumnWrapper from '@/pages/_components/column-wrapper'; import ColumnWrapper from '@/pages/_components/column-wrapper';
import { useIntl, useSearchParams } from '@umijs/max'; import { useIntl } from '@umijs/max';
import { useAtom } from 'jotai';
import _ from 'lodash'; import _ from 'lodash';
import React, { useEffect, useMemo, useRef, useState } from 'react'; import React, { useEffect, useMemo, useRef, useState } from 'react';
import styled from 'styled-components'; import styled from 'styled-components';
@@ -40,29 +38,20 @@ const Content = styled.div`
width: 100%; width: 100%;
`; `;
const StepsWrapper = styled.div`
width: 220px;
padding-inline: 24px;
padding-block: 16px;
border-right: 1px solid var(--ant-color-split);
`;
const MainWrapper = styled.div` const MainWrapper = styled.div`
display: flex; display: flex;
height: 100%; height: 100%;
`; `;
const ClusterCreate: React.FC<{ const ClusterCreate: React.FC<{
action: PageActionType;
setCurrentTitle?: (title: string) => void;
onClose?: () => void; onClose?: () => void;
}> = ({ onClose }) => { }> = ({ onClose, action, setCurrentTitle }) => {
const intl = useIntl();
const startStep = 0; const startStep = 0;
const stepList = useStepList(); const stepList = useStepList();
const { systemConfig } = useSystemConfig(); const { systemConfig } = useSystemConfig();
const [searchParams] = useSearchParams(); const intl = useIntl();
const action =
(searchParams.get('action') as PageActionType) || PageAction.CREATE;
const [clusterSession, setClusterSession] = useAtom(clusterSessionAtom);
const [credentialList, setCredentialList] = useState< const [credentialList, setCredentialList] = useState<
Global.BaseOption<number, { provider: ProviderType }>[] Global.BaseOption<number, { provider: ProviderType }>[]
>([]); >([]);
@@ -85,7 +74,6 @@ const ClusterCreate: React.FC<{
const [formValues, setFormValues] = useState<Record<string, any>>({}); const [formValues, setFormValues] = useState<Record<string, any>>({});
const [submitLoading, setSubmitLoading] = useState<boolean>(false); const [submitLoading, setSubmitLoading] = useState<boolean>(false);
const [isAddWorkerStep, setIsAddWorkerStep] = useState<boolean>(false); const [isAddWorkerStep, setIsAddWorkerStep] = useState<boolean>(false);
const [isComplete, setIsComplete] = useState<boolean>(false);
const formRefs: Record<string, any> = { const formRefs: Record<string, any> = {
[moduleMap.BasicForm]: useRef<any>(null), [moduleMap.BasicForm]: useRef<any>(null),
@@ -240,6 +228,7 @@ const ClusterCreate: React.FC<{
// add worker or cluster registration step // add worker or cluster registration step
const handleAddWorker = () => { const handleAddWorker = () => {
setIsAddWorkerStep(true); setIsAddWorkerStep(true);
setCurrentTitle?.(intl.formatMessage({ id: 'resources.button.create' }));
onNext(); onNext();
}; };
@@ -301,7 +290,6 @@ const ClusterCreate: React.FC<{
const res = await createCluster({ data }); const res = await createCluster({ data });
const info = await queryClusterToken({ id: res.id }); const info = await queryClusterToken({ id: res.id });
setSubmitLoading(false); setSubmitLoading(false);
setIsComplete(true);
setRegistrationInfo({ setRegistrationInfo({
...info, ...info,
cluster_id: res.id cluster_id: res.id
@@ -320,11 +308,6 @@ const ClusterCreate: React.FC<{
return ( return (
<MainWrapper> <MainWrapper>
{/* {!isAddWorkerStep && (
<StepsWrapper>
<ClusterSteps steps={steps} currentStep={currentStep}></ClusterSteps>
</StepsWrapper>
)} */}
<ColumnWrapper <ColumnWrapper
styles={{ styles={{
container: { paddingTop: 16, paddingBottom: 16 } container: { paddingTop: 16, paddingBottom: 16 }
@@ -341,13 +324,6 @@ const ClusterCreate: React.FC<{
/> />
} }
> >
{/* {!isComplete && (
<div style={{ marginBottom: 24 }}>
<Title level={5} style={{ marginBottom: 8, fontSize: 14 }}>
{steps[currentStep]?.subTitle || steps[currentStep]?.title}
</Title>
</div>
)} */}
{!isAddWorkerStep && ( {!isAddWorkerStep && (
<div style={{ marginBottom: 32 }}> <div style={{ marginBottom: 32 }}>
<ClusterSteps <ClusterSteps
@@ -1,4 +1,5 @@
import GSDrawer from '@/components/scroller-modal/gs-drawer'; import GSDrawer from '@/components/scroller-modal/gs-drawer';
import { PageAction } from '@/config';
import React from 'react'; import React from 'react';
import ClusterCreate from './cluster-create'; import ClusterCreate from './cluster-create';
@@ -13,13 +14,14 @@ const ClusterModal: React.FC<ClusterModalProps> = ({
onClose, onClose,
title title
}) => { }) => {
const [currentTitle, setCurrentTitle] = React.useState<string>(title);
const handleCancel = () => { const handleCancel = () => {
onClose(); onClose();
}; };
return ( return (
<GSDrawer <GSDrawer
title={title} title={currentTitle}
open={open} open={open}
onClose={handleCancel} onClose={handleCancel}
destroyOnHidden={true} destroyOnHidden={true}
@@ -34,7 +36,11 @@ const ClusterModal: React.FC<ClusterModalProps> = ({
}} }}
footer={false} footer={false}
> >
<ClusterCreate onClose={handleCancel}></ClusterCreate> <ClusterCreate
onClose={handleCancel}
action={PageAction.CREATE}
setCurrentTitle={setCurrentTitle}
></ClusterCreate>
</GSDrawer> </GSDrawer>
); );
}; };
@@ -65,6 +65,7 @@ const AddWorkerCommand: React.FC<ViewModalProps> = ({
code={code} code={code}
copyValue={code} copyValue={code}
lang="bash" lang="bash"
xScrollable={true}
></HighlightCode> ></HighlightCode>
); );
}; };
@@ -131,7 +131,7 @@ const AddWorker: React.FC<AddWorkerProps> = (props) => {
body: { body: {
paddingBlock: 0 paddingBlock: 0
}, },
wrapper: { width: 865 } wrapper: { width: 700 }
}} }}
footer={false} footer={false}
> >
@@ -1,4 +1,3 @@
import { CheckCircleFilled, CheckCircleOutlined } from '@ant-design/icons';
import { Steps } from 'antd'; import { Steps } from 'antd';
import React from 'react'; import React from 'react';
import styled from 'styled-components'; import styled from 'styled-components';
@@ -9,6 +8,9 @@ const Wrapper = styled.div`
gap: 24px; gap: 24px;
`; `;
/**
* --steps-item-base-width: 20px; type="panel"
*/
const Box = styled.div` const Box = styled.div`
.indicates { .indicates {
color: var(--ant-color-text-tertiary); color: var(--ant-color-text-tertiary);
@@ -16,76 +18,20 @@ const Box = styled.div`
margin-bottom: 24px; margin-bottom: 24px;
} }
.ant-steps { .ant-steps {
--steps-title-font-size: 14px;
.ant-steps-item { .ant-steps-item {
--steps-item-base-width: 20px; --steps-item-base-width: 20px;
} }
.ant-steps-item-rail-wait {
--steps-item-solid-line-color: var(--ant-color-split);
} }
`; &:not(.ant-steps-panel) {
.ant-steps-item-finish {
const StepItemWrapper = styled.div` --steps-item-icon-bg-color: var(--ant-color-primary);
display: flex;
align-items: flex-start;
gap: 12px;
padding-bottom: 16px;
// border-bottom: 1px solid var(--ant-color-split);
.description {
display: flex;
flex-direction: column;
gap: 4px;
.title {
font-weight: 500;
line-height: 20px;
color: var(--ant-color-text-tertiary);
}
.content {
line-height: 22px;
font-size: 14px;
color: var(--ant-color-text-tertiary);
}
}
&.active {
.description {
.title {
color: var(--ant-color-text);
font-weight: 600;
}
.content {
color: var(--ant-color-text);
} }
} }
} }
`; `;
const StepsItem: React.FC<{
active: boolean;
item: {
title: string;
content: string;
};
}> = ({ active, item }) => {
return (
<StepItemWrapper className={active ? 'active' : ''}>
<div className="icon">
{active ? (
<CheckCircleFilled
style={{ color: 'var(--ant-color-primary)', fontSize: 20 }}
/>
) : (
<CheckCircleOutlined
style={{ color: 'var(--ant-color-text-disabled)', fontSize: 20 }}
/>
)}
</div>
<div className="description">
<div className="title">{item.title}</div>
<div className="content">{item.content}</div>
</div>
</StepItemWrapper>
);
};
const ClusterSteps: React.FC<{ const ClusterSteps: React.FC<{
currentStep: number; currentStep: number;
onChange?: (step: number) => void; onChange?: (step: number) => void;
@@ -94,28 +40,41 @@ const ClusterSteps: React.FC<{
const { steps, currentStep = 0, onChange } = props; const { steps, currentStep = 0, onChange } = props;
const visibleSteps = steps.filter((step) => !step.hideInSteps); const visibleSteps = steps.filter((step) => !step.hideInSteps);
return (
<Box> const styles: Record<string, any> = {
<Wrapper> root: {
{/* {visibleSteps.map((item, index) => ( '--ant-steps-description-max-width': 'auto'
<StepsItem },
key={index}
active={currentStep === index}
item={item}
></StepsItem>
))} */}
<Steps
current={currentStep}
items={visibleSteps}
type="panel"
styles={{
item: { item: {
paddingBlock: 0 paddingBlock: 0
}, },
itemIcon: {
fontSize: 0,
width: 8,
height: 8,
marginInlineStart: 0
},
itemWrapper: {
alignItems: 'center'
},
itemRail: { itemRail: {
borderColor: 'var(--ant-color-split)' borderWidth: 1.5,
borderRadius: 1,
insetInlineStart: 10,
insetInlineEnd: 2,
'--steps-horizontal-rail-margin': '12px'
} }
}} };
return (
<Box>
<Wrapper>
<Steps
current={currentStep}
items={visibleSteps}
variant="filled"
size="small"
styles={styles}
></Steps> ></Steps>
</Wrapper> </Wrapper>
</Box> </Box>
@@ -35,11 +35,11 @@ const SuccessResult: React.FC<{
}} }}
icon={ icon={
<CheckCircleFilled <CheckCircleFilled
style={{ color: 'var(--ant-color-success)', fontSize: 42 }} style={{ color: 'var(--ant-color-success)', fontSize: 36 }}
/> />
} }
status="success" status="success"
title={intl.formatMessage({ id: 'clusters.create.complete.tips' })} title={intl.formatMessage({ id: 'clusters.create.steps.complete.tips' })}
subTitle={provider === ProviderValueMap.Kubernetes ? k8sTips : dockerTips} subTitle={provider === ProviderValueMap.Kubernetes ? k8sTips : dockerTips}
extra={[ extra={[
<Flex gap={16} justify="center" key="buttons"> <Flex gap={16} justify="center" key="buttons">
@@ -15,7 +15,9 @@ export default function useStepList() {
return useMemo( return useMemo(
() => [ () => [
{ {
title: intl.formatMessage({ id: 'clusters.create.selectProvider' }), title: intl.formatMessage({
id: 'clusters.create.steps.selectProvider'
}),
content: '', content: '',
subTitle: '', subTitle: '',
description: description:
@@ -35,7 +37,7 @@ export default function useStepList() {
providers: [] providers: []
}, },
{ {
title: intl.formatMessage({ id: 'common.title.config' }), title: intl.formatMessage({ id: 'clusters.create.steps.configure' }),
content: '', content: '',
description: description:
'Set the cluster name, description, or other essential parameters in advanced settings.', 'Set the cluster name, description, or other essential parameters in advanced settings.',
@@ -72,7 +74,7 @@ export default function useStepList() {
beforeNext: handleBack beforeNext: handleBack
}, },
{ {
title: intl.formatMessage({ id: 'clusters.create.complete' }), title: intl.formatMessage({ id: 'clusters.create.steps.complete' }),
content: '', content: '',
description: '', description: '',
showButtons: (provider?: ProviderType) => { showButtons: (provider?: ProviderType) => {
+3 -2
View File
@@ -77,9 +77,10 @@ const AdvanceConfig = () => {
included={true} included={true}
max={modelContextData?.scaled || 163840} max={modelContextData?.scaled || 163840}
tooltip={{}} tooltip={{}}
step={1024}
marks={{ marks={{
[modelContextData?.native]: 'native', [modelContextData?.scaled]: 'scaled',
[modelContextData?.scaled]: 'scaled' [modelContextData?.native]: 'native'
}} }}
></SealSlider> ></SealSlider>
</Form.Item> </Form.Item>