抽出编辑器生成对话状态模型
新增 ImageCanvasGenerationDialogModel 承载生成面板草稿和引用选择规则 补充生成对话状态模型单测 精简 useImageCanvasGenerationWorkflow 中的面板状态构造 更新 TRACKING.md 记录第四十一阶段验证
This commit is contained in:
@@ -1,54 +1,22 @@
|
||||
import {
|
||||
useCallback,
|
||||
useMemo,
|
||||
useState,
|
||||
type Dispatch,
|
||||
type MutableRefObject,
|
||||
type SetStateAction,
|
||||
useCallback,
|
||||
useMemo,
|
||||
useState,
|
||||
} from 'react';
|
||||
|
||||
import { resolveEditorImageReferenceDataUrl } from '../../services/image-editor/editorImageReference';
|
||||
import {
|
||||
editEditorImage,
|
||||
generateEditorCharacterAnimation,
|
||||
generateEditorIconSpritesheet,
|
||||
generateEditorImage,
|
||||
type EditorIconSpritesheetGenerationResult,
|
||||
type EditorIconSpritesheetIconResult,
|
||||
type EditorImageGenerationResult,
|
||||
generateEditorCharacterAnimation,
|
||||
generateEditorIconSpritesheet,
|
||||
generateEditorImage,
|
||||
} from '../../services/image-editor/editorProjectClient';
|
||||
import {
|
||||
createGeneratedResultLayer,
|
||||
createIconSpritesheetResultLayers,
|
||||
createQuickEditResultLayer,
|
||||
} from './ImageCanvasGenerationLayerModel';
|
||||
import {
|
||||
CHARACTER_ANIMATION_DURATION_OPTIONS,
|
||||
CHARACTER_FRAME_DISPLAY_SIZE,
|
||||
CHARACTER_FRAME_ORIGINAL_SIZE,
|
||||
DEFAULT_ICON_DESCRIPTIONS,
|
||||
DEFAULT_IMAGE_MODEL,
|
||||
DEFAULT_SPEC_FORM_VALUES,
|
||||
EDITOR_IMAGE_DIMENSION_OPTIONS,
|
||||
ICON_DESCRIPTION_LIMIT,
|
||||
ICON_FRAME_DISPLAY_SIZE,
|
||||
ICON_FRAME_ORIGINAL_SIZE,
|
||||
SPEC_FRAME_DISPLAY_SIZE,
|
||||
SPEC_FRAME_ORIGINAL_SIZE,
|
||||
buildEditGenerationInputs,
|
||||
buildQuickEditModelOptions,
|
||||
buildQuickEditSizeOptions,
|
||||
calculateCharacterAnimationPrice,
|
||||
createCanvasLayerReference,
|
||||
isCanvasGenerationDialog,
|
||||
resolveImageGenerationErrorMessage,
|
||||
} from './ImageCanvasGenerationModel';
|
||||
import {
|
||||
buildCharacterAnimationSubmissionPlan,
|
||||
buildIconSpritesheetGenerationSubmissionPlan,
|
||||
buildImageGenerationSubmissionPlan,
|
||||
} from './ImageCanvasGenerationSubmissionModel';
|
||||
import { formatImageSizeValue } from './ImageCanvasEditorModel';
|
||||
import type {
|
||||
CanvasGenerationDialogState,
|
||||
CanvasGenerationInputs,
|
||||
@@ -63,6 +31,44 @@ import type {
|
||||
SpecFormValues,
|
||||
SpecGenerationType,
|
||||
} from './ImageCanvasEditorTypes';
|
||||
import {
|
||||
appendCharacterReference,
|
||||
appendIconDescriptionToDialog,
|
||||
assignCharacterSpecReference,
|
||||
assignIconSpecReference,
|
||||
closeGenerateComposerDialog,
|
||||
createCharacterAnimationPanelDraft,
|
||||
createCharacterGenerationDialogDraft,
|
||||
createEditDialogDraft,
|
||||
createGenerateDialogDraft,
|
||||
createIconGenerationDialogDraft,
|
||||
createQuickEditPanelDraft,
|
||||
createSpecDialogDraft,
|
||||
hideGeneratedLayerComposerAfterBlur,
|
||||
updateCharacterAnimationDurationPanel,
|
||||
updateIconDescriptionInDialog,
|
||||
updateSpecFormDialogValue,
|
||||
} from './ImageCanvasGenerationDialogModel';
|
||||
import {
|
||||
createGeneratedResultLayer,
|
||||
createIconSpritesheetResultLayers,
|
||||
createQuickEditResultLayer,
|
||||
} from './ImageCanvasGenerationLayerModel';
|
||||
import {
|
||||
buildEditGenerationInputs,
|
||||
buildQuickEditModelOptions,
|
||||
buildQuickEditSizeOptions,
|
||||
calculateCharacterAnimationPrice,
|
||||
DEFAULT_ICON_DESCRIPTIONS,
|
||||
DEFAULT_IMAGE_MODEL,
|
||||
isCanvasGenerationDialog,
|
||||
resolveImageGenerationErrorMessage,
|
||||
} from './ImageCanvasGenerationModel';
|
||||
import {
|
||||
buildCharacterAnimationSubmissionPlan,
|
||||
buildIconSpritesheetGenerationSubmissionPlan,
|
||||
buildImageGenerationSubmissionPlan,
|
||||
} from './ImageCanvasGenerationSubmissionModel';
|
||||
|
||||
type CanvasSize = { width: number; height: number };
|
||||
|
||||
@@ -98,36 +104,6 @@ type GenerationWorkflowOptions = {
|
||||
setImageContextMenu: Dispatch<SetStateAction<ImageContextMenuState | null>>;
|
||||
};
|
||||
|
||||
function getViewportWorldCenter({
|
||||
canvasSize,
|
||||
viewport,
|
||||
}: {
|
||||
canvasSize: CanvasSize;
|
||||
viewport: CanvasViewport;
|
||||
}) {
|
||||
const safeScale = viewport.scale > 0 ? viewport.scale : 1;
|
||||
return {
|
||||
x: (canvasSize.width / 2 - viewport.x) / safeScale,
|
||||
y: (canvasSize.height / 2 - viewport.y) / safeScale,
|
||||
};
|
||||
}
|
||||
|
||||
function setFailedCharacterGenerationIdle(dialog: GenerateDialogState) {
|
||||
return {
|
||||
...dialog,
|
||||
status: dialog.status === 'failed' ? 'idle' : dialog.status,
|
||||
errorMessage: dialog.status === 'failed' ? undefined : dialog.errorMessage,
|
||||
};
|
||||
}
|
||||
|
||||
function setFailedIconGenerationIdle(dialog: GenerateDialogState) {
|
||||
return {
|
||||
...dialog,
|
||||
status: dialog.status === 'failed' ? 'idle' : dialog.status,
|
||||
errorMessage: dialog.status === 'failed' ? undefined : dialog.errorMessage,
|
||||
};
|
||||
}
|
||||
|
||||
export function useImageCanvasGenerationWorkflow({
|
||||
layers,
|
||||
canvasSize,
|
||||
@@ -149,8 +125,7 @@ export function useImageCanvasGenerationWorkflow({
|
||||
setImageContextMenu,
|
||||
}: GenerationWorkflowOptions) {
|
||||
const [isSpecMenuOpen, setIsSpecMenuOpen] = useState(false);
|
||||
const [isCharacterSpecMenuOpen, setIsCharacterSpecMenuOpen] =
|
||||
useState(false);
|
||||
const [isCharacterSpecMenuOpen, setIsCharacterSpecMenuOpen] = useState(false);
|
||||
const [isCharacterReferenceMenuOpen, setIsCharacterReferenceMenuOpen] =
|
||||
useState(false);
|
||||
const [
|
||||
@@ -179,12 +154,16 @@ export function useImageCanvasGenerationWorkflow({
|
||||
(layer) => layer.id === characterAnimationPanel.sourceLayerId,
|
||||
) ?? null)
|
||||
: null;
|
||||
const quickEditSizeOptions = quickEditPanel
|
||||
? buildQuickEditSizeOptions(quickEditPanel.size)
|
||||
: [];
|
||||
const quickEditModelOptions = quickEditPanel
|
||||
? buildQuickEditModelOptions(quickEditPanel.model)
|
||||
: [];
|
||||
const quickEditSizeOptions = useMemo(
|
||||
() =>
|
||||
quickEditPanel ? buildQuickEditSizeOptions(quickEditPanel.size) : [],
|
||||
[quickEditPanel],
|
||||
);
|
||||
const quickEditModelOptions = useMemo(
|
||||
() =>
|
||||
quickEditPanel ? buildQuickEditModelOptions(quickEditPanel.model) : [],
|
||||
[quickEditPanel],
|
||||
);
|
||||
const characterAnimationPrice = characterAnimationPanel
|
||||
? calculateCharacterAnimationPrice(
|
||||
characterAnimationPanel.resolution,
|
||||
@@ -197,23 +176,9 @@ export function useImageCanvasGenerationWorkflow({
|
||||
: DEFAULT_ICON_DESCRIPTIONS;
|
||||
|
||||
const openGenerateDialog = useCallback(() => {
|
||||
const placeholderWidth = 420;
|
||||
const placeholderHeight = 420;
|
||||
const worldCenter = getViewportWorldCenter({ canvasSize, viewport });
|
||||
openCanvasGenerationDialog({
|
||||
mode: 'generate',
|
||||
prompt: '',
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
placeholder: {
|
||||
x: worldCenter.x - placeholderWidth / 2,
|
||||
y: worldCenter.y - placeholderHeight / 2,
|
||||
width: placeholderWidth,
|
||||
height: placeholderHeight,
|
||||
originalWidth: 2048,
|
||||
originalHeight: 2048,
|
||||
},
|
||||
});
|
||||
openCanvasGenerationDialog(
|
||||
createGenerateDialogDraft({ canvasSize, viewport }),
|
||||
);
|
||||
setActiveTool('generate');
|
||||
selectSingleLayer(null);
|
||||
setQuickEditPanel(null);
|
||||
@@ -227,23 +192,9 @@ export function useImageCanvasGenerationWorkflow({
|
||||
|
||||
const openSpecDialog = useCallback(
|
||||
(specType: SpecGenerationType) => {
|
||||
const worldCenter = getViewportWorldCenter({ canvasSize, viewport });
|
||||
openCanvasGenerationDialog({
|
||||
mode: 'spec',
|
||||
prompt: '',
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
specType,
|
||||
specValues: { ...DEFAULT_SPEC_FORM_VALUES[specType] },
|
||||
placeholder: {
|
||||
x: worldCenter.x - SPEC_FRAME_DISPLAY_SIZE.width / 2,
|
||||
y: worldCenter.y - SPEC_FRAME_DISPLAY_SIZE.height / 2,
|
||||
width: SPEC_FRAME_DISPLAY_SIZE.width,
|
||||
height: SPEC_FRAME_DISPLAY_SIZE.height,
|
||||
originalWidth: SPEC_FRAME_ORIGINAL_SIZE.width,
|
||||
originalHeight: SPEC_FRAME_ORIGINAL_SIZE.height,
|
||||
},
|
||||
});
|
||||
openCanvasGenerationDialog(
|
||||
createSpecDialogDraft({ canvasSize, viewport, specType }),
|
||||
);
|
||||
setIsSpecMenuOpen(false);
|
||||
setActiveTool('generate');
|
||||
selectSingleLayer(null);
|
||||
@@ -260,56 +211,30 @@ export function useImageCanvasGenerationWorkflow({
|
||||
|
||||
const openCharacterAnimationPanel = useCallback(
|
||||
(layer: CanvasLayer) => {
|
||||
if (layer.assetKind !== 'character') {
|
||||
const nextPanel = createCharacterAnimationPanelDraft(layer);
|
||||
if (!nextPanel) {
|
||||
return;
|
||||
}
|
||||
setImageContextMenu(null);
|
||||
setQuickEditPanel(null);
|
||||
setCharacterAnimationPanel({
|
||||
sourceLayerId: layer.id,
|
||||
promptText: '',
|
||||
resolution: '480p',
|
||||
ratio: 'same',
|
||||
frameCount: 32,
|
||||
durationSeconds: 4,
|
||||
status: 'idle',
|
||||
});
|
||||
setCharacterAnimationPanel(nextPanel);
|
||||
selectSingleLayer(layer.id);
|
||||
},
|
||||
[selectSingleLayer, setImageContextMenu],
|
||||
);
|
||||
|
||||
const openCharacterGenerationDialog = useCallback(() => {
|
||||
const worldCenter = getViewportWorldCenter({ canvasSize, viewport });
|
||||
setIsSpecMenuOpen(false);
|
||||
setIsCharacterReferenceMenuOpen(false);
|
||||
setIsPickingCharacterSpecFromCanvas(false);
|
||||
setIsPickingCharacterReferenceFromCanvas(false);
|
||||
const dimensionOptions =
|
||||
EDITOR_IMAGE_DIMENSION_OPTIONS[
|
||||
lastImageModel as keyof typeof EDITOR_IMAGE_DIMENSION_OPTIONS
|
||||
] ?? EDITOR_IMAGE_DIMENSION_OPTIONS[DEFAULT_IMAGE_MODEL];
|
||||
openCanvasGenerationDialog({
|
||||
mode: 'character',
|
||||
prompt: '',
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
characterSpecReference: null,
|
||||
characterReferences: [],
|
||||
imageModel: lastImageModel,
|
||||
aspectRatio: dimensionOptions.aspectRatios[0],
|
||||
imageSize:
|
||||
dimensionOptions.imageSizes.find((size) => size === '1K') ??
|
||||
dimensionOptions.imageSizes[0],
|
||||
placeholder: {
|
||||
x: worldCenter.x - CHARACTER_FRAME_DISPLAY_SIZE.width / 2,
|
||||
y: worldCenter.y - CHARACTER_FRAME_DISPLAY_SIZE.height / 2,
|
||||
width: CHARACTER_FRAME_DISPLAY_SIZE.width,
|
||||
height: CHARACTER_FRAME_DISPLAY_SIZE.height,
|
||||
originalWidth: CHARACTER_FRAME_ORIGINAL_SIZE.width,
|
||||
originalHeight: CHARACTER_FRAME_ORIGINAL_SIZE.height,
|
||||
},
|
||||
});
|
||||
openCanvasGenerationDialog(
|
||||
createCharacterGenerationDialogDraft({
|
||||
canvasSize,
|
||||
viewport,
|
||||
imageModel: lastImageModel,
|
||||
}),
|
||||
);
|
||||
setActiveTool('character');
|
||||
selectSingleLayer(null);
|
||||
setQuickEditPanel(null);
|
||||
@@ -323,37 +248,18 @@ export function useImageCanvasGenerationWorkflow({
|
||||
]);
|
||||
|
||||
const openIconGenerationDialog = useCallback(() => {
|
||||
const worldCenter = getViewportWorldCenter({ canvasSize, viewport });
|
||||
setIsSpecMenuOpen(false);
|
||||
setIsCharacterReferenceMenuOpen(false);
|
||||
setIsPickingCharacterSpecFromCanvas(false);
|
||||
setIsPickingCharacterReferenceFromCanvas(false);
|
||||
setIsPickingIconSpecFromCanvas(false);
|
||||
const dimensionOptions =
|
||||
EDITOR_IMAGE_DIMENSION_OPTIONS[
|
||||
lastImageModel as keyof typeof EDITOR_IMAGE_DIMENSION_OPTIONS
|
||||
] ?? EDITOR_IMAGE_DIMENSION_OPTIONS[DEFAULT_IMAGE_MODEL];
|
||||
openCanvasGenerationDialog({
|
||||
mode: 'icon',
|
||||
prompt: '',
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
iconSpecReference: null,
|
||||
iconDescriptions: [...DEFAULT_ICON_DESCRIPTIONS],
|
||||
imageModel: lastImageModel,
|
||||
aspectRatio: dimensionOptions.aspectRatios[0],
|
||||
imageSize:
|
||||
dimensionOptions.imageSizes.find((size) => size === '1K') ??
|
||||
dimensionOptions.imageSizes[0],
|
||||
placeholder: {
|
||||
x: worldCenter.x - ICON_FRAME_DISPLAY_SIZE.width / 2,
|
||||
y: worldCenter.y - ICON_FRAME_DISPLAY_SIZE.height / 2,
|
||||
width: ICON_FRAME_DISPLAY_SIZE.width,
|
||||
height: ICON_FRAME_DISPLAY_SIZE.height,
|
||||
originalWidth: ICON_FRAME_ORIGINAL_SIZE.width,
|
||||
originalHeight: ICON_FRAME_ORIGINAL_SIZE.height,
|
||||
},
|
||||
});
|
||||
openCanvasGenerationDialog(
|
||||
createIconGenerationDialogDraft({
|
||||
canvasSize,
|
||||
viewport,
|
||||
imageModel: lastImageModel,
|
||||
}),
|
||||
);
|
||||
setActiveTool('icon');
|
||||
selectSingleLayer(null);
|
||||
setQuickEditPanel(null);
|
||||
@@ -372,15 +278,7 @@ export function useImageCanvasGenerationWorkflow({
|
||||
setMetadataLayer(null);
|
||||
setImageContextMenu(null);
|
||||
setQuickEditPanel(null);
|
||||
setGenerateDialog({
|
||||
mode: 'edit',
|
||||
prompt: sourceLayer.prompt
|
||||
? `${sourceLayer.prompt},在保持主体结构的基础上优化画面细节`
|
||||
: '',
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
sourceLayerId: sourceLayer.id,
|
||||
});
|
||||
setGenerateDialog(createEditDialogDraft(sourceLayer));
|
||||
setActiveTool('generate');
|
||||
},
|
||||
[setActiveTool, setGenerateDialog, setImageContextMenu, setMetadataLayer],
|
||||
@@ -392,16 +290,7 @@ export function useImageCanvasGenerationWorkflow({
|
||||
setMetadataLayer(null);
|
||||
setGenerateDialog(null);
|
||||
setCharacterAnimationPanel(null);
|
||||
setQuickEditPanel({
|
||||
sourceLayerId: sourceLayer.id,
|
||||
prompt: '',
|
||||
size: formatImageSizeValue(
|
||||
sourceLayer.originalWidth,
|
||||
sourceLayer.originalHeight,
|
||||
),
|
||||
model: sourceLayer.model?.trim() || DEFAULT_IMAGE_MODEL,
|
||||
status: 'idle',
|
||||
});
|
||||
setQuickEditPanel(createQuickEditPanelDraft(sourceLayer));
|
||||
selectSingleLayer(sourceLayer.id);
|
||||
setActiveTool('generate');
|
||||
},
|
||||
@@ -556,13 +445,7 @@ export function useImageCanvasGenerationWorkflow({
|
||||
const pickCharacterSpecFromLayer = useCallback(
|
||||
(layer: CanvasLayer) => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
currentDialog?.mode === 'character'
|
||||
? {
|
||||
...setFailedCharacterGenerationIdle(currentDialog),
|
||||
characterSpecReference: createCanvasLayerReference(layer),
|
||||
composerOpen: true,
|
||||
}
|
||||
: currentDialog,
|
||||
assignCharacterSpecReference(currentDialog, layer),
|
||||
);
|
||||
setIsPickingCharacterSpecFromCanvas(false);
|
||||
setIsCharacterSpecMenuOpen(false);
|
||||
@@ -574,16 +457,7 @@ export function useImageCanvasGenerationWorkflow({
|
||||
const pickCharacterReferenceFromLayer = useCallback(
|
||||
(layer: CanvasLayer) => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
currentDialog?.mode === 'character'
|
||||
? {
|
||||
...setFailedCharacterGenerationIdle(currentDialog),
|
||||
characterReferences: [
|
||||
...(currentDialog.characterReferences ?? []),
|
||||
createCanvasLayerReference(layer),
|
||||
],
|
||||
composerOpen: true,
|
||||
}
|
||||
: currentDialog,
|
||||
appendCharacterReference(currentDialog, layer),
|
||||
);
|
||||
setIsPickingCharacterReferenceFromCanvas(false);
|
||||
setImageContextMenu(null);
|
||||
@@ -593,18 +467,12 @@ export function useImageCanvasGenerationWorkflow({
|
||||
|
||||
const pickIconSpecFromLayer = useCallback(
|
||||
(layer: CanvasLayer) => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
assignIconSpecReference(currentDialog, layer),
|
||||
);
|
||||
if (layer.assetKind !== 'icon-spec') {
|
||||
return;
|
||||
}
|
||||
setGenerateDialog((currentDialog) =>
|
||||
currentDialog?.mode === 'icon'
|
||||
? {
|
||||
...setFailedIconGenerationIdle(currentDialog),
|
||||
iconSpecReference: createCanvasLayerReference(layer),
|
||||
composerOpen: true,
|
||||
}
|
||||
: currentDialog,
|
||||
);
|
||||
setIsPickingIconSpecFromCanvas(false);
|
||||
setIsIconSpecMenuOpen(false);
|
||||
setImageContextMenu(null);
|
||||
@@ -615,36 +483,14 @@ export function useImageCanvasGenerationWorkflow({
|
||||
const updateIconDescription = useCallback(
|
||||
(index: number, value: string) => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
currentDialog?.mode === 'icon'
|
||||
? {
|
||||
...setFailedIconGenerationIdle(currentDialog),
|
||||
iconDescriptions: (
|
||||
currentDialog.iconDescriptions ?? DEFAULT_ICON_DESCRIPTIONS
|
||||
).map((description, descriptionIndex) =>
|
||||
descriptionIndex === index ? value : description,
|
||||
),
|
||||
}
|
||||
: currentDialog,
|
||||
updateIconDescriptionInDialog(currentDialog, index, value),
|
||||
);
|
||||
},
|
||||
[setGenerateDialog],
|
||||
);
|
||||
|
||||
const addIconDescription = useCallback(() => {
|
||||
setGenerateDialog((currentDialog) => {
|
||||
if (currentDialog?.mode !== 'icon') {
|
||||
return currentDialog;
|
||||
}
|
||||
const descriptions =
|
||||
currentDialog.iconDescriptions ?? DEFAULT_ICON_DESCRIPTIONS;
|
||||
if (descriptions.length >= ICON_DESCRIPTION_LIMIT) {
|
||||
return currentDialog;
|
||||
}
|
||||
return {
|
||||
...setFailedIconGenerationIdle(currentDialog),
|
||||
iconDescriptions: [...descriptions, ''],
|
||||
};
|
||||
});
|
||||
setGenerateDialog(appendIconDescriptionToDialog);
|
||||
}, [setGenerateDialog]);
|
||||
|
||||
const submitIconSpritesheetGeneration = useCallback(
|
||||
@@ -841,52 +687,17 @@ export function useImageCanvasGenerationWorkflow({
|
||||
|
||||
const updateSpecFormValue = useCallback(
|
||||
(key: keyof SpecFormValues, value: string) => {
|
||||
setGenerateDialog((currentDialog) => {
|
||||
if (currentDialog?.mode !== 'spec') {
|
||||
return currentDialog;
|
||||
}
|
||||
const specType = currentDialog.specType ?? 'custom';
|
||||
return {
|
||||
...currentDialog,
|
||||
specValues: {
|
||||
...DEFAULT_SPEC_FORM_VALUES[specType],
|
||||
...currentDialog.specValues,
|
||||
[key]: value,
|
||||
},
|
||||
status:
|
||||
currentDialog.status === 'failed' ? 'idle' : currentDialog.status,
|
||||
errorMessage:
|
||||
currentDialog.status === 'failed'
|
||||
? undefined
|
||||
: currentDialog.errorMessage,
|
||||
};
|
||||
});
|
||||
setGenerateDialog((currentDialog) =>
|
||||
updateSpecFormDialogValue(currentDialog, key, value),
|
||||
);
|
||||
},
|
||||
[setGenerateDialog],
|
||||
);
|
||||
|
||||
const updateCharacterAnimationDuration = useCallback(
|
||||
(frameCountValue: string) => {
|
||||
const option = CHARACTER_ANIMATION_DURATION_OPTIONS.find(
|
||||
(item) => String(item.frameCount) === frameCountValue,
|
||||
);
|
||||
if (!option) {
|
||||
return;
|
||||
}
|
||||
setCharacterAnimationPanel((currentPanel) =>
|
||||
currentPanel
|
||||
? {
|
||||
...currentPanel,
|
||||
frameCount: option.frameCount,
|
||||
durationSeconds: option.durationSeconds,
|
||||
status:
|
||||
currentPanel.status === 'failed' ? 'idle' : currentPanel.status,
|
||||
errorMessage:
|
||||
currentPanel.status === 'failed'
|
||||
? undefined
|
||||
: currentPanel.errorMessage,
|
||||
}
|
||||
: currentPanel,
|
||||
updateCharacterAnimationDurationPanel(currentPanel, frameCountValue),
|
||||
);
|
||||
},
|
||||
[],
|
||||
@@ -940,28 +751,12 @@ export function useImageCanvasGenerationWorkflow({
|
||||
|
||||
const hideGeneratedLayerPanelAfterBlur = useCallback(() => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
(currentDialog?.mode === 'generate' ||
|
||||
currentDialog?.mode === 'spec' ||
|
||||
currentDialog?.mode === 'character' ||
|
||||
currentDialog?.mode === 'icon') &&
|
||||
currentDialog.status !== 'generating'
|
||||
? {
|
||||
...currentDialog,
|
||||
composerOpen: false,
|
||||
}
|
||||
: currentDialog,
|
||||
hideGeneratedLayerComposerAfterBlur(currentDialog),
|
||||
);
|
||||
}, [setGenerateDialog]);
|
||||
|
||||
const closeGenerateComposer = useCallback(() => {
|
||||
setGenerateDialog((currentDialog) =>
|
||||
currentDialog?.mode === 'generate'
|
||||
? {
|
||||
...currentDialog,
|
||||
composerOpen: false,
|
||||
}
|
||||
: currentDialog,
|
||||
);
|
||||
setGenerateDialog(closeGenerateComposerDialog);
|
||||
setActiveTool('select');
|
||||
}, [setActiveTool, setGenerateDialog]);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user