From 237b8b4389d576fa6a3af91e2f1b1d0b8d37be77 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8C=97=E6=9E=B3?= <7854742+wang_rumeng@user.noreply.gitee.com> Date: Thu, 11 Sep 2025 20:04:04 +0800 Subject: [PATCH] =?UTF-8?q?=E5=89=AA=E8=BE=91=20=E6=9C=80=E5=90=8E?= =?UTF-8?q?=E4=B8=80=E6=AC=A1=E4=BF=AE=E6=94=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- api/DTO/movieEdit.ts | 4 +- components/pages/work-flow.tsx | 85 ++++++++++++++++--- .../pages/work-flow/ai-editing-iframe.tsx | 4 + .../pages/work-flow/editing-notification.tsx | 23 +++-- .../pages/work-flow/use-workflow-data.tsx | 41 ++++++--- 5 files changed, 125 insertions(+), 32 deletions(-) diff --git a/api/DTO/movieEdit.ts b/api/DTO/movieEdit.ts index aa61fde..c7681f2 100644 --- a/api/DTO/movieEdit.ts +++ b/api/DTO/movieEdit.ts @@ -670,8 +670,8 @@ export const LOADING_TEXT_MAP = { postProduction: (step: string) => `Post-production: ${step}...`, final: 'Generating final product...', complete: 'Task completed', - toManyFailed: 'Too many failed storyboards, Please click the edit button to go to the intelligent editing platform.', - editingError: 'Editing failed. Please refresh the page and try again.' + toManyFailed: 'Too many failed storyboards, Please click the scissors button to go to the intelligent editing platform.', + editingError: 'Editing failed. Please click the scissors button to go to the intelligent editing platform.' } as const; export type Status = 'IN_PROGRESS' | 'COMPLETED' | 'FAILED'; diff --git a/components/pages/work-flow.tsx b/components/pages/work-flow.tsx index 8678743..793f632 100644 --- a/components/pages/work-flow.tsx +++ b/components/pages/work-flow.tsx @@ -41,6 +41,9 @@ const WorkFlow = React.memo(function WorkFlow() { const [aiEditingResult, setAiEditingResult] = React.useState(null); const aiEditingButtonRef = useRef<{ handleAIEditing: () => Promise }>(null); const [editingStatus, setEditingStatus] = React.useState<'initial' | 'idle' | 'success' | 'error'>('initial'); + const [iframeAiEditingKey, setIframeAiEditingKey] = React.useState(`iframe-ai-editing-${Date.now()}`); + const [isEditingInProgress, setIsEditingInProgress] = React.useState(false); + const isEditingInProgressRef = useRef(false); const searchParams = useSearchParams(); const episodeId = searchParams.get('episodeId') || ''; @@ -52,30 +55,81 @@ const WorkFlow = React.memo(function WorkFlow() { const [isHandleEdit, setIsHandleEdit] = React.useState(false); // 处理编辑计划生成完成的回调 const handleEditPlanGenerated = useCallback(() => { + console.log('🚀 handleEditPlanGenerated called, current ref:', isEditingInProgressRef.current); + + // 防止重复调用 - 使用 ref 避免依赖项变化 + if (isEditingInProgressRef.current) { + console.log('⚠️ 编辑已在进行中,跳过重复调用'); + return; + } + console.log('✨ 编辑计划生成完成,开始AI剪辑'); setIsHandleEdit(true); setEditingStatus('idle'); + setIsEditingInProgress(true); + isEditingInProgressRef.current = true; + aiEditingButtonRef.current?.handleAIEditing(); editingNotificationKey.current = `editing-${Date.now()}`; showEditingNotification({ description: 'Performing intelligent editing...', successDescription: 'Editing successful', - timeoutDescription: 'Editing failed. Please click the edit button to go to the smart editing platform.', + timeoutDescription: 'Editing failed. Please click the scissors button to go to the intelligent editing platform.', timeout: 8 * 60 * 1000, key: editingNotificationKey.current, onFail: () => { - console.log('Editing failed'); + console.log('❌ onFail callback triggered - Editing failed, retrying...'); // 清缓存 生成计划 视频重新分析 localStorage.removeItem(`isLoaded_plan_${episodeId}`); - // 3秒后关闭通知 + + // 先销毁当前通知 + if (editingNotificationKey.current) { + notification.destroy(editingNotificationKey.current); + } + + // 重新生成 iframeAiEditingKey 触发重新渲染 + setIframeAiEditingKey(`iframe-ai-editing-${Date.now()}`); + + // 延时200ms后显示重试通知,确保之前的通知已销毁 setTimeout(() => { - setEditingStatus('error'); - if (editingNotificationKey.current) { - notification.destroy(editingNotificationKey.current); - } - }, 3000); + editingNotificationKey.current = `editing-${Date.now()}`; + showEditingNotification({ + description: 'Retry intelligent editing...', + successDescription: 'Editing successful', + timeoutDescription: 'Editing failed. Please click the scissors button to go to the intelligent editing platform.', + timeout: 5 * 60 * 1000, // 5分钟超时 + key: editingNotificationKey.current, + onFail: () => { + console.log('Editing retry failed'); + // 清缓存 + localStorage.removeItem(`isLoaded_plan_${episodeId}`); + // 5秒后关闭通知并设置错误状态 + setTimeout(() => { + setEditingStatus('error'); + setIsEditingInProgress(false); // 重置编辑状态 + isEditingInProgressRef.current = false; // 重置 ref + if (editingNotificationKey.current) { + notification.destroy(editingNotificationKey.current); + } + }, 5000); + } + }); + }, 200); } }); + }, [episodeId]); // 移除 isEditingInProgress 依赖 + + /** 处理导出失败 */ + const handleExportFailed = useCallback(() => { + console.log('Export failed, setting error status'); + setEditingStatus('error'); + setIsEditingInProgress(false); + isEditingInProgressRef.current = false; + + // 销毁当前编辑通知 + if (editingNotificationKey.current) { + notification.destroy(editingNotificationKey.current); + } }, []); // 使用自定义 hooks 管理状态 @@ -99,7 +153,8 @@ const WorkFlow = React.memo(function WorkFlow() { isShowAutoEditing } = useWorkflowData({ onEditPlanGenerated: handleEditPlanGenerated, - editingStatus: editingStatus + editingStatus: editingStatus, + onExportFailed: handleExportFailed }); const { @@ -113,7 +168,14 @@ const WorkFlow = React.memo(function WorkFlow() { // 监听粗剪是否完成,如果完成 更新 showEditingNotification 的状态 为完成,延时 3s 并关闭 useEffect(() => { + console.log('🎬 final video useEffect triggered:', { + finalUrl: taskObject.final.url, + notificationKey: editingNotificationKey.current, + isHandleEdit + }); + if (taskObject.final.url && editingNotificationKey.current && isHandleEdit) { + console.log('🎉 显示编辑完成通知'); // 更新通知状态为完成 showEditingNotification({ isCompleted: true, @@ -126,6 +188,8 @@ const WorkFlow = React.memo(function WorkFlow() { console.log('Editing successful'); localStorage.setItem(`isLoaded_plan_${episodeId}`, 'true'); setEditingStatus('success'); + setIsEditingInProgress(false); // 重置编辑状态 + isEditingInProgressRef.current = false; // 重置 ref // 3秒后关闭通知 setTimeout(() => { if (editingNotificationKey.current) { @@ -135,7 +199,7 @@ const WorkFlow = React.memo(function WorkFlow() { }, }); } - }, [taskObject.final, isHandleEdit]); + }, [taskObject.final, isHandleEdit, episodeId]); const handleEditModalOpen = useCallback((tab: string) => { setActiveEditTab(tab); @@ -266,6 +330,7 @@ const WorkFlow = React.memo(function WorkFlow() {
((props, ref) => { const { + key, projectId, token, userId, @@ -418,6 +421,7 @@ export const AIEditingIframe = React.forwardRef