Make an mp4 out of a Chrome DevTools trace with screenshots.
const fs = require('fs'); | |
const path = require('path'); | |
const spawn = require('child_process').spawn; | |
const FPS = 60; | |
const MICROSEC_PER_FRAME = Math.round(1000000 / FPS); | |
if (process.argv.length < 3) { | |
console.log(`node ${path.relative('.', process.argv[1])} [DevToolsProfile]`); | |
process.exit(1); | |
} | |
let traceFile = path.resolve(process.argv[2]); | |
let trace = JSON.parse(fs.readFileSync(traceFile, 'utf8')).traceEvents; | |
trace = trace.filter(event => event.name === "Screenshot").sort((a, b) => a.ts - b.ts); | |
if (trace.length === 0) { | |
console.log('Trace was not recorded with Screenshots. Ensure Screenshots is checked before recording.') | |
process.exit(1); | |
} | |
let { name } = path.parse(traceFile); | |
let ffmpeg = spawn("ffmpeg", [ | |
"-f", "image2pipe", | |
"-r", `${FPS}`, | |
"-vcodec", "mjpeg", | |
"-i", "pipe:", | |
"-vcodec", "libx264", | |
"-vf", "scale=trunc(iw/2)*2:trunc(ih/2)*2", | |
`${name}.mp4` | |
], { | |
stdio: ['pipe', 'inherit', 'inherit'] | |
}); | |
let buffer; | |
let target = trace[0].ts; | |
for (let i = 0; i < trace.length; i++) { | |
let event = trace[i]; | |
// repeat last frame until caught up | |
while (target < event.ts) { | |
ffmpeg.stdin.write(buffer); | |
target += MICROSEC_PER_FRAME; | |
} | |
buffer = Buffer.from(event.args.snapshot, "base64"); | |
ffmpeg.stdin.write(buffer); | |
target += MICROSEC_PER_FRAME; | |
} | |
ffmpeg.stdin.end(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment