diff --git a/apps/desktop/src/pages/ProjectDetails.tsx b/apps/desktop/src/pages/ProjectDetails.tsx index c3ff2a5..6042f14 100644 --- a/apps/desktop/src/pages/ProjectDetails.tsx +++ b/apps/desktop/src/pages/ProjectDetails.tsx @@ -31,6 +31,8 @@ import { MaterialMatchingResult, MaterialMatchingRequest } from '../types/materi import { MaterialSegmentView } from '../components/MaterialSegmentView'; import { formatDistanceToNow } from 'date-fns'; import { zhCN } from 'date-fns/locale'; +import { MaterialSegmentStats } from '../components/MaterialSegmentStats'; +import { MaterialSegmentViewMode } from '../types/materialSegmentView'; // 格式化时间 const formatTime = (dateString: string) => { @@ -105,15 +107,37 @@ export const ProjectDetails: React.FC = () => { const [editingBinding, setEditingBinding] = useState(null); const [showMaterialEditDialog, setShowMaterialEditDialog] = useState(false); const [editingMaterial, setEditingMaterial] = useState(null); - const [activeTab, setActiveTab] = useState<'materials' | 'segments' | 'templates' | 'debug' | 'ai-logs'>('materials'); + const [activeTab, setActiveTab] = useState<'overview' | 'materials' | 'segments' | 'templates' | 'ai-logs'>('overview'); const [_batchClassificationResult, setBatchClassificationResult] = useState(null); // 素材匹配状态 const [showMatchingResultDialog, setShowMatchingResultDialog] = useState(false); const [matchingResult, setMatchingResult] = useState(null); const [matchingLoading, setMatchingLoading] = useState(false); + const [segmentStats, setSegmentStats] = useState(null); const [currentMatchingBinding, setCurrentMatchingBinding] = useState(null); + // 加载片段统计数据 + const loadSegmentStats = async (projectId: string) => { + try { + const stats = await invoke('get_material_segment_stats', { projectId }); + setSegmentStats(stats); + } catch (error) { + console.error('Failed to load segment stats:', error); + // 设置默认统计数据 + setSegmentStats({ + total_segments: 0, + total_duration: 0, + classified_segments: 0, + classification_coverage: 0, + by_classification: {}, + by_model: {}, + by_duration_range: {}, + avg_segment_duration: 0 + }); + } + }; + // 加载项目详情 useEffect(() => { if (!projects.length) { @@ -133,9 +157,11 @@ export const ProjectDetails: React.FC = () => { loadMaterialStats(foundProject.id); // 加载项目的模板绑定 bindingActions.fetchTemplatesByProject(foundProject.id); + // 加载片段统计数据 + loadSegmentStats(foundProject.id); } } - }, [id, projects, loadMaterials, loadMaterialStats, bindingActions]); + }, [id, projects, loadMaterials, loadMaterialStats, bindingActions, loadSegmentStats]); // 加载模板列表 useEffect(() => { @@ -526,88 +552,7 @@ export const ProjectDetails: React.FC = () => { - {/* 美观的项目统计概览 */} -
- {/* 总素材数 */} -
-
-
-
-

总素材数

-

{stats?.total_materials || 0}

-
-
- -
-
-
- {/* 视频文件 */} -
-
-
-
-

视频文件

-

{stats?.video_count || 0}

-
-
- -
-
-
- - {/* 音频文件 */} -
-
-
-
-

音频文件

-

{stats?.audio_count || 0}

-
-
- -
-
-
- - {/* 图片文件 */} -
-
-
-
-

图片文件

-

{stats?.image_count || 0}

-
-
- -
-
-
- - {/* AI分类状态 */} -
-
-
-
-

AI分类队列

-
-

- {queueStats?.pending_tasks || 0} -

- 待处理 -
- {queueStats?.processing_tasks && queueStats.processing_tasks > 0 && ( -

- {queueStats.processing_tasks} 个正在处理 -

- )} -
-
- -
-
-
-
{/* 主要内容区域 */}
@@ -615,6 +560,20 @@ export const ProjectDetails: React.FC = () => {
{/* 选项卡内容 */} -
+
+ {/* 项目概述选项卡 */} + {activeTab === 'overview' && ( +
+ {/* 项目统计概览 */} +
+

项目统计

+
+ {/* 总素材数 */} +
+
+
+
+

总素材数

+

{stats?.total_materials || 0}

+
+
+ +
+
+
+ + {/* 视频文件 */} +
+
+
+
+

视频文件

+

{stats?.video_count || 0}

+
+
+ +
+
+
+ + {/* 音频文件 */} +
+
+
+
+

音频文件

+

{stats?.audio_count || 0}

+
+
+ +
+
+
+ + {/* 图片文件 */} +
+
+
+
+

图片文件

+

{stats?.image_count || 0}

+
+
+ +
+
+
+ + {/* AI分类状态 */} +
+
+
+
+

AI分类队列

+
+

+ {queueStats?.pending_tasks || 0} +

+ 待处理 +
+ {queueStats?.processing_tasks && queueStats.processing_tasks > 0 && ( +

+ {queueStats.processing_tasks} 个正在处理 +

+ )} +
+
+ +
+
+
+
+
+ + {/* 片段管理统计 */} + {project && ( +
+

片段统计

+ +
+ )} + + {/* AI视频分类进度 */} + {project && ( +
+

AI分析进度

+ +
+ )} + + {/* 项目信息 */} +
+

项目信息

+
+
+ 项目路径 + + {project?.path} + +
+
+ 创建时间 + + {project?.created_at ? formatTime(project.created_at) : '-'} + +
+
+ 最后更新 + + {project?.updated_at ? formatTime(project.updated_at) : '-'} + +
+
+
+
+ )} + {/* 素材管理选项卡 */} {activeTab === 'materials' && ( -
+
{/* AI视频分类进度 */} {project && ( { {/* 片段管理选项卡 */} {activeTab === 'segments' && project && ( -
+
)} {/* 模板绑定选项卡 */} {activeTab === 'templates' && project && ( -
+

模板绑定管理

@@ -794,7 +892,7 @@ export const ProjectDetails: React.FC = () => { {/* AI分析日志选项卡 */} {activeTab === 'ai-logs' && project && ( -
+

AI分析日志