Skip to content

Instantly share code, notes, and snippets.

@curegit
Last active November 26, 2024 06:04
Show Gist options
  • Save curegit/b6c84eff634b84708a3bbeb5a7c72d07 to your computer and use it in GitHub Desktop.
Save curegit/b6c84eff634b84708a3bbeb5a7c72d07 to your computer and use it in GitHub Desktop.
Download a video via Media Capture and Streams API
async function newRecorder(
target = "stream",
querySelector = "video",
frameRate = 60,
systemAudio = false,
) {
let stream = null;
switch (target) {
// mediaStream (video/canvas)
case null:
case "":
case "stream":
stream = (
querySelector instanceof Element || querySelector instanceof Document
? querySelector
: document.querySelector(querySelector)
).captureStream(frameRate);
break;
// mediaStream (desktop/tabs)
case "display":
case "tab":
stream = await navigator.mediaDevices.getDisplayMedia({
video: true,
audio: true,
systemAudio: systemAudio ? "include" : "exclude",
});
break;
// mediaStream (user devices)
case "user":
case "camera":
stream = await navigator.mediaDevices.getUserMedia({
video: true,
audio: true,
});
break;
}
if (!stream) {
throw new Error("Wrong parameter or unexpected error!");
}
function initRecorder(stream) {
const mediaRecorder = new MediaRecorder(stream, {
mimeType: MediaRecorder.isTypeSupported("video/webm; codecs=vp9")
? "video/webm; codecs=vp9"
: "video/webm",
});
const chunks = [];
mediaRecorder.addEventListener("dataavailable", (e) => {
if (event.data.size > 0) {
chunks.push(e.data);
}
});
mediaRecorder.addEventListener("stop", () => {
const blob = new Blob(chunks, { type: chunks[0].type });
downloadWebm(blob);
});
return [chunks, mediaRecorder];
}
function downloadWebm(blob) {
const url = URL.createObjectURL(blob);
const a = document.createElement("a");
a.href = url;
a.download = `video-${now()}.webm`;
a.click();
}
function now() {
const now = new Date();
const year = now.getFullYear();
const month = `${now.getMonth() + 1}`.padStart(2, "0");
const date = `${now.getDate()}`.padStart(2, "0");
const hour = `${now.getHours()}`.padStart(2, "0");
const minute = `${now.getMinutes()}`.padStart(2, "0");
return `${year}${month}${date}-${hour}${minute}`;
}
return initRecorder(stream);
}
// Usage example 1: video stream
var [buf, r] = await newRecorder("stream", "video", 60);
r.start();
// Usage example 2: screen sharing
var [buf, r] = await newRecorder("display");
r.start();
// Call r.stop() to perform partial stop
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment