Audio API: Fail to resume music and also visualize it. Is there bug in html5-audio? - html

I have a button. Every time it is clicked, a music is played. When it's clicked the second time, the music resumes. I also want to visualize the music.
So i begin with html5 audio (complete code in http://jsfiddle.net/karenpeng/PAW7r/):
$("#1").click(function(){
audio1.src = '1.mp3';
audio1.controls = true;
audio1.autoplay = true;
audio1.loop = true;
source = context.createMediaElementSource(audio1);
source.connect(analyser);
analyser.connect(context.destination);
});
But when it's clicked more than once, it console.log error:
Uncaught Error: INVALID_STATE_ERR: DOM Exception 11
Then i change to use web audio API, and change the source to:
source = context.createBufferSource();
The error is gone.
And then, i need to visualize it.
But ironicly, it only works in html5 audio!
(complete code in http://jsfiddle.net/karenpeng/FvgQF/, it does not work in jsfiddle cuz i dont know how to write processing.js script properly, but it does run on my pc)
var audio = new Audio();
audio.src = '2.mp3';
audio.controls = true;
audio.autoplay = true;
audio.loop=true;
var context = new webkitAudioContext();
var analyser = context.createAnalyser();
var source = context.createMediaElementSource(audio);
source.connect(analyser);
analyser.connect(context.destination);
var freqData = new Uint8Array(analyser.frequencyBinCount);
analyser.getByteFrequencyData(freqData);
//visualization using freqData
when i change the source to :
source = context.createBufferSource();
it does not show anything.
So is there way to visualize it and yet without error and enable it to resume again and again?

Actually, I believe the problem is that you're trying to create a SECOND web audio node for the same media element. (Your code, when clicked, re-sets the SRC, controls, etc., but it's not creating a new Audio().) You should either hang on to the MediaElementAudioSourceNode you created, or create new Audio elements.
E.g.:
var context = new webkitAudioContext();
var analyser = context.createAnalyser();
var source = null;
var audio0 = new Audio();
$("#0").click(function(){
audio0.src = 'http://www.bornemark.se/bb/mp3_demos/PoA_Sorlin_-_Stay_Up.mp3';
audio0.controls = true;
audio0.autoplay = true;
audio0.loop = true;
if (source==null) {
source = context.createMediaElementSource(audio0);
source.connect(analyser);
analyser.connect(context.destination);
}
});​
Hope that helps!
-Chris Wilson

From what I can tell, this is likely because the MediaElementSourceNode may only be able to take in an Audio that isn't already playing. The Audio object is declared outside of the click handler, so you're trying to analyze audio that's in the middle of playing the second time you click.
Note that the API doesn't seem to specify this, so I'm not 100% sure, but this makes intuitive sense.

Related

Empty microphone data from getUserMedia

Using the following code I get all zeroes in the audio stream from my microphone (using Chrome):
navigator.mediaDevices.getUserMedia({audio:true}).then(
function(stream) {
var audioContext = new AudioContext();
var source = audioContext.createMediaStreamSource(stream);
var node = audioContext.createScriptProcessor(8192, 1, 1);
source.connect(node);
node.connect(audioContext.destination);
node.onaudioprocess = function (e) {
console.log("Audio:", e.inputBuffer.getChannelData(0));
};
}).catch(function(error) {console.error(error);})
I created a jsfiddle here: https://jsfiddle.net/g3dck4dr/
What's wrong here?
Umm, something in your hardware config is wrong? The fiddle works fine for me (that is, it shows non-zero values). Do other web audio input tests work, like https://webaudiodemos.appspot.com/input/index.html?
Test to make sure you've selected the right input, and you don't have a hardware mute switch on.

How to play html5 game offline?

I wanted to save some html5 games on the laptop for my little brother to play when he's out of wifi range. I downloaded all the files and changed the paths so that no erros appear.
Now when I open index.html a blank page oppen with a loader gif and nothing else loads. I dont understand why? No errors are thrown. The only error is the one that it cannot find ads (when loadvoyager is called). I tried to comment it, still nothing positively happends.
This is an archive of the game: https://www.dropbox.com/s/5x3dk7w693j3os1/caca.rar?dl=0
Thank you!
Solution
Go to this site:
http://scotty-staging.softgames.de/assets/api/voyager.js
or use this mirror i created:
File only : http://www.mediafire.com/download/4b8uhvm75fbqtwy/voyager.js
Full game: http://www.mediafire.com/download/y8ocia4rr5552jx/html5Game.7z
Save the javascript file in assets and than you can play the game.
update ( problem )
var displayLoadScrn = function(){
var body = SG.d.getElementsByTagName('body')[0];
if( typeof body != "undefined" ){
if( SG.d.getElementById('sg-loadscrn') == null ){
SG.debug && console.log('show load-screen: complete');
body.appendChild(loadScrn);
}
SG.loadVoyager(); //<---- This is where it goes wrong //
}
else{
if(SG.debug) console.log('show load-screen: body-tag not ready. retrying in '+SG.loadScrnTimer+'ms');
setTimeout(displayLoadScrn,SG.loadScrnTimer);
}
};
displayLoadScrn();
var displayImage = function(){
var body = SG.d.getElementsByTagName('body')[0];
if( typeof body != "undefined" ){
body.appendChild(loadScrn);
SG.loadVoyager(); //<---- This is where it also goes wrong //
}
else{
if(SG.debug) console.log('show load-screen: body-tag not ready. retrying in '+SG.loadScrnTimer+'ms');
setTimeout(displayImage,SG.loadScrnTimer);
}
};
displayImage();
The problem is that you didnt provide the voyager resource script in the assets folder, but it needs to be loaded
loadVoyager : function(){
var sgc = document.createElement('script'); sgc.type = 'text/javascript'; sgc.async = true;
var random = Math.floor((Math.random()*100000000)+1);
//sgc.src = 'http://scotty-staging.softgames.de/assets/api/voyager.js';
sgc.src = 'assets/voyager.js?_='+random; //<-- this line //
//sgc.src = '//localhost:3000/assets/api/voyager.js';
sgc.onload = SG.boot;
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(sgc, s);
},
You see the middle "sgc.src = 'assets/voyager.js?='+random;" , that is still trying to load, what I did is removing the commented out lines, I kept the "sgc.src = 'assets/voyager.js?='+random;" uncommented and downloaded the voyager file and placed it in the assets folder.
You cannot comment out the loadvoyager, because it needs to be loaded. Otherwise your page will be loading all the time, with not response
Looks like a file named voyager.js is missing from the assets folder. Open the console in the browser for this detail(F12 in Chrome).
And just to be on the safer side try opening this game through a local-server this way you don't have to worry about all the things the browser is concerned about when running the game.

Popup keeps showing up on iPad because it won't accept cookies

I have made a popup that is meant to load when my website loads.
I have added a cookie to remember if the user has seen the popup after closing it, so that they are not presented with the popup again. It's working well, apart from on the iPad the popup loads on every single page of the site.
Does anyone know the best way around this?
My cookie code is:
function SetCookie(cookieName,cookieValue,nDays) {
var today = new Date();
var expire = new Date();
if (nDays==null || nDays==0) nDays=1;
expire.setTime(today.getTime() + 3600000*24*nDays);
document.cookie = cookieName+"="+escape(cookieValue)
+ ";expires="+expire.toGMTString();
}
$("#member").click(function(){
SetCookie("subscribed","1");
$( "#Subscribe" ).dialog("close");
return false;
});
Give HTML5 Storage a try! See: http://www.w3schools.com/html/html5_webstorage.asp
// store an item in the localstorage
localStorage.setItem('popup_shown', true);
// get an item from localstorage
var popupShown = localStorage.getItem('popup_shown');

Web Audio API: How to load another audio file?

I want to write a basic script for HTML5 Web Audio API, can play some audio files. But I don't know how to unload a playing audio and load another one. In my script two audio files are playing in the same time,but not what I wanted.
Here is my code:
var context,
soundSource,
soundBuffer;
// Step 1 - Initialise the Audio Context
context = new webkitAudioContext();
// Step 2: Load our Sound using XHR
function playSound(url) {
// Note: this loads asynchronously
var request = new XMLHttpRequest();
request.open("GET", url, true);
request.responseType = "arraybuffer";
// Our asynchronous callback
request.onload = function() {
var audioData = request.response;
audioGraph(audioData);
};
request.send();
}
// This is the code we are interested in
function audioGraph(audioData) {
// create a sound source
soundSource = context.createBufferSource();
// The Audio Context handles creating source buffers from raw binary
soundBuffer = context.createBuffer(audioData, true/* make mono */);
// Add the buffered data to our object
soundSource.buffer = soundBuffer;
// Plug the cable from one thing to the other
soundSource.connect(context.destination);
// Finally
soundSource.noteOn(context.currentTime);
}
// Stop all of sounds
function stopSounds(){
// How can do this?
}
// Events for audio buttons
document.querySelector('.pre').addEventListener('click',
function () {
stopSounds();
playSound('http://thelab.thingsinjars.com/web-audio-tutorial/hello.mp3');
}
);
document.querySelector('.next').addEventListener('click',
function() {
stopSounds();
playSound('http://thelab.thingsinjars.com/web-audio-tutorial/nokia.mp3');
}
);
You should be pre-loading sounds into buffers once, at launch, and simply resetting the AudioBufferSourceNode whenever you want to play it back.
To play multiple sounds in sequence, you need to schedule them using noteOn(time), one after the other, based on buffer respective lengths.
To stop sounds, use noteOff.
Sounds like you are missing some fundamental web audio concepts. This (and more) is described in detail and shown with samples in this HTML5Rocks tutorial and the FAQ.

Safari - HTML5 Audio

I'm using javascript to dynamically populate the audio tag with source info. Works fine in Chrome, but in Safari the source info changes within the audio tag and yet it plays the same song. Any ideas as to why this would be happening?
http://www.chicagowebguru.com/HTML5Player/
In Safari, when you change the source, you also have to call .load() on the audio player to get it to actually load the new source.
Other browsers don't need this it seems.
Have you tried recreating the node?
document.removeChild(document.getElementById("audio-player");
var dynamicAudio = document.createElement("audio");
dynamicAudio.name = "audio-player";
dynamicAudio.id = "audio-player";
var dynamicSound1 = document.createElement("source");
var dynamicSound2 = document.createElement("source");
var dynamicSound3 = document.createElement("source");
dynamicSound1.src = "http://www.chicagowebguru.com/audio/RainbowConnection.mp3";
dynamicSound2.src = "http://www.chicagowebguru.com/audio/RainbowConnection.ogg";
dynamicSound3.src = "http://www.chicagowebguru.com/audio/RainbowConnection.wav";
dynamicAudio.appendChild(dynamicSound1);
dynamicAudio.appendChild(dynamicSound2);
dynamicAudio.appendChild(dynamicSound3);
refNode = document.getElementById("message-container");
document.body.insertBefore(dynamicAudio,refNode.nextSibling);
or you could use jQuery maybe