sono
Version:
A simple yet powerful JavaScript library for working with Web Audio
198 lines (177 loc) • 4.56 kB
JavaScript
;
exports.__esModule = true;
exports.default = BufferSource;
function BufferSource(buffer, context, endedCallback) {
var api = {};
var ended = false;
var loop = false;
var paused = false;
var cuedAt = 0;
var playbackRate = 1;
var playing = false;
var sourceNode = null;
var startedAt = 0;
function createSourceNode() {
if (!sourceNode && context) {
sourceNode = context.createBufferSource();
sourceNode.buffer = buffer;
}
return sourceNode;
}
/*
* Controls
*/
function stop() {
if (sourceNode) {
sourceNode.onended = null;
try {
sourceNode.disconnect();
sourceNode.stop(0);
} catch (e) {}
sourceNode = null;
}
paused = false;
cuedAt = 0;
playing = false;
startedAt = 0;
}
function pause() {
var elapsed = context.currentTime - startedAt;
stop();
cuedAt = elapsed;
playing = false;
paused = true;
}
function endedHandler() {
stop();
ended = true;
if (typeof endedCallback === 'function') {
endedCallback(api);
}
}
function play() {
var delay = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 0;
var offset = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
if (playing) {
return;
}
delay = delay ? context.currentTime + delay : 0;
if (offset) {
cuedAt = 0;
}
if (cuedAt) {
offset = cuedAt;
}
while (offset > api.duration) {
offset = offset % api.duration;
}
createSourceNode();
sourceNode.onended = endedHandler;
sourceNode.start(delay, offset);
sourceNode.loop = loop;
sourceNode.playbackRate.value = playbackRate;
startedAt = context.currentTime - offset;
ended = false;
paused = false;
cuedAt = 0;
playing = true;
}
/*
* Destroy
*/
function destroy() {
stop();
buffer = null;
context = null;
endedCallback = null;
sourceNode = null;
}
/*
* Getters & Setters
*/
Object.defineProperties(api, {
play: {
value: play
},
pause: {
value: pause
},
stop: {
value: stop
},
destroy: {
value: destroy
},
currentTime: {
get: function get() {
if (cuedAt) {
return cuedAt;
}
if (startedAt) {
var time = context.currentTime - startedAt;
while (time > api.duration) {
time = time % api.duration;
}
return time;
}
return 0;
},
set: function set(value) {
cuedAt = value;
}
},
duration: {
get: function get() {
return buffer ? buffer.duration : 0;
}
},
ended: {
get: function get() {
return ended;
}
},
loop: {
get: function get() {
return loop;
},
set: function set(value) {
loop = !!value;
if (sourceNode) {
sourceNode.loop = loop;
}
}
},
paused: {
get: function get() {
return paused;
}
},
playbackRate: {
get: function get() {
return playbackRate;
},
set: function set(value) {
playbackRate = value;
if (sourceNode) {
sourceNode.playbackRate.value = playbackRate;
}
}
},
playing: {
get: function get() {
return playing;
}
},
progress: {
get: function get() {
return api.duration ? api.currentTime / api.duration : 0;
}
},
sourceNode: {
get: function get() {
return createSourceNode();
}
}
});
return Object.freeze(api);
}