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

5

35

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!

Bless answered 3/7, 2013 at 19:57 Comment(3)
I have a similar post at #17508299 -- I'm having essentially the same problem, and I really hope someone answers your question.Mandragora
I saw your question yesterday. For me the file size is too big so uploading it to the server and converting it there is not a viable option. For your case, if you want to upload and then convert, using a VM is the best option.Bless
@ArjunBajaj did you find a solution to this? I am interested if you did.Endow
M
37

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/

Marylynnmarylynne answered 27/3, 2014 at 9:19 Comment(2)
THANK YOU, THANK YOU, THANK YOU. I wish I could upvote this 1000 timesFlywheel
@Remus Negrota, This works on Chrome, but hangs on Firefox. My research found, something goes infinite loop in the libmp3lame.min.js in Firefox. Are you using a modified version of libmp3lame.min.js?Skardol
D
4

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.

Donatello answered 8/7, 2013 at 15:26 Comment(0)
G
4

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

Gammon answered 21/11, 2013 at 1:50 Comment(0)
S
2

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

Scopoline answered 10/1, 2014 at 14:2 Comment(0)
V
2

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....

Victimize answered 26/9, 2014 at 3:42 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.