Converting WAV to any compressed audio format in client-side JavaScript

19,664

Solution 1

I've made an audio recorder that records to mp3 directly from the browser combining RecorderJS and libmp3lame.js

You can find the gitHub project here: https://github.com/nusofthq/Recordmp3js

and a more detailed explanation of the implementation: http://nusofthq.com/blog/recording-mp3-using-only-html5-and-javascript-recordmp3-js/

Solution 2

What you really want is the mediaStream "Recording API", which is currently being worked on. Until that's available, I advise using emscriptem on C/C++ source, and consider running it in a webworker to avoid blocking the UI and other tabs.

Solution 3

I was facing the same problem and came up with quite a quick and dirty solution:

  • zip the wav-file with zip.js (works with Chrome, Firefox, Safari 6 and Internet Explorer 10)

Further intel see Documentation zip.js

At least this is reducing size a lot, file is about >75% smaller so 1:4 compression

UPDATE: Maybe have a look at this: https://webrtc.github.io/samples/

It is a Chat Application for Chrome and Firefox developed by google, I assume with kind of CC-License

Solution 4

I had a similar issue (also using recorder.js) and have managed to resolve using the superb videoconverter.js project which includes a port of ffmpeg to Javascript using emscripen. Downside to this is the ffmpeg.js file is about 25Mb.

I modified the existing exportWAV function in recorderWorker.js to return both a WAV (for HTML5 <audio> playback) and a Blob containing an encoded MP2 file:

function encodeWAV(samples) {

  var buffer = new ArrayBuffer(44 + samples.length * 2);
  var view = new DataView(buffer);

  /* ... various writing methods */

  return { wavdata: new Blob([buffer], { type: "audio/wav" }), mp2data: ffmpeg_convert(buffer) };
}

function ffmpeg_convert(buffer) {
    console.log("starting mp2 conversion");
    var args = "-i input -f mp2 output.mp2";
    var results = ffmpeg_run({
        arguments: args.split(" "),
        files: [
          {
              data: new Uint8Array(buffer),
              "name": "input"
          }
        ]
    });
    if (results) {
        var file = results[0];
        console.log("File recieved", file.name, file.data);
        return new Blob([file.data], { type: "audio/mpeg" });
    }
    return null;
}

This method can be used to encode the WAV to any codec suppored by ffmpeg's libavcodec

Solution 5

I was able to achieve compression using opus.js,

you can find my implementation here: recordOpus, but there is a catch, mine is coupled with server-side, and I use node.js server....

Share:
19,664
Arjun Bajaj
Author by

Arjun Bajaj

I'm the Co-Founder of HeadOn Labs.

Updated on June 05, 2022

Comments

  • Arjun Bajaj
    Arjun Bajaj about 2 years

    I am recording audio from getUserMedia({audio:true}); in the browser using Recorder.js and then exporting it as a WAV file because that's the only option the library provides.

    A 1 minute 20 seconds file is 14.1 MB large. I need to upload the audio to a server and I need to do it fast. How do I convert the WAV audio in any other compressed format to lower the file size?

    I don't mind converting to:

    • MP3
    • Opus
    • WebM
    • Ogg
    • FLAC
    • any other format you know of

    If there is no way as of now to convert to any of these formats, how can I compress the WAV file on the client?

    PS: I did a lot of searches to find anything that converts WAV in JS, but found nothing. libmp3lame.js isn't working in Chrome.

    Thanks!