refactor: ui/ux

This commit is contained in:
jialin
2026-04-08 18:54:06 +08:00
committed by jialin
parent 06160546a6
commit 1c09cc6c8c
22 changed files with 325 additions and 167 deletions
+1 -1
View File
@@ -1,4 +1,4 @@
export const HEADER_HEIGHT = 56; export const HEADER_HEIGHT = 48;
export const DEFAULT_ENTER_PAGE = { export const DEFAULT_ENTER_PAGE = {
adminForNormal: '/dashboard', adminForNormal: '/dashboard',
+3
View File
@@ -4,6 +4,9 @@ export default {
'root-entry-name': 'variable', 'root-entry-name': 'variable',
hashed: false, hashed: false,
components: { components: {
Layout: {
headerHeight: 48
},
Input: { Input: {
inputFontSize: 14, inputFontSize: 14,
inputFontSizeLG: 14 inputFontSizeLG: 14
+12 -4
View File
@@ -4,6 +4,8 @@
@import url('./overrides.less'); @import url('./overrides.less');
html { html {
--page-header-height: 56px;
--page-content-padding: 8px;
--color-text-light-1: rgba(255, 255, 255, 90%); --color-text-light-1: rgba(255, 255, 255, 90%);
--color-fill-1: var(--ant-color-bg-container); --color-fill-1: var(--ant-color-bg-container);
--color-scrollbar-thumb: rgba(193, 193, 193, 80%); --color-scrollbar-thumb: rgba(193, 193, 193, 80%);
@@ -22,8 +24,8 @@ html {
--color-fill-3: #f3f6fa; --color-fill-3: #f3f6fa;
--color-logs-bg: #1e1e1e; --color-logs-bg: #1e1e1e;
--color-logs-text: #d4d4d4; --color-logs-text: #d4d4d4;
--layout-content-blockpadding: 32px; --layout-content-blockpadding: 24px;
--layout-content-inlinepadding: 32px; --layout-content-inlinepadding: 24px;
--layout-content-header-inlinepadding: 40px; --layout-content-header-inlinepadding: 40px;
--border-radius-modal: 12px; --border-radius-modal: 12px;
--menu-border-radius-base: 4px; --menu-border-radius-base: 4px;
@@ -120,6 +122,8 @@ html[data-theme='light'] {
background-color: #fff !important; background-color: #fff !important;
transition: none !important; transition: none !important;
} }
background-color: #f5f5f5;
} }
body { body {
@@ -275,7 +279,7 @@ body {
} }
.ant-pro-sider .ant-layout-sider-children { .ant-pro-sider .ant-layout-sider-children {
border-right: 1px solid var(--ant-color-split); // border-right: 1px solid var(--ant-color-split);
} }
} }
@@ -336,7 +340,7 @@ body {
.ant-pro-layout-container { .ant-pro-layout-container {
overflow-x: auto; overflow-x: auto;
min-height: 100vh; min-height: 100vh;
background-color: var(--ant-color-bg-container); // background-color: var(--ant-color-bg-container);
} }
.ant-pro-sider { .ant-pro-sider {
@@ -819,3 +823,7 @@ body {
.ant-drawer .ant-drawer-mask.ant-drawer-mask-blur { .ant-drawer .ant-drawer-mask.ant-drawer-mask-blur {
backdrop-filter: blur(2px); backdrop-filter: blur(2px);
} }
.ant-pro-grid-content {
padding-right: 8px;
}
+1 -1
View File
@@ -60,7 +60,7 @@ const Wrapper = styled.div`
display: flex; display: flex;
align-items: center; align-items: center;
gap: 24px; gap: 24px;
height: 40px; height: 32px;
`; `;
const DropdownWrapper = styled.div` const DropdownWrapper = styled.div`
min-width: 160px; min-width: 160px;
+28 -6
View File
@@ -215,10 +215,28 @@ export default (props: any) => {
}, [matchedRoute]); }, [matchedRoute]);
useEffect(() => { useEffect(() => {
const body = document.querySelector('body'); const initializeScroller = () => {
if (body) { // const body = document.querySelector('.ant-pro-grid-content-children');
const ins = initialize(body); // if (body) {
window.__GPUSTACK_BODY_SCROLLER__ = ins; // const ins = initialize(body);
// window.__GPUSTACK_BODY_SCROLLER__ = ins;
// return true;
// }
// return false;
return true;
};
// Try to initialize immediately
if (!initializeScroller()) {
// If element not found, retry with requestAnimationFrame
const rafId = requestAnimationFrame(() => {
if (!initializeScroller()) {
// If still not found, retry after a short delay
const timeoutId = setTimeout(initializeScroller, 100);
return () => clearTimeout(timeoutId);
}
});
return () => cancelAnimationFrame(rafId);
} }
}, [initialize]); }, [initialize]);
@@ -312,6 +330,8 @@ export default (props: any) => {
}); });
}; };
console.log('userConfig==========title', userConfig.title);
return ( return (
<ConfigProvider <ConfigProvider
componentSize="large" componentSize="large"
@@ -336,7 +356,7 @@ export default (props: any) => {
<DarkMask></DarkMask> <DarkMask></DarkMask>
<ProLayout <ProLayout
fixSiderbar fixSiderbar
fixedHeader={true} fixedHeader={false}
breadcrumbRender={false} breadcrumbRender={false}
route={route} route={route}
location={location} location={location}
@@ -384,7 +404,9 @@ export default (props: any) => {
<Outlet /> <Outlet />
) : ( ) : (
<PageContainerInner> <PageContainerInner>
<Outlet /> <div>
<Outlet />
</div>
</PageContainerInner> </PageContainerInner>
)} )}
</Exception> </Exception>
+54 -31
View File
@@ -1,44 +1,67 @@
import useOverlayScroller from '@/hooks/use-overlay-scroller';
import { import {
PageContainer, PageContainer,
RouteContext,
type PageContainerProps type PageContainerProps
} from '@ant-design/pro-components'; } from '@ant-design/pro-components';
import styled from 'styled-components'; import classNames from 'classnames';
import { useContext, useEffect, useRef } from 'react';
import pageBoxCss from './styles/page-box.less';
const paddingInlinePageContainerContent = 32; const paddingInlinePageContainerContent = 24;
const StyledPageContainer = styled(PageContainer)` export const PageContainerInner: React.FC<
.ant-affix { PageContainerProps & {
top: 0 !important; leftContent?: React.ReactNode;
height: auto; rightContent?: React.ReactNode;
styles?: {
containerWrapper?: React.CSSProperties;
};
} }
.ant-page-header { > = ({ children, styles, title, leftContent, rightContent, ...rest }) => {
padding-block-end: 8px; const { initialize: initialize } = useOverlayScroller({
.ant-page-header-heading { defer: false
padding-block-start: 0; });
const pageContext = useContext(RouteContext);
const contentWrapperRef = useRef<HTMLDivElement>(null);
useEffect(() => {
if (contentWrapperRef.current) {
const ins = initialize(contentWrapperRef.current);
window.__GPUSTACK_BODY_SCROLLER__ = ins;
} }
} }, [initialize, contentWrapperRef]);
.ant-pro-page-container-warp-page-header {
padding-inline: ${paddingInlinePageContainerContent}px;
}
.ant-page-header-heading-title {
font-size: 16px;
}
`;
export const PageContainerInner: React.FC<PageContainerProps> = ({
children,
...rest
}) => {
return ( return (
<StyledPageContainer <div className={pageBoxCss.containerWrapper}>
{...rest} <PageContainer
fixedHeader={true} {...rest}
token={{ fixedHeader={false}
paddingInlinePageContainerContent: paddingInlinePageContainerContent title={false}
}} style={{
> flex: 1
{children} }}
</StyledPageContainer> token={{
paddingInlinePageContainerContent: paddingInlinePageContainerContent
}}
>
<div className={pageBoxCss.title}>
<div className={pageBoxCss.left}>
{leftContent || pageContext.title}
</div>
{rightContent && (
<div className={pageBoxCss.right}>{rightContent}</div>
)}
</div>
<div
className={classNames(pageBoxCss.contentWrapper)}
style={styles?.containerWrapper}
ref={contentWrapperRef}
>
{children}
</div>
</PageContainer>
</div>
); );
}; };
@@ -0,0 +1,62 @@
.containerWrapper {
:global {
.ant-affix {
top: 0 !important;
height: auto;
}
.ant-page-header {
padding-block-end: 8px;
.ant-page-header-heading {
padding-block-start: 0;
}
}
.ant-page-header-heading-title {
font-size: 16px;
}
.ant-pro-page-container-children-container {
height: calc(100vh - 56px);
display: flex;
flex-direction: column;
border: 1px solid rgb(237, 237, 237);
border-radius: 8px;
overflow: hidden;
background-color: var(--ant-color-bg-container);
padding: 0;
}
}
.contentWrapper {
flex: 1;
overflow-y: auto;
padding-block: var(--layout-content-blockpadding);
padding-inline: var(--layout-content-inlinepadding);
}
.title {
display: flex;
align-items: center;
justify-content: space-between;
width: 100%;
padding-inline: var(--layout-content-inlinepadding);
font-size: 16px;
color: var(--ant-color-text);
font-weight: 600;
padding-block: 9px 8px;
height: 56px;
border-bottom: 1px solid var(--ant-color-split);
.left {
display: flex;
align-items: center;
}
.right {
display: flex;
align-items: center;
}
}
}
+31 -29
View File
@@ -46,34 +46,36 @@ const LLModels: React.FC = () => {
setActiveKey(key); setActiveKey(key);
}); });
const header = useMemo(() => { const title = useMemo(() => {
return { return (
title: ( <div className="flex items-center">
<div className="flex items-center"> <span className="font-600 flex-center">
<span className="font-600"> {intl.formatMessage({ id: 'menu.models.deployment' })}
{intl.formatMessage({ id: 'menu.models.deployment' })} </span>
</span> <Segmented
<Segmented shape="round"
options={[ style={{
{ backgroundColor: 'var(--ant-color-fill-secondary)'
label: intl.formatMessage({ id: 'models.table.modelView' }), }}
value: TabsValueMap.ModelView, size="middle"
icon: <IconFont type={'icon-models'}></IconFont> className="m-l-24 font-400"
}, options={[
{ {
label: intl.formatMessage({ id: 'models.table.instanceView' }), label: intl.formatMessage({ id: 'models.table.modelView' }),
value: TabsValueMap.InstanceView, value: TabsValueMap.ModelView,
icon: <IconFont type={'icon-instance-outline'}></IconFont> icon: <IconFont type={'icon-models'}></IconFont>
} },
]} {
size="middle" label: intl.formatMessage({ id: 'models.table.instanceView' }),
className="m-l-24 font-600" value: TabsValueMap.InstanceView,
value={activeKey} icon: <IconFont type={'icon-instance-outline'}></IconFont>
onChange={handleTabChange} }
></Segmented> ]}
</div> value={activeKey}
) onChange={handleTabChange}
}; ></Segmented>
</div>
);
}, [activeKey, intl]); }, [activeKey, intl]);
useEffect(() => { useEffect(() => {
@@ -103,7 +105,7 @@ const LLModels: React.FC = () => {
}, [activeKey]); }, [activeKey]);
return ( return (
<PageContainerInner header={header}> <PageContainerInner leftContent={title}>
<DeploymentsContext.Provider <DeploymentsContext.Provider
value={{ value={{
generateFormValues, generateFormValues,
@@ -131,7 +131,7 @@ const useProviderColumns = (options: {
{ {
title: intl.formatMessage({ id: 'clusters.title' }), title: intl.formatMessage({ id: 'clusters.title' }),
dataIndex: 'cluster_id', dataIndex: 'cluster_id',
minWidth: 200, width: 200,
render: (text: number) => ( render: (text: number) => (
<AutoTooltip ghost> <AutoTooltip ghost>
{text {text
@@ -157,6 +157,7 @@ const useProviderColumns = (options: {
title: intl.formatMessage({ id: 'models.table.vram.allocated' }), title: intl.formatMessage({ id: 'models.table.vram.allocated' }),
dataIndex: 'allocated_vram', dataIndex: 'allocated_vram',
sorter: tableSorter(6), sorter: tableSorter(6),
width: 160,
render: (text, record) => ( render: (text, record) => (
<AutoTooltip ghost> <AutoTooltip ghost>
{convertFileSize( {convertFileSize(
+41 -22
View File
@@ -1,12 +1,11 @@
import breakpoints from '@/config/breakpoints'; import breakpoints from '@/config/breakpoints';
import HotKeys from '@/config/hotkeys'; import HotKeys from '@/config/hotkeys';
import useWindowResize from '@/hooks/use-window-resize'; import useWindowResize from '@/hooks/use-window-resize';
import { ExtraContent } from '@/layouts/extraRender';
import { modelCategoriesMap } from '@/pages/llmodels/config'; import { modelCategoriesMap } from '@/pages/llmodels/config';
import { MessageOutlined, OneToOneOutlined } from '@ant-design/icons'; import { MessageOutlined, OneToOneOutlined } from '@ant-design/icons';
import { useIntl } from '@umijs/max'; import { useIntl } from '@umijs/max';
import { useMemoizedFn } from 'ahooks'; import { useMemoizedFn } from 'ahooks';
import { Divider, Segmented, Tabs, TabsProps } from 'antd'; import { Segmented, Tabs, TabsProps } from 'antd';
import classNames from 'classnames'; import classNames from 'classnames';
import _ from 'lodash'; import _ from 'lodash';
import { useEffect, useMemo, useRef, useState } from 'react'; import { useEffect, useMemo, useRef, useState } from 'react';
@@ -109,11 +108,11 @@ const Playground: React.FC = () => {
fetchData(); fetchData();
}, []); }, []);
const header = useMemo(() => { const title = useMemo(() => {
return { return (
title: ( <div className="flex justify-between items-center">
<div className="flex items-center"> <div className="flex items-center">
<span className="font-600"> <span className="font-600 flex-center">
{intl.formatMessage({ id: 'menu.playground.chat' })} {intl.formatMessage({ id: 'menu.playground.chat' })}
</span> </span>
{ {
@@ -126,8 +125,14 @@ const Playground: React.FC = () => {
></Segmented> ></Segmented>
} }
</div> </div>
) <ViewCodeButtons
}; handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse}
activeKey={activeKey}
key="view-code-buttons"
/>
</div>
);
}, [activeKey, optionsList, intl]); }, [activeKey, optionsList, intl]);
useHotkeys( useHotkeys(
@@ -148,25 +153,39 @@ const Playground: React.FC = () => {
compare: activeKey === 'compare', compare: activeKey === 'compare',
chat: activeKey !== 'compare' chat: activeKey !== 'compare'
})} })}
header={header} styles={{
extra={[ containerWrapper: {
padding: 0
}
}}
leftContent={
<div className="flex items-center">
<span className="font-600 flex-center">
{intl.formatMessage({ id: 'menu.playground.chat' })}
</span>
{
<Segmented
shape="round"
style={{
backgroundColor: 'var(--ant-color-fill-secondary)'
}}
size="middle"
className="m-l-24 font-400"
options={optionsList}
value={activeKey}
onChange={(key) => setActiveKey(key)}
></Segmented>
}
</div>
}
rightContent={
<ViewCodeButtons <ViewCodeButtons
handleViewCode={handleViewCode} handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse} handleToggleCollapse={handleToggleCollapse}
activeKey={activeKey} activeKey={activeKey}
key="view-code-buttons" key="view-code-buttons"
/>, />
<div key="divider-wrapper"> }
{activeKey === 'chat' && (
<Divider
key="divider"
orientation="vertical"
style={{ height: 16, marginInline: 16 }}
/>
)}
</div>,
<ExtraContent key="extra-content" />
]}
> >
<div className="play-ground"> <div className="play-ground">
<div className="chat"> <div className="chat">
@@ -15,7 +15,7 @@ const ViewCodeButtons: React.FC<{
} }
return ( return (
<Space key="buttons" style={{ marginRight: 8 }}> <Space key="buttons">
<Button <Button
size="middle" size="middle"
onClick={handleViewCode} onClick={handleViewCode}
+8 -11
View File
@@ -1,9 +1,7 @@
import HotKeys from '@/config/hotkeys'; import HotKeys from '@/config/hotkeys';
import { ExtraContent } from '@/layouts/extraRender';
import { modelCategoriesMap } from '@/pages/llmodels/config'; import { modelCategoriesMap } from '@/pages/llmodels/config';
import { useIntl } from '@umijs/max'; import { useIntl } from '@umijs/max';
import { useMemoizedFn } from 'ahooks'; import { useMemoizedFn } from 'ahooks';
import { Divider } from 'antd';
import classNames from 'classnames'; import classNames from 'classnames';
import _ from 'lodash'; import _ from 'lodash';
import { useEffect, useRef, useState } from 'react'; import { useEffect, useRef, useState } from 'react';
@@ -81,20 +79,19 @@ const PlaygroundEmbedding: React.FC = () => {
return ( return (
<PageContainerInner <PageContainerInner
className={classNames('playground-container chat')} className={classNames('playground-container chat')}
extra={[ styles={{
containerWrapper: {
padding: 0
}
}}
rightContent={
<ViewCodeButtons <ViewCodeButtons
activeKey="" activeKey=""
handleViewCode={handleViewCode} handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse} handleToggleCollapse={handleToggleCollapse}
key="view-code-buttons" key="view-code-buttons"
/>, />
<Divider }
key="divider"
orientation="vertical"
style={{ height: 16, marginInline: 16 }}
/>,
<ExtraContent key="extra-content" />
]}
> >
<div className="play-ground"> <div className="play-ground">
<div className="chat"> <div className="chat">
+1 -1
View File
@@ -622,7 +622,7 @@ const GroundEmbedding: React.FC<MessageProps> = forwardRef((props, ref) => {
className="ground-left-footer" className="ground-left-footer"
style={{ style={{
width: '100%', width: '100%',
padding: '0 32px 16px' padding: '0 var(--layout-content-inlinepadding) 16px'
}} }}
> >
<h3 className="m-l-10 flex-between flex-center font-size-14 line-24 m-b-16"> <h3 className="m-l-10 flex-between flex-center font-size-14 line-24 m-b-16">
+23 -12
View File
@@ -1,12 +1,11 @@
import breakpoints from '@/config/breakpoints'; import breakpoints from '@/config/breakpoints';
import HotKeys from '@/config/hotkeys'; import HotKeys from '@/config/hotkeys';
import useWindowResize from '@/hooks/use-window-resize'; import useWindowResize from '@/hooks/use-window-resize';
import { ExtraContent } from '@/layouts/extraRender';
import { modelCategoriesMap } from '@/pages/llmodels/config'; import { modelCategoriesMap } from '@/pages/llmodels/config';
import { DiffOutlined, HighlightOutlined } from '@ant-design/icons'; import { DiffOutlined, HighlightOutlined } from '@ant-design/icons';
import { useIntl } from '@umijs/max'; import { useIntl } from '@umijs/max';
import { useMemoizedFn } from 'ahooks'; import { useMemoizedFn } from 'ahooks';
import { Divider, Segmented, Tabs, TabsProps } from 'antd'; import { Segmented, Tabs, TabsProps } from 'antd';
import classNames from 'classnames'; import classNames from 'classnames';
import _ from 'lodash'; import _ from 'lodash';
import { useEffect, useMemo, useRef, useState } from 'react'; import { useEffect, useMemo, useRef, useState } from 'react';
@@ -156,21 +155,33 @@ const TextToImages: React.FC = () => {
return ( return (
<PageContainerInner <PageContainerInner
header={header} leftContent={
extra={[ <div className="flex items-center">
<span className="font-600 flex-center">
{intl.formatMessage({ id: 'menu.playground.text2images' })}
</span>
<Segmented
shape="round"
style={{
backgroundColor: 'var(--ant-color-fill-secondary)'
}}
size="middle"
className="m-l-24 font-400"
options={optionsList}
value={activeKey}
onChange={(key) => setActiveKey(key)}
></Segmented>
</div>
}
rightContent={
<ViewCodeButtons <ViewCodeButtons
handleViewCode={handleViewCode} handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse} handleToggleCollapse={handleToggleCollapse}
activeKey={activeKey} activeKey={activeKey}
key="view-code-buttons" key="view-code-buttons"
></ViewCodeButtons>, ></ViewCodeButtons>
<Divider }
key="divider" styles={{ containerWrapper: { padding: 0 } }}
orientation="vertical"
style={{ height: 16, marginInline: 16 }}
/>,
<ExtraContent key="extra-content" />
]}
className={classNames('playground-container chat')} className={classNames('playground-container chat')}
> >
<div className="play-ground"> <div className="play-ground">
+8 -11
View File
@@ -1,9 +1,7 @@
import HotKeys from '@/config/hotkeys'; import HotKeys from '@/config/hotkeys';
import { ExtraContent } from '@/layouts/extraRender';
import { modelCategoriesMap } from '@/pages/llmodels/config'; import { modelCategoriesMap } from '@/pages/llmodels/config';
import { useIntl } from '@umijs/max'; import { useIntl } from '@umijs/max';
import useMemoizedFn from 'ahooks/lib/useMemoizedFn'; import useMemoizedFn from 'ahooks/lib/useMemoizedFn';
import { Divider } from 'antd';
import classNames from 'classnames'; import classNames from 'classnames';
import _ from 'lodash'; import _ from 'lodash';
import { useEffect, useRef, useState } from 'react'; import { useEffect, useRef, useState } from 'react';
@@ -85,20 +83,19 @@ const PlaygroundRerank: React.FC = () => {
return ( return (
<PageContainerInner <PageContainerInner
className={classNames('playground-container chat')} className={classNames('playground-container chat')}
extra={[ styles={{
containerWrapper: {
padding: 0
}
}}
rightContent={
<ViewCodeButtons <ViewCodeButtons
activeKey="" activeKey=""
handleViewCode={handleViewCode} handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse} handleToggleCollapse={handleToggleCollapse}
key="view-code-buttons" key="view-code-buttons"
></ViewCodeButtons>, ></ViewCodeButtons>
<Divider }
key="divider"
orientation="vertical"
style={{ height: 16, marginInline: 16 }}
/>,
<ExtraContent key="extra-content" />
]}
> >
<div className="play-ground"> <div className="play-ground">
<div className="chat"> <div className="chat">
+5 -2
View File
@@ -41,7 +41,7 @@ import { fieldConfig } from './params-config';
const { Text } = Typography; const { Text } = Typography;
const SearchInputWrapper = styled.div` const SearchInputWrapper = styled.div`
margin: 16px 32px 10px; margin: 16px var(--layout-content-inlinepadding) 10px;
position: relative; position: relative;
`; `;
@@ -477,7 +477,10 @@ const GroundReranker: React.FC<MessageProps> = forwardRef((props, ref) => {
<div className="ground-left-footer"> <div className="ground-left-footer">
<h3 <h3
className="m-l-10 flex-between flex-center font-size-14 line-24 m-b-0" className="m-l-10 flex-between flex-center font-size-14 line-24 m-b-0"
style={{ padding: '0 32px', marginTop: 16 }} style={{
padding: '0 var(--layout-content-inlinepadding)',
marginTop: 16
}}
> >
<span>{intl.formatMessage({ id: 'playground.rerank.query' })}</span> <span>{intl.formatMessage({ id: 'playground.rerank.query' })}</span>
</h3> </h3>
+24 -12
View File
@@ -2,12 +2,11 @@ import IconFont from '@/components/icon-font';
import breakpoints from '@/config/breakpoints'; import breakpoints from '@/config/breakpoints';
import HotKeys from '@/config/hotkeys'; import HotKeys from '@/config/hotkeys';
import useWindowResize from '@/hooks/use-window-resize'; import useWindowResize from '@/hooks/use-window-resize';
import { ExtraContent } from '@/layouts/extraRender';
import { modelCategoriesMap } from '@/pages/llmodels/config'; import { modelCategoriesMap } from '@/pages/llmodels/config';
import { AudioOutlined } from '@ant-design/icons'; import { AudioOutlined } from '@ant-design/icons';
import { useIntl, useSearchParams } from '@umijs/max'; import { useIntl, useSearchParams } from '@umijs/max';
import useMemoizedFn from 'ahooks/lib/useMemoizedFn'; import useMemoizedFn from 'ahooks/lib/useMemoizedFn';
import { Divider, Segmented, Tabs, TabsProps } from 'antd'; import { Segmented, Tabs, TabsProps } from 'antd';
import classNames from 'classnames'; import classNames from 'classnames';
import _ from 'lodash'; import _ from 'lodash';
import { useEffect, useMemo, useRef, useState } from 'react'; import { useEffect, useMemo, useRef, useState } from 'react';
@@ -196,21 +195,34 @@ const Playground: React.FC = () => {
return ( return (
<PageContainerInner <PageContainerInner
header={header} leftContent={
extra={[ <div className="flex items-center">
<span className="font-600 flex-center">
{intl.formatMessage({ id: 'menu.playground.speech' })}
</span>
{
<Segmented
shape="round"
style={{
backgroundColor: 'var(--ant-color-fill-secondary)'
}}
size="middle"
className="m-l-24 font-400"
options={optionsList}
value={activeKey}
onChange={(key) => setActiveKey(key)}
></Segmented>
}
</div>
}
rightContent={
<ViewCodeButtons <ViewCodeButtons
activeKey="" activeKey=""
handleViewCode={handleViewCode} handleViewCode={handleViewCode}
handleToggleCollapse={handleToggleCollapse} handleToggleCollapse={handleToggleCollapse}
key="view-code-buttons" key="view-code-buttons"
></ViewCodeButtons>, ></ViewCodeButtons>
<Divider }
key="divider"
orientation="vertical"
style={{ height: 16, marginInline: 16 }}
/>,
<ExtraContent key="extra-content" />
]}
className={classNames('playground-container', { className={classNames('playground-container', {
compare: activeKey === 'compare', compare: activeKey === 'compare',
chat: activeKey !== 'compare' chat: activeKey !== 'compare'
+4 -1
View File
@@ -9,7 +9,10 @@
justify-content: space-between; justify-content: space-between;
flex-direction: column; flex-direction: column;
position: relative; position: relative;
height: calc(100vh - @HEADER_HEIGHT); height: calc(
100vh - @HEADER_HEIGHT - var(--page-content-padding) -
var(--page-header-height)
);
width: calc(100% - 390px); width: calc(100% - 390px);
.message-list-wrap { .message-list-wrap {
@@ -5,7 +5,10 @@
width: 390px; width: 390px;
border-left: 1px solid var(--ant-color-split); border-left: 1px solid var(--ant-color-split);
transition: width 0.3s ease; transition: width 0.3s ease;
height: calc(100vh - @HEADER_HEIGHT); height: calc(
100vh - @HEADER_HEIGHT - var(--page-content-padding) -
var(--page-header-height)
);
padding-top: 16px; padding-top: 16px;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
+10 -18
View File
@@ -1,4 +1,4 @@
@HEADER_HEIGHT: 56px; @HEADER_HEIGHT: 48px;
.play-ground { .play-ground {
display: flex; display: flex;
@@ -39,7 +39,10 @@
.params { .params {
overflow: hidden; overflow: hidden;
height: calc(100vh - @HEADER_HEIGHT); height: calc(
100vh - var(--page-header-height) - var(--page-content-padding) -
@HEADER_HEIGHT
);
.collapse { .collapse {
width: 0; width: 0;
@@ -48,7 +51,7 @@
} }
.params-box { .params-box {
padding-inline: 32px; padding-inline: var(--layout-content-inlinepadding);
height: 100%; height: 100%;
width: 390px; width: 390px;
overflow-y: auto; overflow-y: auto;
@@ -70,7 +73,10 @@
.ant-divider { .ant-divider {
margin: 0; margin: 0;
height: calc(100vh - 136px); height: calc(
100vh - var(--page-header-height) - var(--page-content-padding) -
@HEADER_HEIGHT
);
} }
} }
} }
@@ -85,20 +91,6 @@
position: relative; position: relative;
} }
&.chat {
.ant-page-header {
// &::after {
// position: absolute;
// content: '';
// left: 32px;
// right: 32px;
// bottom: 0;
// height: 1px;
// border-bottom: 1px solid var(--ant-color-split);
// }
}
}
&.compare { &.compare {
.ant-pro-page-container-children-container { .ant-pro-page-container-children-container {
padding-inline: 0; padding-inline: 0;
+1 -1
View File
@@ -3,7 +3,7 @@
display: flex; display: flex;
flex-direction: column; flex-direction: column;
height: 100%; height: 100%;
padding-inline: 32px; padding-inline: var(--layout-content-inlinepadding);
padding-bottom: 16px; padding-bottom: 16px;
.documents { .documents {
@@ -1,5 +1,5 @@
.speech-to-text { .speech-to-text {
padding: 32px; padding: var(--layout-content-inlinepadding);
height: 100%; height: 100%;
display: flex; display: flex;
gap: 30px; gap: 30px;