Communitygithub.com

手工舞台短片

把品牌自己的戰役靜幀剪成 15–20 秒的定格舞台短片:紙偶、撕紙字幕,最後一卡落在產品和字標上。

手工舞台短片 是什麼?

把真實照片擴成 9:16,只做幾下發僵的動作,道具從照片裡摳出來,再在本地渲染 12 步一拍的運動、八音盒圓舞曲和結尾卡。臉、產品和印刷標籤保持原樣。七張靜幀的模型費用大約兩三美元,成片在本機免費剪完。

相容平台✓Claude Code~Codex CLI~Cursor
npx skills add https://github.com/DarthManly/handmade-stage-film-skill/tree/HEAD

在你喜歡的 AI 中提問

開啟一個已預先載入此 Agent Skill 的新對話。

說明文件

手工舞台影片

萬聖節夜晚,無所事事:一位留著黑色鮑伯頭的女孩坐在手繪紙板沙發上,手拿粉紅色飲料,按下紙板遙控器。紙板電視機開啟雪花雜訊,螢幕上一個小幽靈跳起舞來,然後從螢幕剝離飄走。它飄到她的杯子旁(「它想喝一口。」),落在棋盤格桌面上,一支巨叉刺向一盤手繪莓果(「梔子花。莓果。優格。」),喝了一口後,她坐在一頂巨大的女巫帽上,周圍星星蹦跳而出(「……完全魔法。」)。杯子以潦草字跡寫著「魔法漂亮水」和箭頭,最後一張卡片有品牌字標、杯子、幽靈、「萬聖節限定」和販售地點。每一幀都來自該品牌自己的七張宣傳照片。

它以四個部分組成:

  • scripts/generate.mjs 將靜態照片轉為素材:9:16 關鍵影格(Nano Banana 2 繪製額外背景,原始像素疊回其上)、Kling 短片片段、切割出的道具、重新放置的標籤和品牌字標。
  • scripts/reel.mjs 將片段按影片時間線剪輯為一個連續片段。
  • scripts/sfx.mjs 合成音效:一首原創音樂盒華爾滋以及每個事件對應的聲音。
  • scripts/render.mjs 以舞台秀方式播放所有內容:每秒 12 幀的步進動作、手持抖動、移動噪點、紙偶、撕紙字幕、附箭頭的標籤、開啟的電視螢幕以及最後一張卡片。它使用 headless Chrome 和 FFmpeg 在本機渲染。

設定(每台機器一次)

在此技能資料夾內執行:

npm install

這會安裝 puppeteer-core 和 ffmpeg-static。必須已安裝 Google Chrome,或設定 CHROME_PATH 指向 Chrome/Chromium 執行檔(npx @puppeteer/browsers install chrome-headless-shell@stable 會顯示一個)。

影片素材需要 Nano Banana 2 和 Kling 2.5 Turbo 的 API 金鑰;腳本透過模型 API 閘道呼叫它們,金鑰於此建立(https://fal.ai/dashboard/keys)。使用者在其終端機中設定為 FAL_KEY(例如在其 shell 設定檔中)。切勿要求使用者將金鑰貼入對話中,也切勿印出金鑰。

成本

模型使用費,計入使用者自己的 API 金鑰:每張靜態照片擴展為 9:16 需 $0.08(每次 edit 亦同),每個 5 秒片段需 $0.35,每個切割道具幾分之一美分(2026 年 10 月價格)。七張靜態照片、五個片段的一部影片約需 $2.30。連續片段、道具、字幕、音效和最終 MP4 在使用者機器上免費製作。在生成前告知使用者成本。

成功關鍵

  • 他們自己的照片,關鍵處未經更動。 擴展和每個片段都從品牌的真實靜態照片開始;extend 將原始像素疊回 AI 的版本上,relabel 將清晰的標籤疊回任何片段中標籤模糊的畫格上。
  • 一個故事,而非幻燈片。 規劃一個小情節貫穿各張照片,並有一個物件在之間移動(此處為從電視逃出的小幽靈紙偶)。字幕是簡短的故事節拍,而非口號。
  • 刻意笨拙。 所有內容以 1/12 秒的步伐移動,帶有細微抖動,紙偶在關鍵影格上搖晃,字幕以三步驟彈出,箭頭以三筆畫繪製。不要讓它平滑。
  • 一半產品,一半品牌。 產品出現在大部分鏡頭中,並有一個特寫加上標籤;最後一張卡片是品牌字標、產品、名稱和購買地點。

工作流程

  1. 收集 4-8 張同一次拍攝的靜態照片(3:4、4:5 或 9:16)、產品名稱、一句話(口味、材質)、一則備註(「萬聖節限定」)和行動呼籲。詢問靜態照片底部是否帶有印刷的品牌字標或徽章(這些會在畫格中被塗掉,並為最後一張卡片進行去背)。
  2. 分鏡腳本(在生成前顯示):鏡頭順序、情節、每個片段中移動的內容(一到兩個小動作,產品保持靜止)、哪些道具要切割為紙偶及其動作、字幕和標籤,以及成本。控制在 15-20 秒內。
  3. 關鍵影格:對每張非 9:16 的靜態照片執行 node scripts/generate.mjs extend --in still.jpg --out keys/<shot>.png --cover <rows>(--cover = 原始照片底部印刷品牌字標頻寬的畫素高度,若有的話)。以全尺寸檢視每個關鍵影格:若模型在新頻帶中留下鏡像或重複的物件,則用同一張照片中的單純紋理覆蓋它。
  4. 試拍:一個片段,包含情節鉤子的鏡頭:node scripts/generate.mjs clip --start keys/<shot>.png --prompt "…" --out clips/<shot>.mp4。提示詞僅描述移動的內容(「她用手指按下遙控器上的一個按鈕;杯子保持直立不動」);固定後綴保持攝影機鎖定,且場景、臉部和產品不變。展示結果,然後執行其餘部分。
  5. 其他動態鏡頭的片段。逐格觀看每個片段:記下動作發生的位置(以放置音效和紙偶),以及產品上小字體模糊的位置。使用 relabel --clip … --key keys/<shot>.png --box x,y,w,h(關鍵影格中的標籤方框)修正標籤,或僅使用產品移動前的畫格。並非每個鏡頭都需要片段:帶有緩慢推近的靜態特寫鏡頭(still、box、boxTo)通常更適合產品。
  6. 道具:對每個紙偶(角色、星星、花朵、莓果、手中的產品)執行 cutout --in keys/<shot>.png --box x,y,w,h --out props/<name>.png;對移除某物(例如沒有幽靈的電視螢幕)的盤子執行 edit。品牌字標:wordmark --in still.jpg --box x,y,w,h --out props/wordmark.png。最後一張卡片的背景是從某個關鍵影格中裁切的彩繪牆壁。
  7. 建立 effect.json 從 examples/example.json(參見鏡頭和最後一張卡片),然後執行 node scripts/reel.mjs effect.json --out reel.mp4 並設定 "reel": "reel.mp4"。
  8. 音效:node scripts/sfx.mjs effect.json --out stage.m4a,然後設定 "music": "stage.m4a"。計時有任何變更後重新執行。--no-bed --music track.mp3 可將華爾滋替換為使用者已取得授權的音樂曲目。
  9. 驗證:node scripts/validate.mjs effect.json — 修正所有錯誤,並向使用者讀出所有警告。
  10. 草稿:node scripts/render.mjs effect.json --quality draft --width 540 --out draft.mp4,並檢查每個鏡頭的一格畫面:確認無字幕、標籤或紙偶蓋住臉部或產品,且所有內容避開右側 14% 的平台按鈕區域。
  11. 最終版:node scripts/render.mjs effect.json --out film.mp4 --poster poster.png。針對小紅書,裁切 3:4 版本:ffmpeg -i film.mp4 -vf crop=720:960:0:160 -c:a copy film-3x4.mp4(預設寬度 720;確認重要內容未位於頂部或底部 160 畫素內)。

鏡頭

所有位置以 1080 × 1920 畫格畫素為單位。每個鏡頭為下列之一:

  • 片段鏡頭:clip(reel.mjs 剪輯的檔案)、from 和 to(片段中的秒數)、speed(0.5 = 半速,配合 12 步播放可充分利用短暫良好片段中的每一格)、hold(動作開始前第一格停留的秒數)。
  • 靜態鏡頭:still(影像)、len、box 和 boxTo(影像畫素中的 [x, y, width] 9:16 視窗;視角從一個移動到另一個)。

每個鏡頭可以包含:

  • captions:{ "text", "at", "out", "x", "y", "rot", "size" } — 帶有手寫文字的撕紙碎片;\n 換行。
  • tags:{ "text", "at", "x", "y", "to": [x, y], "ink": "dark" | "light", "rot", "size" } — 帶有自行繪製箭頭的手寫文字,指向 to。
  • puppets:{ "image", "path": [[t, x, y, width, rotation], …], "sound", "exit", "flip", "wobble" } — 在關鍵影格之間移動的切割道具(t 為鏡頭內的秒數,x、y 為中心)。一個寬度為 0 的關鍵影格緊接一個全寬的關鍵影格即為彈出。除非 "exit": true,否則道具會停留在最後一個關鍵影格。sound 在其第一個關鍵影格播放。
  • screen:{ "rect": [x, y, w, h], "off", "static", "plate", "plateAt" } — 電視或手機螢幕,在 off 之前為黑色,static 之前為雪花雜訊,並從 plateAt 開始顯示 plate(同一關鍵影格但螢幕已清空),以便紙偶可從中爬出。
  • sounds:[[t, "kind"], …] — click、tvon、static、ghost、boing、tap、pop、whoosh、land、stab、sip、sparkle、chime、paper、scribble、cut。剪輯、字幕、標籤、螢幕和有 sound 的紙偶會自動獲得對應音效。

最後一張卡片

end:len、bg(9:16 彩繪牆壁)、wordmark(wordmarkY、wordmarkWidth)、name(nameY、nameSize)、line(lineY)、note 在撕紙碎片上(noteX、noteY)、cta 在膠囊形按鈕上(ctaY),以及 puppets 如鏡頭般(從邊緣滑入手中的產品、角色、星星)。每個都有對應的 …At 時間。

欄位

欄位必要備註
reel是相對於 JSON 檔案的影片檔案路徑 — 所有片段鏡頭由 scripts/reel.mjs 剪輯為一個無聲的 9:16 連續片段(reel.mp4)
shots是2-10 個項目的列表:clip、from、to、speed、hold、still、len — 按順序排列的影片:片段鏡頭(靜態照片的 AI 片段)和靜態鏡頭(帶有緩慢移動的靜態照片);另請參閱 SKILL.md、鏡頭
end.bg否相對於 JSON 檔案的圖片路徑 — 最後一張卡片的背景:來自照片的彩繪牆壁或背景,9:16
end.wordmark否相對於 JSON 檔案的圖片路徑 — 透明背景上的品牌字標(scripts/generate.mjs wordmark)
end.name否文字,少於 4 個單詞 — 產品名稱,最後一張卡片上手寫字體
end.line否文字,少於 6 個單詞 — 名稱下方的一行簡短說明,例如口味
end.note否文字,少於 4 個單詞 — 在撕紙碎片上,例如「萬聖節限定」
end.cta否文字,少於 12 個單詞
music否相對於 JSON 檔案的音訊檔案路徑 — 來自 scripts/sfx.mjs 的配樂(stage.m4a)
palette否顏色為 #RRGGBB;鍵值:ink(字幕和深色標籤)、paper(撕紙碎片和淺色標籤)和 accent(行動呼籲膠囊按鈕)

提示

  • 撰寫緊湊的片段提示詞:一或兩個小動作、面無表情的臉、「杯子保持直立不動,標籤朝向攝影機」。大動作會模糊臉部和標籤。
  • Kling 自行選擇時機:觀察動作落點,並將點擊、剪輯和紙偶放在該畫格上,而非整數時間點。
  • 為故事提供一個旅行者:從一張照片切割出的紙偶,出現在後續鏡頭中,可將七張靜態照片連結成一部影片。
  • 從照片本身切割紙偶,而非使用新的美術素材:相同的顏料、紙張和光線使它們具有歸屬感。
  • 保持字幕在三四個單詞內;圖片講述了大部分故事。

輸出

H.264 MP4,1080 × 1920,30 fps(畫面以每秒 12 步移動),15-20 秒含音效,外加一個宣傳幀(PNG)。

相關技能