110 lines
3.3 KiB
JavaScript
110 lines
3.3 KiB
JavaScript
(() => {
|
|
const updateRate = 1000 / 10;
|
|
const sWidth = 224;
|
|
const sHeight = 208;
|
|
const colours = ['#0f9', '#ff9', '#f09', '#0ff', '#f0f'];
|
|
|
|
const gfx = document.querySelector('.sprite').getContext('2d');
|
|
const play = document.querySelector('.play');
|
|
const bars = Array.from(document.querySelectorAll('.bar'));
|
|
|
|
let audioBuffer;
|
|
const knowsWhatAnOpusIs = document.createElement('audio').canPlayType('audio/ogg;codecs=opus') !== '';
|
|
|
|
const displayPlayButton = () => {
|
|
play.onclick = () => { attemptPlay(); };
|
|
play.classList.remove('hidden');
|
|
};
|
|
|
|
const startAnimation = () => {
|
|
play.classList.add('hidden');
|
|
requestAnimationFrame(update);
|
|
};
|
|
|
|
const aud = (() => {
|
|
const audObj = window.AudioContext || window.webkitAudioContext;
|
|
try {
|
|
return new audObj({ latencyHint: 'playback' });
|
|
} catch(ex) {
|
|
return new audObj;
|
|
}
|
|
})();
|
|
|
|
const attemptPlay = () => {
|
|
play.onclick = null;
|
|
|
|
aud.resume().then(() => {
|
|
if(aud.state !== 'running') {
|
|
displayPlayButton();
|
|
return;
|
|
}
|
|
|
|
aud.decodeAudioData(audioBuffer)
|
|
.then(buffer => {
|
|
const source = aud.createBufferSource();
|
|
source.connect(aud.destination);
|
|
source.buffer = buffer;
|
|
source.loop = true;
|
|
source.start();
|
|
startAnimation();
|
|
})
|
|
.catch(ex => {
|
|
console.error(ex);
|
|
alert('Failed to decode audio, oops!');
|
|
startAnimation();
|
|
});
|
|
});
|
|
};
|
|
|
|
let sFrames;
|
|
const sprite = new Image;
|
|
sprite.onload = () => {
|
|
sFrames = sprite.height / sHeight;
|
|
|
|
const xhr = new XMLHttpRequest;
|
|
xhr.responseType = 'arraybuffer';
|
|
xhr.onload = () => {
|
|
audioBuffer = xhr.response;
|
|
|
|
if(aud.state === 'running')
|
|
attemptPlay();
|
|
else
|
|
displayPlayButton();
|
|
};
|
|
xhr.onerror = ex => {
|
|
console.error(ex);
|
|
alert('Failed to load audio, oops!');
|
|
startAnimation();
|
|
};
|
|
xhr.open('GET', `admin.${knowsWhatAnOpusIs ? 'opus' : 'caf'}`);
|
|
xhr.send();
|
|
};
|
|
sprite.src = 'lurkmoar.png';
|
|
|
|
let lastUpdate, updates = 0;
|
|
const update = t => {
|
|
try {
|
|
if(lastUpdate !== undefined && t - updateRate < lastUpdate)
|
|
return;
|
|
++updates;
|
|
lastUpdate = t;
|
|
|
|
gfx.canvas.width = gfx.canvas.clientWidth;
|
|
gfx.clearRect(0, 0, gfx.canvas.width, gfx.canvas.height);
|
|
|
|
const saWidth = sWidth * (gfx.canvas.clientHeight / sHeight);
|
|
gfx.drawImage(
|
|
sprite,
|
|
0, sHeight * (updates % sFrames),
|
|
sWidth, sHeight,
|
|
(gfx.canvas.width / 2) - (saWidth / 2), 0,
|
|
saWidth, gfx.canvas.height
|
|
);
|
|
|
|
for(let i = 0; i < bars.length; ++i)
|
|
bars[i].style.background = colours[(i + updates) % colours.length];
|
|
} finally {
|
|
requestAnimationFrame(update);
|
|
}
|
|
};
|
|
})();
|