/** * System takes care of updating all the entities (based on their component data) * @param apiSystem GameLib.API.System * @constructor */ GameLib.System.Audio = function( apiSystem ) { GameLib.System.call( this, apiSystem ); this.instanceCreatedSubscription = null; this.removeComponentSubscription = null; this.playAudioSubscription = null; this.pauseAllAudioSubscription = null; this.muteAudioSubscription = null; this.continueAllAudioSubscription = null; this.stopAudioSubscription = null; this.stopAllAudioSubscription = null; this.mute = false; this.paused = []; this.audioComponents = []; this.toPlay = []; }; GameLib.System.Audio.prototype = Object.create(GameLib.System.prototype); GameLib.System.Audio.prototype.constructor = GameLib.System.Audio; /** * Start this system (add all event listeners) */ GameLib.System.Audio.prototype.start = function() { GameLib.System.prototype.start.call(this); this.instanceCreatedSubscription = GameLib.Event.Subscribe( GameLib.Event.INSTANCE_CREATED, this.instanceCreated.bind(this) ); this.removeComponentSubscription = GameLib.Event.Subscribe( GameLib.Event.REMOVE_COMPONENT, this.removeComponent.bind(this) ); this.playAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.PLAY_AUDIO, this.playAudio.bind(this) ); this.pauseAllAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.PAUSE_ALL_AUDIO, this.pauseAllAudio.bind(this) ); this.muteAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.MUTE_AUDIO, this.muteAudio.bind(this) ); this.continueAllAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.CONTINUE_ALL_AUDIO, this.continueAllAudio.bind(this) ); this.stopAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.STOP_AUDIO, this.stopAudio.bind(this) ); this.stopAllAudioSubscription = GameLib.Event.Subscribe( GameLib.Event.STOP_ALL_AUDIO, this.stopAllAudio.bind(this) ); }; /** * From now on we want to track everything about a component, only from the systems that are active * @param data */ GameLib.System.Audio.prototype.instanceCreated = function(data) { if (data.component instanceof GameLib.D3.Audio) { GameLib.Utils.PushUnique(this.audioComponents, data.component); data.component.instance.onEnded = function() { this.isPlaying = false; GameLib.Event.Emit( GameLib.Event.AUDIO_ENDED, { audio : data.component } ); }; var index = this.toPlay.indexOf(data.component.name); if (index !== -1) { GameLib.Event.Emit( GameLib.Event.PLAY_AUDIO, { name : data.component.name } ); this.toPlay.splice(index, 1); } } }; /** * Removes a particle engine from this system * @param data */ GameLib.System.Audio.prototype.playAudio = function(data) { var found = false; this.audioComponents.map( function(audio) { if (audio.name === data.name) { found = true; if (!audio.instance) { console.log('audio not ready yet'); } // if (this.mute && typeof audio.backupVolume === 'undefined') { // audio.backupVolume = audio.volume; // audio.volume = 0; // audio.updateInstance('volume'); // } // // if (!this.mute && typeof audio.backupVolume === 'number') { // audio.volume = audio.backupVolume; // delete audio.backupVolume; // audio.updateInstance('volume'); // } if (audio.overplay) { if (audio.instance.isPlaying) { audio.instance.stop(); } audio.instance.offset = 0; audio.instance.play(); } else if (!audio.instance.isPlaying) { audio.instance.play(); } } }.bind(this) ); if (!found) { /** * This audio still has to load */ console.log('delaying audio play until loaded for: ' + data.name); this.toPlay.push(data.name); } }; GameLib.System.Audio.prototype.pauseAllAudio = function(data) { this.paused = []; this.audioComponents.map( function(audio) { if (audio.instance.isPlaying) { this.paused.push(audio); // audio.currentTime = audio.instance.context.currentTime; audio.paused = true; audio.updateInstance('paused'); } }.bind(this) ) }; GameLib.System.Audio.prototype.continueAllAudio = function(data) { this.paused.map( function(audio) { // audio.instance.context.currentTime = audio.currentTime; audio.paused = false; audio.updateInstance('paused'); } ); this.paused = []; }; GameLib.System.Audio.prototype.stopAllAudio = function(data) { this.audioComponents.map( function(audio) { if (audio.instance.isPlaying) { audio.instance.stop(); } } ) }; GameLib.System.Audio.prototype.stopAudio = function(data) { this.audioComponents.map( function(audio) { if (audio.name === data.name) { if (audio.instance.isPlaying) { audio.instance.stop(); } } } ) }; GameLib.System.Audio.prototype.removeComponent = function(data) { }; GameLib.System.Audio.prototype.muteAudio = function() { this.mute = !this.mute; if (this.mute) { this.audioVolumes = this.audioComponents.reduce( function(result, audio) { result.push( { audio : audio, volume : audio.volume } ); audio.volume = 0; audio.updateInstance('volume'); return result; }, [] ); GameLib.Event.Emit(GameLib.Event.AUDIO_MUTED, {audioSystem:this}); } else { this.audioVolumes.map( function(audioVolume) { audioVolume.audio.volume = audioVolume.volume; audioVolume.audio.updateInstance('volume'); } ); GameLib.Event.Emit(GameLib.Event.AUDIO_UNMUTED, {audioSystem:this}); } }; /** * Stop this system (remove all event listeners) */ GameLib.System.Audio.prototype.stop = function() { GameLib.System.prototype.stop.call(this); this.instanceCreatedSubscription.remove(); this.removeComponentSubscription.remove(); this.playAudioSubscription.remove(); this.pauseAllAudioSubscription.remove(); this.muteAudioSubscription.remove(); this.continueAllAudioSubscription.remove(); this.stopAudioSubscription.remove(); this.stopAllAudioSubscription.remove(); };