合并图标规范与图集生成优化
合入 PR 137 的图标规范生成、稳定引用与图集提示词链路 保留主分支现行音效提交、Prompt 模块与结果压缩逻辑 解决 External Worker、生成提交和客户端测试冲突
This commit is contained in:
@@ -25,6 +25,7 @@ import {
|
||||
extractEditorUiDesignAssets,
|
||||
generateEditorBackgroundMusic,
|
||||
generateEditorCharacterAnimation,
|
||||
generateEditorIconSpec,
|
||||
generateEditorIconSpritesheet,
|
||||
generateEditorImage,
|
||||
generateEditorScene,
|
||||
@@ -83,7 +84,6 @@ import {
|
||||
buildIconSpritesheetGenerationSubmissionPlan,
|
||||
buildImageGenerationSubmissionPlan,
|
||||
resolveGenerationAssetLabel,
|
||||
resolveImageGenerationDialogPrompt,
|
||||
} from './ImageCanvasGenerationSubmissionModel';
|
||||
import { validateSoundEffectPrompt } from './ImageCanvasSoundEffectPromptModel';
|
||||
import type {
|
||||
@@ -362,7 +362,7 @@ type GenerationSubmissionWorkflowOptions = {
|
||||
onGenerationWarning?: (message: string) => void;
|
||||
};
|
||||
|
||||
async function normalizeImageGenerationReferenceImages<
|
||||
async function normalizeGenerationReferenceImages<
|
||||
T extends { referenceImageSrcs?: string[] },
|
||||
>(
|
||||
input: T,
|
||||
@@ -743,10 +743,7 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
);
|
||||
|
||||
const isBackgroundMusicSubmissionProjectCurrent = useCallback(
|
||||
(scope: {
|
||||
currentUserId: string | null;
|
||||
projectId: string | null;
|
||||
}) => {
|
||||
(scope: { currentUserId: string | null; projectId: string | null }) => {
|
||||
const currentScope = currentBackgroundMusicSubmissionScopeRef.current;
|
||||
return (
|
||||
currentScope.mounted &&
|
||||
@@ -1365,11 +1362,6 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
if (!canvasDialog) {
|
||||
return;
|
||||
}
|
||||
const iconSpecReference = dialog.iconSpecReference;
|
||||
if (!iconSpecReference) {
|
||||
return;
|
||||
}
|
||||
|
||||
setSubmittingIconDialog({
|
||||
...canvasDialog,
|
||||
iconDescriptions: submissionPlan.iconDescriptions,
|
||||
@@ -1381,11 +1373,6 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
try {
|
||||
const canvasCompletionPlaceholder =
|
||||
getGeneratingDialogPlaceholder(dialog);
|
||||
const referenceImageSrc = await resolveEditorGenerationMediaReference(
|
||||
iconSpecReference,
|
||||
'image',
|
||||
projectId,
|
||||
);
|
||||
const referenceImageSrcs = await Promise.all(
|
||||
(dialog.generationReferences ?? []).map((reference) =>
|
||||
resolveEditorGenerationMediaReference(
|
||||
@@ -1398,7 +1385,6 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
const generated = await runEditorGenerationWithWalletRefresh(
|
||||
generateEditorIconSpritesheet({
|
||||
...submissionPlan.input,
|
||||
referenceImageSrc,
|
||||
...(referenceImageSrcs.length ? { referenceImageSrcs } : {}),
|
||||
projectId,
|
||||
generationInputs: submissionPlan.generationInputs,
|
||||
@@ -1884,6 +1870,26 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
onWalletBalanceMayHaveChanged,
|
||||
]);
|
||||
|
||||
const resetProjectBackedGenerationDialog = useCallback(
|
||||
(canvasDialog: CanvasGenerationDialogState | null) => {
|
||||
if (!canvasDialog || !projectId) {
|
||||
return false;
|
||||
}
|
||||
updateCanvasGenerationDialogById(canvasDialog.id, (currentDialog) =>
|
||||
currentDialog.generatedLayerId
|
||||
? currentDialog
|
||||
: {
|
||||
...currentDialog,
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
errorMessage: undefined,
|
||||
},
|
||||
);
|
||||
return true;
|
||||
},
|
||||
[projectId, updateCanvasGenerationDialogById],
|
||||
);
|
||||
|
||||
const submitImageGeneration = useCallback(
|
||||
async (dialog: GenerateDialogState) => {
|
||||
const canvasDialog = isCanvasGenerationDialog(dialog) ? dialog : null;
|
||||
@@ -2128,6 +2134,64 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
canvasDialog?.id,
|
||||
submissionPlan.result.title,
|
||||
);
|
||||
} else if (submissionPlan.kind === 'icon-spec') {
|
||||
const iconSpecInput = submissionPlan.input;
|
||||
const canvasCompletionPlaceholder =
|
||||
getGeneratingDialogPlaceholder(dialog);
|
||||
const generated = await runEditorGenerationWithWalletRefresh(
|
||||
generateEditorIconSpec({
|
||||
...iconSpecInput,
|
||||
projectId,
|
||||
assetFolderId,
|
||||
assetLabel: submissionPlan.result.title,
|
||||
...(projectId && canvasCompletionPlaceholder
|
||||
? {
|
||||
canvasCompletion: {
|
||||
dialogId: canvasDialog?.id,
|
||||
title: submissionPlan.result.title,
|
||||
placeholder: canvasCompletionPlaceholder,
|
||||
},
|
||||
}
|
||||
: {}),
|
||||
}),
|
||||
onWalletBalanceMayHaveChanged,
|
||||
);
|
||||
notifyEditorGenerationWarning(
|
||||
generated.warning?.reason,
|
||||
onGenerationWarning,
|
||||
);
|
||||
if (
|
||||
await applyQueuedEditorGenerationProject(
|
||||
generated,
|
||||
projectId,
|
||||
applyProjectSnapshot,
|
||||
onQueuedGenerationTask,
|
||||
onWalletBalanceMayHaveChanged,
|
||||
onGenerationWarning,
|
||||
canvasDialog?.id,
|
||||
)
|
||||
) {
|
||||
return;
|
||||
}
|
||||
if (generated.project && applyProjectSnapshot) {
|
||||
applyProjectSnapshot(generated.project);
|
||||
if (generated.asset) {
|
||||
upsertGeneratedAsset?.(generated.asset);
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (resetProjectBackedGenerationDialog(canvasDialog)) {
|
||||
return;
|
||||
}
|
||||
addGeneratedResultLayer(generated, {
|
||||
frame: canvasCompletionPlaceholder,
|
||||
assetKind: submissionPlan.result.assetKind,
|
||||
title: submissionPlan.result.title,
|
||||
dialogId: canvasDialog?.id,
|
||||
generationInputs:
|
||||
generated.asset?.generationInputs ??
|
||||
submissionPlan.result.generationInputs,
|
||||
});
|
||||
} else if (submissionPlan.kind === 'video') {
|
||||
const canvasCompletionPlaceholder =
|
||||
getGeneratingDialogPlaceholder(dialog);
|
||||
@@ -2174,6 +2238,9 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (resetProjectBackedGenerationDialog(canvasDialog)) {
|
||||
return;
|
||||
}
|
||||
addVideoResultLayer(
|
||||
generated,
|
||||
submissionPlan.result.title,
|
||||
@@ -2430,6 +2497,9 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (resetProjectBackedGenerationDialog(canvasDialog)) {
|
||||
return;
|
||||
}
|
||||
addAudioResultLayer(
|
||||
generated,
|
||||
submissionPlan.result.title,
|
||||
@@ -2438,12 +2508,11 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
canvasDialog?.id,
|
||||
);
|
||||
} else if (submissionPlan.kind === 'scene') {
|
||||
const sceneGenerationInput =
|
||||
await normalizeImageGenerationReferenceImages(
|
||||
submissionPlan.input,
|
||||
resolveImageGenerationDialogReferences(dialog),
|
||||
projectId,
|
||||
);
|
||||
const sceneGenerationInput = await normalizeGenerationReferenceImages(
|
||||
submissionPlan.input,
|
||||
resolveImageGenerationDialogReferences(dialog),
|
||||
projectId,
|
||||
);
|
||||
const canvasCompletionPlaceholder =
|
||||
getGeneratingDialogPlaceholder(dialog);
|
||||
const generated = await runEditorGenerationWithWalletRefresh(
|
||||
@@ -2487,26 +2556,10 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
}
|
||||
if (generated.project && applyProjectSnapshot) {
|
||||
applyProjectSnapshot(generated.project);
|
||||
if (generated.asset) {
|
||||
upsertGeneratedAsset?.(generated.asset);
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (canvasDialog && projectId) {
|
||||
updateCanvasGenerationDialogById(
|
||||
canvasDialog.id,
|
||||
(currentDialog) =>
|
||||
currentDialog.generatedLayerId
|
||||
? currentDialog
|
||||
: {
|
||||
...currentDialog,
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
errorMessage: undefined,
|
||||
},
|
||||
);
|
||||
if (generated.asset) upsertGeneratedAsset?.(generated.asset);
|
||||
return;
|
||||
}
|
||||
if (resetProjectBackedGenerationDialog(canvasDialog)) return;
|
||||
addGeneratedResultLayer(generated, {
|
||||
frame: canvasCompletionPlaceholder,
|
||||
assetKind: submissionPlan.result.assetKind,
|
||||
@@ -2515,12 +2568,11 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
generationInputs: submissionPlan.result.generationInputs,
|
||||
});
|
||||
} else {
|
||||
const imageGenerationInput =
|
||||
await normalizeImageGenerationReferenceImages(
|
||||
submissionPlan.input,
|
||||
resolveImageGenerationDialogReferences(dialog),
|
||||
projectId,
|
||||
);
|
||||
const imageGenerationInput = await normalizeGenerationReferenceImages(
|
||||
submissionPlan.input,
|
||||
resolveImageGenerationDialogReferences(dialog),
|
||||
projectId,
|
||||
);
|
||||
const resultTitle =
|
||||
submissionPlan.result.title ??
|
||||
`生成图片 ${layerCounterRef.current + 1}`;
|
||||
@@ -2572,19 +2624,7 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (canvasDialog && projectId) {
|
||||
updateCanvasGenerationDialogById(
|
||||
canvasDialog.id,
|
||||
(currentDialog) =>
|
||||
currentDialog.generatedLayerId
|
||||
? currentDialog
|
||||
: {
|
||||
...currentDialog,
|
||||
status: 'idle',
|
||||
composerOpen: true,
|
||||
errorMessage: undefined,
|
||||
},
|
||||
);
|
||||
if (resetProjectBackedGenerationDialog(canvasDialog)) {
|
||||
return;
|
||||
}
|
||||
addGeneratedResultLayer(generated, {
|
||||
@@ -2721,6 +2761,7 @@ export function useImageCanvasGenerationSubmissionWorkflow({
|
||||
layers,
|
||||
quickEditSelectionState,
|
||||
rememberImageModel,
|
||||
resetProjectBackedGenerationDialog,
|
||||
projectId,
|
||||
assetFolderId,
|
||||
applyProjectSnapshot,
|
||||
|
||||
Reference in New Issue
Block a user