Skip to content

Instantly share code, notes, and snippets.

@jussi-kalliokoski
Created April 18, 2012 06:12
Show Gist options
  • Select an option

  • Save jussi-kalliokoski/2411407 to your computer and use it in GitHub Desktop.

Select an option

Save jussi-kalliokoski/2411407 to your computer and use it in GitHub Desktop.
Load an audio file into a Float32Array using Audio Data API
function mozLoadFile (url, callback) {
function throwAsync (err) {
setTimeout(function () {
callback(typeof err === 'string' ?
Error(err) : err);
}, 0);
}
function onaudioavailable (e) {
loadedmetadata();
var n, b, i, m;
for (n=0; n<channelCount; n++) {
b = new Float32Array(frameBufferLength / channelCount);
buffers[n].push(b);
for (i=n, m=0; i<frameBufferLength; i+=channelCount, m++) {
b[m] = e.frameBuffer[i];
}
}
length += frameBufferLength / channelCount;
}
function loadedmetadata () {
if (isMetaDataLoaded) {
return;
}
sampleRate = audio.mozSampleRate;
channelCount = audio.mozChannels;
frameBufferLength = audio.mozFrameBufferLength;
for (var n=0; n<channelCount; n++) {
buffers.push([]);
}
isMetaDataLoaded = true;
}
function onended () {
var i, b, d, o;
for (i=0; i<channelCount; i++) {
b = new Float32Array(length);
o = 0;
while (d = buffers[i].shift()) {
b.subarray(o, o + d.length).set(d);
o += d.length;
}
buffers[i] = b;
}
callback(undefined, {
sampleRate: sampleRate,
samples: buffers
});
}
var audio = document.createElement('audio');
var length = 0;
var buffers = [];
var sampleRate = 0;
var channelCount = 0;
var isMetaDataLoaded = false;
var frameBufferLength = 0;
if (!audio.mozSetup) {
throwAsync("No Audio Data API");
return;
}
audio.addEventListener('MozAudioAvailable', onaudioavailable, false);
audio.addEventListener('loadedmetadata', onloadedmetadata, false);
audio.addEventListener('ended', onended, false);
audio.addEventListener('error', throwAsync, false);
audio.muted = true;
audio.src = url;
audio.play();
}
@happyworm
Copy link

Hmm... My test seems to make audio (WAV or OGG) sound like Barry White. Looking to see if the data is getting doubled somewhere...

@happyworm
Copy link

In onaudioavailable():

for (i=n; i<frameBufferLength; i+=channelCount) {
    b[Math.floor(i/channelCount)] = e.frameBuffer[i];
}

@jussi-kalliokoski
Copy link
Author

Ahhh, I shouldn't have tested with a mono file. Should be fixed now, but I'm not sure, because I optimized it a bit. :P

@happyworm
Copy link

Yep, your code works fine. I knew mine was a hack.

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