From 74266dc5cc786f86106cdf6999d34d1c7e5d0099 Mon Sep 17 00:00:00 2001 From: lanyuanxiaoyao Date: Mon, 8 Jun 2026 11:36:02 +0800 Subject: [PATCH] =?UTF-8?q?style:=20=E6=94=B6=E9=9B=86=E7=AE=B1=E5=B8=83?= =?UTF-8?q?=E5=B1=80=E6=B7=B1=E5=8C=96=E2=80=94=E2=80=94=E5=8D=A1=E7=89=87?= =?UTF-8?q?=E6=B5=81=E3=80=81OS=E6=BB=9A=E5=8A=A8=E3=80=81=E6=93=8D?= =?UTF-8?q?=E4=BD=9C=E5=8C=BAfill=E6=8C=89=E9=92=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/development/frontend.md | 18 ++--- .../inbox/components/MaterialContent.tsx | 53 +++++++------ .../inbox/components/MaterialDetailPanel.tsx | 79 ++++++++++++------- src/web/styles.css | 12 +-- 4 files changed, 92 insertions(+), 70 deletions(-) diff --git a/docs/development/frontend.md b/docs/development/frontend.md index 084a379..5cc3ef6 100644 --- a/docs/development/frontend.md +++ b/docs/development/frontend.md @@ -26,15 +26,15 @@ ConsoleShell 包含:`XProvider(zhCN + zhCN_X)` + `AntApp` + `Layout`(Header/Si ## 页面 -| 页面 | 路径 | 入口 | -| -------- | -------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| 总览 | `/` | `features/dashboard/index.tsx` | -| 项目管理 | `/projects` | `features/projects/index.tsx` — FilterToolbar(状态 Select + 搜索 + 新建/归档恢复删除) + ProjectTable + ProjectFormModal。支持创建/编辑/归档/恢复/删除、列表排序、URL 同步筛选参数。 | -| 模型管理 | `/models` 和 `/models/providers` | 独立路由页面:`ModelListPage.tsx`(FilterToolbar + ModelTable) + `ProviderListPage.tsx`(FilterToolbar + ProviderTable)。模型支持供应商/能力筛选和列表排序,供应商支持类型筛选和列表排序。模型表单使用 `GET /api/providers/options`。供应商表单支持预保存连通性测试(`POST /api/providers/test`)。 | -| 设置 | `/settings` | `features/settings/index.tsx` — 卡片式布局分区管理平台业务设置。"主题"卡片使用 antd Form 水平布局,包含主题模式(Radio.Group 按钮风:系统/明亮/黑暗)和紧凑模式(Switch 开关),使用 `useSettings` hook 通过 `GET/PUT /api/settings` 实时保存,`message` toast 反馈。 | -| 聊天室 | `/workbench/:id` | `features/chat/index.tsx` | -| 收集箱 | `/workbench/:id/inbox` | `features/inbox/index.tsx` — 协调层(selectedId + modalOpen)+ MaterialSidebar(列表容器)+ MaterialDetailPanel(详情容器)+ AddMaterialModal。素材 CRUD 通过 TanStack Query hooks 接入后端 API。 | -| 404 | `*` | `features/not-found/index.tsx` | +| 页面 | 路径 | 入口 | +| -------- | -------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | +| 总览 | `/` | `features/dashboard/index.tsx` | +| 项目管理 | `/projects` | `features/projects/index.tsx` — FilterToolbar(状态 Select + 搜索 + 新建/归档恢复删除) + ProjectTable + ProjectFormModal。支持创建/编辑/归档/恢复/删除、列表排序、URL 同步筛选参数。 | +| 模型管理 | `/models` 和 `/models/providers` | 独立路由页面:`ModelListPage.tsx`(FilterToolbar + ModelTable) + `ProviderListPage.tsx`(FilterToolbar + ProviderTable)。模型支持供应商/能力筛选和列表排序,供应商支持类型筛选和列表排序。模型表单使用 `GET /api/providers/options`。供应商表单支持预保存连通性测试(`POST /api/providers/test`)。 | +| 设置 | `/settings` | `features/settings/index.tsx` — 卡片式布局分区管理平台业务设置。"主题"卡片使用 antd Form 水平布局,包含主题模式(Radio.Group 按钮风:系统/明亮/黑暗)和紧凑模式(Switch 开关),使用 `useSettings` hook 通过 `GET/PUT /api/settings` 实时保存,`message` toast 反馈。 | +| 聊天室 | `/workbench/:id` | `features/chat/index.tsx` | +| 收集箱 | `/workbench/:id/inbox` | `features/inbox/index.tsx` — 协调层(selectedId + modalOpen)+ MaterialSidebar(列表容器)+ MaterialDetailPanel(透明内容区+OS滚动+操作区卡片)+ MaterialContent(纵向卡片流,基本信息Card)+ AddMaterialModal。操作区始终渲染,按钮 fill 样式 + disabled 控制。素材 CRUD 通过 TanStack Query hooks 接入后端 API。 | +| 404 | `*` | `features/not-found/index.tsx` | ### 聊天页面 diff --git a/src/web/features/inbox/components/MaterialContent.tsx b/src/web/features/inbox/components/MaterialContent.tsx index a57cb7c..365c489 100644 --- a/src/web/features/inbox/components/MaterialContent.tsx +++ b/src/web/features/inbox/components/MaterialContent.tsx @@ -1,4 +1,4 @@ -import { Card, Descriptions, Tag, Typography } from "antd"; +import { Card, Descriptions, Flex, Tag, Typography } from "antd"; import type { Material, MaterialType } from "../types"; @@ -19,31 +19,32 @@ export function MaterialContent({ material }: MaterialContentProps) { const typeLabel = MATERIAL_TYPE_LABELS[material.materialType] ?? material.materialType; return ( - <> - 素材详情 - - {material.description} - {material.processedContent && ( - - {material.processedContent} - - )} - - - {statusInfo.label} - - {typeLabel} - {material.associatedDate} - {formatRelativeTime(material.createdAt)} - + + + + {material.description} + {material.processedContent && ( + + {material.processedContent} + + )} + + + {statusInfo.label} + + {typeLabel} + {material.associatedDate} + {formatRelativeTime(material.createdAt)} + + - + ); } diff --git a/src/web/features/inbox/components/MaterialDetailPanel.tsx b/src/web/features/inbox/components/MaterialDetailPanel.tsx index 4fffc63..d4d2d8e 100644 --- a/src/web/features/inbox/components/MaterialDetailPanel.tsx +++ b/src/web/features/inbox/components/MaterialDetailPanel.tsx @@ -1,10 +1,16 @@ import { CheckOutlined, CloseOutlined, RedoOutlined } from "@ant-design/icons"; -import { App as AntApp, Button, Empty, Result, Space, Spin, Tag } from "antd"; +import "overlayscrollbars/styles/overlayscrollbars.css"; +import { App as AntApp, Button, Empty, Result, Space, Spin, Typography } from "antd"; +import { OverlayScrollbarsComponent } from "overlayscrollbars-react"; import { useMaterial } from "../../../shared/hooks/use-materials"; -import { STATUS_MAP } from "./constants"; import { MaterialContent } from "./MaterialContent"; +const OS_OPTIONS = { + overflow: { x: "hidden", y: "scroll" }, + scrollbars: { autoHide: "move", theme: "os-theme-custom" }, +} as const; + interface MaterialDetailPanelProps { materialId: null | string; onApprove: (materialId: string) => Promise; @@ -23,8 +29,13 @@ export function MaterialDetailPanel({ if (!materialId) { return (
-
+ + +
+ + 请先选择素材 +
); @@ -48,9 +59,9 @@ function MaterialDetailPanelInner({ materialId, onApprove, onDiscard, onRetry, p if (isLoading) { return (
-
+ -
+
); } @@ -58,9 +69,9 @@ function MaterialDetailPanelInner({ materialId, onApprove, onDiscard, onRetry, p if (error) { return (
-
+ -
+
); } @@ -68,9 +79,9 @@ function MaterialDetailPanelInner({ materialId, onApprove, onDiscard, onRetry, p if (!data || !materialId) { return (
-
+ -
+
); } @@ -104,31 +115,39 @@ function MaterialDetailPanelInner({ materialId, onApprove, onDiscard, onRetry, p } }; - const statusInfo = STATUS_MAP[data.status] ?? { color: "default", label: data.status }; - return (
-
+ -
+
- {statusInfo.label} - {data.status === "review" ? ( - - - - - ) : data.status === "failed" ? ( - - - - ) : null} + + + + +
); diff --git a/src/web/styles.css b/src/web/styles.css index 393602f..d62c87d 100644 --- a/src/web/styles.css +++ b/src/web/styles.css @@ -334,6 +334,7 @@ body { .app-inbox-page { display: flex; + gap: var(--ant-margin-sm); height: 100%; overflow: hidden; } @@ -342,6 +343,7 @@ body { display: flex; flex: 1; flex-direction: column; + gap: var(--ant-margin-sm); min-height: 0; min-width: 0; } @@ -349,17 +351,17 @@ body { .app-inbox-content { flex: 1; min-height: 0; - padding: var(--ant-padding-xl); - overflow-y: auto; + overflow: hidden; } .app-inbox-action-bar { display: flex; flex-shrink: 0; align-items: center; - justify-content: space-between; - padding: var(--ant-padding-sm) var(--ant-padding-xl); - border-top: 1px solid var(--ant-color-border-secondary); + justify-content: flex-end; + padding: var(--ant-padding-sm); + border: 1px solid var(--ant-color-border-secondary); + border-radius: var(--ant-border-radius-lg); background: var(--ant-color-bg-container); }