Skip to content

Instantly share code, notes, and snippets.

@erraticgenerator
Last active June 27, 2022 04:51
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save erraticgenerator/aef25bc40b0bda91690c7f3d150c61e7 to your computer and use it in GitHub Desktop.
Save erraticgenerator/aef25bc40b0bda91690c7f3d150c61e7 to your computer and use it in GitHub Desktop.
Video export from p5.js sketch 1
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<script src="https://unpkg.com/h264-mp4-encoder/embuild/dist/h264-mp4-encoder.web.js"></script>
<script src="https://cdn.jsdelivr.net/npm/p5@1.1.9/lib/p5.js"></script>
<style>
html { font-family: sans-serif; font-size: 12px; }
</style>
</head>
<body>
<script>
/*
library used: https://github.com/TrevorSundberg/h264-mp4-encoder
a simple example exporting mp4 with p5js.
custom animation loop, not using draw(), fixed-length animation.
*/
let cwidth = 640
let cheight = 360
let button
let checkbox
const frate = 30 // frame rate
const numFrames = 100 // num of frames to record
let recording = true
function setup() {
createCanvas(cwidth, cheight)
frameRate(frate)
button = createButton('record')
button.mousePressed(record)
checkbox = createCheckbox(' preview only')
checkbox.style('display', 'inline')
checkbox.changed(()=> {
recording = !recording
})
anim(0) // display first frame
}
function anim(count) {
background(220)
textSize(128)
textAlign(CENTER, CENTER)
text(count, width / 2, height / 2)
}
function record() {
HME.createH264MP4Encoder().then(async encoder => {
encoder.outputFilename = 'test'
encoder.width = cwidth
encoder.height = cheight
encoder.frameRate = frate
encoder.kbps = 50000 // video quality
encoder.groupOfPictures = 10 // lower if you have fast actions.
encoder.initialize()
for (let i = 0; i < numFrames; i++) {
anim(i)
encoder.addFrameRgba(drawingContext.getImageData(0, 0, canvas.width, canvas.height).data)
await new Promise(resolve => window.requestAnimationFrame(resolve))
}
encoder.finalize()
if (recording) {
const uint8Array = encoder.FS.readFile(encoder.outputFilename);
const anchor = document.createElement('a')
anchor.href = URL.createObjectURL(new Blob([uint8Array], { type: 'video/mp4' }))
anchor.download = encoder.outputFilename
anchor.click()
}
encoder.delete()
})
}
</script>
</body>
</html>
@Metamere
Copy link

This doesn't seem to work when I run it in the P5.js editor and hit record. The other non-looped example worked fine for me.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment