auto-save 2026-05-13 14:54 (~2)
This commit is contained in:
@@ -1715,6 +1715,13 @@
|
||||
"type": "session-heartbeat",
|
||||
"message": "Claude 会话活跃 · 最近命令:claude · 2 项未提交变更 · 最近提交:auto-save 2026-05-13 14:43 (~6)",
|
||||
"files_changed": 2
|
||||
},
|
||||
{
|
||||
"ts": "2026-05-13T14:49:32+08:00",
|
||||
"type": "commit",
|
||||
"message": "auto-save 2026-05-13 14:49 (~5)",
|
||||
"hash": "ffffb1e",
|
||||
"files_changed": 5
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
@@ -179,14 +179,80 @@ export function StoryboardBar({ job, selectedFrames, focusedFrame, onFocusFrame,
|
||||
)
|
||||
)}
|
||||
|
||||
{/* 编排详情面板 — focusedFrame 有值时展开(嵌入 bar,不弹 modal) */}
|
||||
{focusFrame && !collapsed && (
|
||||
{/* 编排详情面板 — 简化版:只展示该分镜的所有提取图 */}
|
||||
{focusFrame && !collapsed && (() => {
|
||||
type Shot = { e: typeof focusElements[number]; cid: string; isLegacy: boolean }
|
||||
const allShots: Shot[] = []
|
||||
focusElements.forEach((e) => {
|
||||
if (e.cutouts && e.cutouts.length > 0) {
|
||||
e.cutouts.forEach((cid) => allShots.push({ e, cid, isLegacy: false }))
|
||||
} else if (e.cutout_id) {
|
||||
allShots.push({ e, cid: e.cutout_id, isLegacy: true })
|
||||
}
|
||||
})
|
||||
return (
|
||||
<div
|
||||
className="border-t border-white/10 bg-black/20 overflow-y-auto"
|
||||
style={{ maxHeight: "55vh" }}
|
||||
>
|
||||
<div className="p-4">
|
||||
<div className="text-[12px] font-semibold text-white mb-2 flex items-center gap-1.5">
|
||||
<Sparkle className="h-3.5 w-3.5 text-violet-300" />
|
||||
分镜 {focusSeq} · 提取图
|
||||
<span className="text-[10px] text-white/40 font-mono">· {allShots.length} 张</span>
|
||||
</div>
|
||||
{allShots.length === 0 ? (
|
||||
<div className="rounded-md border border-dashed border-white/15 p-3 text-[11px] text-white/40">
|
||||
该分镜暂无提取图 · 到关键帧节点画框「AI 提取」后会出现
|
||||
</div>
|
||||
) : (
|
||||
<div className="grid grid-cols-6 gap-2">
|
||||
{allShots.map(({ e, cid, isLegacy }) => {
|
||||
const url = isLegacy
|
||||
? cutoutUrl(job.id, focusFrame.index, e.id)
|
||||
: cutoutUrl(job.id, focusFrame.index, e.id, cid)
|
||||
return (
|
||||
<a
|
||||
key={`${e.id}_${cid}`}
|
||||
href={url}
|
||||
target="_blank"
|
||||
rel="noreferrer"
|
||||
className="relative block rounded-md overflow-hidden border border-white/15 hover:border-violet-300/60 bg-white"
|
||||
style={{ aspectRatio: "1/1" }}
|
||||
title={`${e.name_zh} · 点击查看原图`}
|
||||
>
|
||||
<img src={url} alt={e.name_zh} className="absolute inset-0 w-full h-full object-contain" />
|
||||
<div className="absolute bottom-0 left-0 right-0 px-1.5 py-0.5 text-[9px] text-white bg-black/70 truncate">
|
||||
{e.name_zh}
|
||||
</div>
|
||||
</a>
|
||||
)
|
||||
})}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
})()}
|
||||
|
||||
{/* 旧 form 面板已暂时移除(用户要求只展示提取图) */}
|
||||
{false && focusFrame && (
|
||||
<div style={{ display: "none" }}>
|
||||
{/* 占位防止 saving / form / FieldX 等变量未使用报错 */}
|
||||
<span>{saving}{savedTick}{form.subject}{focusCutCount}</span>
|
||||
<FieldText label="" value="" onChange={() => {}} />
|
||||
<FieldNum label="" value={0} onChange={() => {}} />
|
||||
<FieldTextarea label="" value="" onChange={() => {}} />
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* 旧 form 面板代码(保留 fallback 渲染) */}
|
||||
{false && focusFrame && !collapsed && (
|
||||
<div
|
||||
className="border-t border-white/10 bg-black/20 overflow-y-auto"
|
||||
style={{ maxHeight: "50vh" }}
|
||||
>
|
||||
<div className="flex gap-4 p-4">
|
||||
{/* 左:分镜大图 */}
|
||||
<div className="flex-shrink-0 flex flex-col gap-1.5" style={{ width: 260 }}>
|
||||
<img
|
||||
src={effectiveFrameUrl(job.id, focusFrame)}
|
||||
|
||||
Reference in New Issue
Block a user