diff --git a/app/api/canvas/local-edit/route.ts b/app/api/canvas/local-edit/route.ts index fa13891ed..733e91699 100644 --- a/app/api/canvas/local-edit/route.ts +++ b/app/api/canvas/local-edit/route.ts @@ -273,17 +273,25 @@ function buildAnnotationSvg(params: { function buildLocalEditPrompt(regions: NormalizedLocalEditRegion[]) { const regionLines = regions - .map((region) => `区域 ${region.index}(${region.colorName},编号 ${region.index}):${region.prompt}`) + .map((region) => { + const left = Math.round(region.rect.x * 1000) / 10; + const top = Math.round(region.rect.y * 1000) / 10; + const width = Math.round(region.rect.width * 1000) / 10; + const height = Math.round(region.rect.height * 1000) / 10; + return `区域 ${region.index}(${region.colorName},编号 ${region.index},原图位置 x=${left}%,y=${top}%,w=${width}%,h=${height}%):${region.prompt}`; + }) .join("\n"); return [ - "输入图片1是一张带彩色标注框和框下提示词的图片编辑参考图;输入图片2是同一张原始干净图,用于保持画面细节与未编辑区域。", - "彩色框、编号、提示词气泡只是编辑指令,不是最终画面内容。", + "输入图片1是原始干净图,也是最终输出必须继承的唯一画面基底。", + "输入图片2是同一张图的彩色标注说明图,只用于理解编辑区域位置和区域提示词,不是画面参考。", + "请不要复刻、保留、描摹或生成输入图片2里的任何彩色框、编号圆点、提示词气泡、边框线、半透明色块或标注文字。", + "如果输入图片2的标注元素与输入图片1冲突,必须完全忽略标注元素,只保留输入图片1的真实画面内容。", "", "请严格根据每个区域下方的提示词,只在对应彩色框附近完成局部编辑:", regionLines, "", - "最终输出必须去除所有彩色框、编号、提示词气泡和标注文字。", + "最终输出必须是干净照片:不得出现任何彩色框、蓝框、绿框、红框、矩形边框、编号、提示词气泡、标注文字或 UI 元素。", "未被彩色框标注的区域必须尽量保持原图不变。", "新增内容必须匹配原图的透视、光线、比例、清晰度、色温和真实摄影风格。", "如果某个区域提示词与原图空间冲突,以自然融入原图为最高优先级。", @@ -382,9 +390,11 @@ export async function POST(request: NextRequest) { typeof body.model === "string" && body.model.trim() ? body.model.trim() : undefined, + negativePrompt: + "彩色框、蓝色边框、绿色边框、红色边框、矩形框、编号圆点、提示词气泡、标注文字、UI 控件、半透明色块、选区边框", prompt, promptExtend: false, - referenceImages: [annotatedUpload.url, sourceImageUrl], + referenceImages: [sourceImageUrl, annotatedUpload.url], ownerKey: session.user.id, };