|
| 1 | +import assert from "node:assert/strict"; |
| 2 | +import { mkdirSync, mkdtempSync, readFileSync, rmSync, writeFileSync } from "node:fs"; |
| 3 | +import { tmpdir } from "node:os"; |
| 4 | +import { dirname, join } from "node:path"; |
| 5 | +import { spawnSync } from "node:child_process"; |
| 6 | +import test from "node:test"; |
| 7 | + |
| 8 | +const script = new URL("./transitions.mjs", import.meta.url).pathname; |
| 9 | + |
| 10 | +function write(filePath, contents) { |
| 11 | + mkdirSync(dirname(filePath), { recursive: true }); |
| 12 | + writeFileSync(filePath, contents); |
| 13 | +} |
| 14 | + |
| 15 | +test("inject extends a documented frame root that omits data-duration", (t) => { |
| 16 | + const project = mkdtempSync(join(tmpdir(), "faceless-transitions-")); |
| 17 | + t.after(() => rmSync(project, { force: true, recursive: true })); |
| 18 | + |
| 19 | + write( |
| 20 | + join(project, "STORYBOARD.md"), |
| 21 | + `--- |
| 22 | +format: 1920x1080 |
| 23 | +--- |
| 24 | +
|
| 25 | +## Frame 1 — First |
| 26 | +
|
| 27 | +- duration: 2s |
| 28 | +- transition_in: cut |
| 29 | +- status: animated |
| 30 | +- src: compositions/frames/01-a.html |
| 31 | +
|
| 32 | +## Frame 2 — Second |
| 33 | +
|
| 34 | +- duration: 2s |
| 35 | +- transition_in: crossfade |
| 36 | +- status: animated |
| 37 | +- src: compositions/frames/02-b.html |
| 38 | +`, |
| 39 | + ); |
| 40 | + write( |
| 41 | + join(project, "index.html"), |
| 42 | + `<!doctype html><html><body> |
| 43 | +<div id="root" data-composition-id="main" data-duration="4"></div> |
| 44 | +<div id="el-01-a" data-start="0" data-duration="2" data-track-index="0"></div> |
| 45 | +<div id="el-02-b" data-start="2" data-duration="2" data-track-index="0"></div> |
| 46 | +<script>window.__timelines={}; window.__timelines["main"] = gsap.timeline({ paused: true });</script> |
| 47 | +</body></html>`, |
| 48 | + ); |
| 49 | + write( |
| 50 | + join(project, "compositions/frames/01-a.html"), |
| 51 | + `<template><div id="root" data-composition-id="01-a"><div class="clip" data-start="0" data-duration="2" data-track-index="0">first</div></div></template>`, |
| 52 | + ); |
| 53 | + write( |
| 54 | + join(project, "compositions/frames/02-b.html"), |
| 55 | + `<template><div id="root" data-composition-id="02-b"><div class="clip" data-start="0" data-duration="2" data-track-index="0">second</div></div></template>`, |
| 56 | + ); |
| 57 | + |
| 58 | + const result = spawnSync( |
| 59 | + process.execPath, |
| 60 | + [script, "inject", "--storyboard", join(project, "STORYBOARD.md"), "--hyperframes", project], |
| 61 | + { encoding: "utf8" }, |
| 62 | + ); |
| 63 | + |
| 64 | + assert.equal(result.status, 0, result.stderr); |
| 65 | + const outgoing = readFileSync(join(project, "compositions/frames/01-a.html"), "utf8"); |
| 66 | + assert.match(outgoing, /data-composition-id="01-a" data-duration="2.5"/); |
| 67 | + assert.match(outgoing, /class="clip"[^>]*data-duration="2.5"/); |
| 68 | +}); |
0 commit comments