How can I add predefined length to audio recorded from MediaRecorder in Chrome?

This is a chrome bug.

FF does expose the duration of the recorded media, and if you do set the currentTimeof the recorded media to more than its actual duration, then the property is available in chrome…

function exportAudio(blob) {
  const aud = document.getElementById("aud");
  aud.src = URL.createObjectURL(blob);
  aud.addEventListener("loadedmetadata", () => {
    // It should have been already available here
    console.log("duration:", aud.duration);
    // Handle chrome's bug
    if (aud.duration === Infinity) {
      // Set it to bigger than the actual duration
      aud.currentTime = 1e101;
      aud.addEventListener("timeupdate", () => {
        console.log("after workaround:", aud.duration);
        aud.currentTime = 0;
      }, { once: true });
    }
  });
}

// We need user-activation
document.getElementById("button").onclick = async ({ target }) => {
  target.remove();
  const resp = await fetch("https://upload.wikimedia.org/wikipedia/commons/4/4b/011229beowulf_grendel.ogg");
  const audioData = await resp.arrayBuffer();
  const ctx = new AudioContext();
  const audioBuf = await ctx.decodeAudioData(audioData);
  const source = ctx.createBufferSource();
  source.buffer = audioBuf;
  const dest = ctx.createMediaStreamDestination();
  source.connect(dest);

  const recorder = new MediaRecorder(dest.stream);
  const chunks = [];
  recorder.ondataavailable = ({data}) => chunks.push(data);
  recorder.onstop = () => exportAudio(new Blob(chunks));
  source.start(0);
  recorder.start();
  console.log("Recording...");
  // Record only 5 seconds
  setTimeout(function() {
    recorder.stop();
  }, 5000);

}
<button id="button">start</button>
<audio id="aud" controls></audio>

So the advice here would be to star the bug report so that chromium’s team takes some time to fix it, even if this workaround can do the trick…

Leave a Comment

tech