Communitygithub.com

eternityspring/reelbench-skills

Fügt Aufnahmen mit Shot-Informationen zu einem direkt ansehbaren Video zusammen: Links das Bild, rechts die Details des aktuellen Shots (Shots-Nummer, Start/Ende, Dauer, Einstellungsgröße, Kategorie, Kamerabewegung, Bildbeschreibung, Dialog). Beim Szenenwechsel aktualisiert sich die Tabelle automatisch und die aktuelle Zeile wird hervorgehoben.

Was ist reelbench-skills?

Dieses Skill erstellt aus einem `shots.json` (erzeugt von `video-shots`) und dem dazugehörigen Originalvideo ein neues Video, das auf einer Seite das Originalbild und auf der anderen Seite die Detailinformationen des aktuellen Shots anzeigt. Die Tabelle der Shots scrollt automatisch mit und hebt die aktuelle Zeile hervor. Das Layout passt sich automatisch an das Seitenverhältnis des Originalvideos an: Bei horizontalen oder quadratischen Videos wird das Bild oben und die Informationen unten angezeigt; bei vertikalen Videos wird das Bild links und die Informationen rechts dargestellt. Das Bild wird immer unbeschnitten skaliert. Es wird nur eine minimale Anzahl von Screenshots erstellt (Grundlage + zwei lange, vollständig aufgeklappte Tabellenbilder) und das Scrollen sowie die Hervorhebung werden über die Zeitsteuerung von FFmpeg realisiert. Das vollständige Layout befindet sich in `scripts/panel.css`, sodass es ohne Änderungen am Hauptskript angepasst werden kann. Das Skill benötigt keine npm-Abhängigkeiten und arbeitet mit FFmpeg sowie einem Headless-Browser. Es ist ideal für Entwickler, die ein Video mit eingebetteten Shot-Informationen exportieren möchten.

Funktioniert mit✓Claude Code✓Codex CLI~Cursor
npx skills add https://github.com/eternityspring/reelbench-skills/tree/HEAD/skills/video-sync

In Ihrer bevorzugten KI fragen

Öffnet einen neuen Chat, in dem dieser Agent-Skill bereits geladen ist.

Dokumentation

video-sync

Aus shots.json + Originalvideo wird ein Video erstellt: Auf einer Seite das Bild, auf der anderen Seite die Shot-Informationen des aktuellen Shots. Beim Szenenwechsel aktualisiert sich die Tabelle automatisch und die aktuelle Zeile wird hervorgehoben.

Das Layout richtet sich ausschließlich nach dem Seitenverhältnis:

OriginalvideoLayoutZusammensetzung
Horizontal (breit > hoch), QuadratischBild oben, Informationen untenvstack
Vertikal (hoch > breit)Bild links, Informationen rechtshstack

In beiden Fällen wird das Bild unbeschnitten skaliert. Das Panel füllt den verbleibenden Platz.

Es werden nur drei Screenshots erstellt; die beweglichen Teile übernimmt FFmpeg. Auf dem Panel ändern sich nur zwei Dinge: die Scroll-Position und die hervorgehobene Zeile. Daher werden die Zeilenpositionen einmal gemessen, ein Hintergrundbild sowie zwei vollständig aufgeklappte Tabellenbilder erstellt (eines abgedunkelt, eines vollständig hell). Scrollen = ein Ausschnitt aus dem dunklen Hintergrundbild, Hervorhebung = eine Zeile aus dem hellen Tabellenbild wird darüber gelegt. Die Positionen werden über sendcmd an jedem Schnittpunkt mit einer kleinen Expression gesteuert. Bei 53 Shots sinkt die Anzahl der Screenshots von 53 auf 3 (12 Sekunden).

Der aktuelle Shot wird in der zweiten Zeile fixiert: Die ersten beiden Shots scrollen nicht (die Hervorhebung bewegt sich nach unten in die nächste Zeile), ab dem dritten Shot wird bei jedem Schnitt eine Zeile nach oben gescrollt. Die Bewegung erfolgt am Schnittpunkt, der Rest ist statisch – am Schnittpunkt wird innerhalb von --ease (Standard: 0,45) Sekunden an die Zielposition gescrollt und bleibt dann stehen. Bei einem 16-Sekunden-Langshot würde die Liste hingegen kontinuierlich kriechen, was den Zuschauer 16 Sekunden lang ablenken würde.

Die Zeilenhöhe wird durch den Inhalt bestimmt: Je länger die Beschreibung, desto höher die Zeile. Die Hervorhebungsleiste ist nach Zeilenhöhe gestaffelt (die Höhe von crop lässt sich zur Laufzeit nicht ändern).

{baseDir} = Verzeichnis, in dem sich diese Datei befindet. Das Skript {baseDir}/scripts/video-sync.mjs hat keine Abhängigkeiten und wird direkt mit node ausgeführt.

Abgrenzungen (was nicht gemacht wird): Keine Shot-Analyse (das ist Aufgabe von video-shots, dieses Skill verwendet dessen shots.json), kein Schneiden, keine Überblendungen, keine Musik, keine Untertitel im Bild, keine Frame-für-Frame-Rendering (Animationen werden von FFmpeg zeitgesteuert erstellt).


Schritt 0 – Shot-Daten müssen vorhanden sein

Eine shots.json (Ausgabe von video-shots) und das zugehörige Originalvideo sind erforderlich. Wenn frames/ (ein Schlüsselbild pro Shot) vorhanden ist, wird dieses als Thumbnail in der Tabelle verwendet – andernfalls bleibt die Stelle leer.

Die shots.json muss mit dem Video übereinstimmen: Wenn meta.durationSeconds nicht mit der Videodauer übereinstimmt, wird die Synthese abgebrochen; korrigieren Sie zuerst die Shots.

Schritt 1 – Geometrie prüfen, dann Video erstellen

node {baseDir}/scripts/video-sync.mjs plan shots.json --video <Video>

Nur berechnen, nicht synthetisieren – dauert nur Sekunden: Layout, Bildbereich, Panelbereich, Ausgabeabmessungen. Prüfen Sie zuerst diese drei Zahlen, bevor Sie fortfahren – die Synthese eines 3-minütigen Videos dauert ein bis zwei Minuten; ein Fehler wäre dann ärgerlich.

Anpassungen: --panel <Verhältnis> (horizontal: Panelhöhe / Bildhöhe, Standard 0,8; vertikal: Panelbreite / Bildbreite, Standard 1,6), --width / --height (Obergrenze des Bildbereichs, Standard 1920 / 1080).

Ist das Originalvideo zu klein, skaliert den Bildbereich hoch: Das Panel wird relativ zum Bildbereich berechnet. Bei einem 640x360-Video wäre das Panel nur 640x288 groß – vier Spalten wären zu eng. --scale 2 skaliert den Bildbereich auf 1280x720 und das Panel auf 1280x576, das Seitenverhältnis bleibt erhalten. Standard ist 1 (keine Skalierung). plan / panels / compose / export müssen alle denselben --scale-Wert verwenden.

Schritt 2 – Panel rendern

node {baseDir}/scripts/video-sync.mjs panels shots.json --video <Video> \
  --frames frames --lang zh|en [--out panels] [--chrome <Pfad>]

Erzeugt static.png (Hintergrund), list-dim.png / list-lit.png (vollständig aufgeklappte Tabelle, einmal abgedunkelt, einmal hell), layout.json (Zeilenpositionen, die für das Scrollen bei der Synthese verwendet werden), sowie panels/panel.html – im Browser öffnen, um das Panel zu sehen. Mit #S07 kann der Shot gewechselt werden (die Scroll-Animation im Preview entspricht der Exportversion).

Das Layout wird über {baseDir}/scripts/panel.css angepasst: Nach einer Änderung wird panels erneut ausgeführt, um das neue Layout zu übernehmen – ohne Änderungen am Skript oder an der Screenshot-Logik. Stilkonventionen in {baseDir}/references/panel-style.md.

Schritt 3 – Synthese

node {baseDir}/scripts/video-sync.mjs compose shots.json --video <Video> \
  [--panels panels] [-o out.mp4] [--crf 20] [--ease 0.45]

Die Audiospur wird unverändert übernommen (bei stummen Videos wird automatisch keine Tonspur hinzugefügt). Nach der Synthese werden in stderr die Ausgabemaße, Dauer und das Layout ausgegeben – überprüfen Sie diese Angaben.

Die beiden Schritte können auch in einem Befehl kombiniert werden:

node {baseDir}/scripts/video-sync.mjs export shots.json --video <Video> -o out.mp4 --frames frames

Schritt 4 – Stichprobenprüfung ⛔ Nicht überspringen

Prüfen Sie nicht nur, ob die Synthese ohne Fehler abgeschlossen wurde. Nehmen Sie mindestens drei Stichproben, um zu sehen, ob die Informationen mit dem Bild übereinstimmen:

for t in 5 30 60; do ffmpeg -v error -y -ss $t -i out.mp4 -frames:v 1 -q:v 3 /tmp/check-$t.jpg; done

Überprüfen Sie drei Dinge: Zu welchem Shot gehört das Bild in diesem Frame? Ist die Shots-Nummer im Panel dieselbe? Wird die hervorgehobene Zeile korrekt aktualisiert? Abweichungen deuten in der Regel darauf hin, dass shots.json und das Originalvideo nicht zusammengehören oder dass --video falsch angegeben wurde.

Melden Sie das Ergebnis in einem Satz: Ausgabepfad, Größe, Dauer, Layout, Anzahl der Shots und welche Panels nicht gerendert wurden (falls vorhanden).


Abgrenzungen

  • Das Scrollen erfolgt nur am Schnittpunkt: Innerhalb von --ease Sekunden wird an die Zielposition gescrollt und bleibt dann stehen. Ein „gleichmäßiges Durchlaufen“ ist theoretisch möglich (durch Anpassung der motionPlan-Segmente), würde aber bei langen Shots zu störendem Flimmern führen.
  • Ein Headless-Browser ist erforderlich (Chrome/Chromium/Edge). Der Preis für „das Layout kann frei angepasst werden“: Mit FFmpegs drawtext müsste man Zeilenumbrüche, Thumbnails und Hervorhebungen selbst implementieren, und jede Layoutänderung würde eine Überarbeitung des Filtergraphen erfordern.
  • Das Vokabular (Einstellungsgröße/Kategorie/Kamerabewegung/Schnitt) ist in diesem Skill eigenständig enthalten – es wird nicht aus anderen Verzeichnissen importiert, damit das Skill vollständig kopiert werden kann. Wenn in video-shots neue Begriffe hinzugefügt werden, müssen sie auch hier ergänzt werden, da sie sonst als Enum-Schlüssel angezeigt werden.
  • Das Rendern des Panels erzeugt immer drei Screenshots, unabhängig von der Anzahl der Shots: 53 Shots dauern etwa 12 Sekunden. Die Synthese skaliert mit der Videolänge; ein 203-Sekunden-Video benötigt etwa 75 Sekunden.

Selbsttest

node {baseDir}/scripts/selftest.mjs

122 Assertions, ohne FFmpeg oder Browser: Geometrie (horizontal/quadratisch/vertikal, gerade Kantenlängen, Ober-/Untergrenzen, Drehknöpfe), Datenvertrag der Panelseite (Vokabularverteilung, Rolleninformationen, Thumbnails nur vorhanden/fehlend, Escape-Sequenzen), Animationsbefehle (jeder Befehl muss kurz sein – zu lange Expressions führen zu FFmpeg-Konfigurationsfehlern), FFmpeg-Parameter. Nach Änderungen am Skript zuerst diesen Test ausführen.

Individual skills in this repo

This repo contains 2 individual skills — each has its own dedicated page.

eternityspring/reelbench-skills

把一条视频重建成「只有画面和声音」的干净文件——**源片的元数据一概不搬**: GPS、设备型号、账号 ID、创建时间、章节、GoPro 的遥测轨,全部留在原地。 走的是白名单而不是黑名单:不列要删什么,只说带什么过去(画面一条流、声音一条流), 隐私保证来自结构,不来自枚举。 难点不在容器 tag,在**看不见的那几层**:x264 把完整编码参数写成 SEI 塞在码流里、 AAC 把版本号写进 DSE、avc1 的 compressorname 里还有一份——`ffprobe` 一个都看不见。 五个藏身处逐一堵死,每一处都有实测。 默认 `--mode copy`:**画面逐字节照搬**(cmp 验证过),只重编音频,53 秒的片子 1.3 秒跑完; `--mode encode` 完整重编码,多杀掉码流域的东西。 验收不靠声称:把源片所有元数据字符串当「针」,在输出文件里做**字节级扫描**, 扎到一根就红。12 道门全部由脚本确定性检查。 零依赖、零 API key,只要 node 和 ffmpeg。 Use when asked to 清元数据、去元数据、抹掉视频信息、视频隐私、去水印信息、 strip video metadata、remove exif from video、scrub video。

eternityspring/reelbench-skills

拉片:把一条成片拆成逐镜头的分析表——每个镜头的时长、景别、类别、运镜、画面。 分工刻在骨子里:**能量的都由代码量**(切点来自 ffmpeg 场景检测,时长是切点相减, 运动量是逐帧差分的中位数),模型只判断它真正该判断的那几件事(景别 / 类别 / 运镜 / 画面 / 节奏), 然后每一条判断都被代码当场对账——**声称推拉摇移却实测几乎不动,门直接拦**。 看片走联系表(每镜起手帧 + 收尾帧各拼一张大图,一屏二十几个镜头,a/b 对照就是运镜), 不是一张张翻。检测漏刀多刀用 recut 补刀并刀,自动重编号重算时长,手改边界过不了门。 产出 shots.json + Markdown 镜头表 + **单页交互式拉片报告**:内嵌播放器(播放时同步高亮镜头、 点镜头跳转)、镜头节奏带、可搜索可筛选可排序的镜头表(列表 / 卡片两种视图、首尾关键帧并排、 点图开大图)、景别类别运镜分布、出场人物、质量门、导出 JSON。单文件零依赖,离线双击能开。 15 道质量门全部由脚本确定性检查。 零依赖、零 API key,只要 node 和 ffmpeg。 Use when asked to 拉片、拆镜头、分析视频镜头、镜头时长、景别、运镜、镜头表、 video shot breakdown、shot list from video。

Verwandte Skills