202 lines
5.5 KiB
JavaScript
202 lines
5.5 KiB
JavaScript
const PRELOAD_BACKWARD = 2;
|
|
const PRELOAD_FORWARD = 8;
|
|
|
|
document.addEventListener('DOMContentLoaded', () => {
|
|
const currentImage = document.getElementById('current-image');
|
|
const preloadImages = document.getElementById('preload-images');
|
|
|
|
let currentPage = parseInt(localStorage.getItem(`${WORK_ID}-currentPage`)) || 0;
|
|
let duration = parseInt(localStorage.getItem(`${WORK_ID}-duration`)) || 10;
|
|
let rtl = (localStorage.getItem(`${WORK_ID}-rtl`) !== "false");
|
|
let paused = true;
|
|
|
|
let elapsed = 0;
|
|
let timerLastRun = null;
|
|
let timerAnimationRequestID = null;
|
|
|
|
function requestTimer() {
|
|
timerAnimationRequestID = window.requestAnimationFrame(runTimer);
|
|
}
|
|
|
|
function runTimer(now) {
|
|
if (paused) {
|
|
return;
|
|
}
|
|
|
|
if (timerLastRun === null) {
|
|
elapsed = 0;
|
|
} else {
|
|
elapsed += now - timerLastRun;
|
|
}
|
|
timerLastRun = now;
|
|
|
|
if (elapsed >= duration*1000) {
|
|
changePage(currentPage + 1);
|
|
elapsed = 0;
|
|
}
|
|
|
|
updateBar();
|
|
|
|
requestTimer();
|
|
}
|
|
|
|
const progressBar = document.getElementById('progress');
|
|
function updateBar() {
|
|
progressBar.style.width = `${100*elapsed/(1000*duration)}%`;
|
|
}
|
|
|
|
function stopTimer() {
|
|
if (timerAnimationRequestID) {
|
|
window.cancelAnimationFrame(timerAnimationRequestID);
|
|
timerAnimationRequestID = null;
|
|
}
|
|
timerLastRun = null;
|
|
elapsed = 0;
|
|
updateBar();
|
|
}
|
|
|
|
function imageSrc(s) {
|
|
const img = new Image();
|
|
img.src = s;
|
|
return img;
|
|
}
|
|
|
|
function preload() {
|
|
if (!currentImage.getElementsByTagName('img')[0].complete) {
|
|
setTimeout(preload, 50);
|
|
return;
|
|
}
|
|
|
|
preloadImages.replaceChildren(...(
|
|
IMAGES.slice(
|
|
Math.max(currentPage - PRELOAD_BACKWARD, 0),
|
|
currentPage + PRELOAD_FORWARD + 1,
|
|
).map(imageSrc)
|
|
));
|
|
}
|
|
|
|
function changePage(pageNum) {
|
|
elapsed = 0;
|
|
updateBar();
|
|
|
|
const previous = IMAGES[currentPage];
|
|
const current = IMAGES[pageNum];
|
|
|
|
if (current == null) {
|
|
return;
|
|
}
|
|
|
|
currentPage = pageNum;
|
|
localStorage.setItem(`${WORK_ID}-currentPage`, currentPage);
|
|
|
|
currentImage.replaceChildren(imageSrc(current));
|
|
|
|
document.getElementById('current-page').innerText = (pageNum + 1).toLocaleString();
|
|
|
|
setTimeout(preload, 1);
|
|
}
|
|
|
|
const durationDisplay = document.getElementById('duration');
|
|
function changeDuration(secs, pause) {
|
|
duration = secs;
|
|
localStorage.setItem(`${WORK_ID}-duration`, duration);
|
|
paused = pause;
|
|
|
|
durationDisplay.textContent = duration.toLocaleString() + 's';
|
|
if (paused) {
|
|
durationDisplay.style.textDecoration = "line-through 2px";
|
|
stopTimer();
|
|
} else {
|
|
durationDisplay.style.textDecoration = "";
|
|
requestTimer();
|
|
}
|
|
}
|
|
|
|
function left() {
|
|
if (currentPage === 0) {
|
|
rtl = true;
|
|
localStorage.setItem(`${WORK_ID}-rtl`, rtl);
|
|
}
|
|
changePage(currentPage + (rtl ? 1 : -1));
|
|
}
|
|
|
|
function right() {
|
|
if (currentPage === 0) {
|
|
rtl = false;
|
|
localStorage.setItem(`${WORK_ID}-rtl`, rtl);
|
|
}
|
|
changePage(currentPage + (rtl ? -1 : 1));
|
|
}
|
|
|
|
function restart() {
|
|
changePage(0);
|
|
}
|
|
|
|
function exitToWork() {
|
|
changeDuration(duration, true);
|
|
if (currentPage === IMAGES.length - 1) {
|
|
localStorage.removeItem(`${WORK_ID}-currentPage`);
|
|
}
|
|
window.location.href = `../${INDEX}`;
|
|
}
|
|
|
|
function hideTapZones() {
|
|
document.getElementById('controls').style.opacity = 0;
|
|
}
|
|
|
|
changePage(currentPage);
|
|
changeDuration(duration, paused);
|
|
|
|
document.onkeydown = event => {
|
|
hideTapZones();
|
|
|
|
switch (event.key) {
|
|
case "ArrowLeft":
|
|
event.preventDefault();
|
|
left();
|
|
break;
|
|
case "ArrowRight":
|
|
event.preventDefault();
|
|
right();
|
|
break;
|
|
case " ":
|
|
event.preventDefault();
|
|
changeDuration(duration, !paused);
|
|
break;
|
|
case "ArrowUp":
|
|
event.preventDefault();
|
|
if (2 <= duration && duration <= 10) {
|
|
changeDuration(duration - 1, false);
|
|
} else if (10 < duration && duration <= 20) {
|
|
changeDuration(duration - 2.5, false);
|
|
} else if (20 < duration) {
|
|
changeDuration(duration - 5, false);
|
|
}
|
|
break;
|
|
case "ArrowDown":
|
|
event.preventDefault();
|
|
if (duration < 10) {
|
|
changeDuration(duration + 1, false);
|
|
} else if (10 <= duration && duration < 20) {
|
|
changeDuration(duration + 2.5, false);
|
|
} else if (20 <= duration) {
|
|
changeDuration(duration + 5, false);
|
|
}
|
|
break;
|
|
case "Enter":
|
|
event.preventDefault();
|
|
restart();
|
|
break;
|
|
case "Escape":
|
|
event.preventDefault();
|
|
exitToWork();
|
|
break;
|
|
}
|
|
};
|
|
|
|
document.onclick = hideTapZones;
|
|
document.getElementById("tap-left").onclick = left;
|
|
document.getElementById("tap-right").onclick = right;
|
|
document.getElementById("tap-restart").onclick = restart;
|
|
document.getElementById("tap-back").onclick = exitToWork;
|
|
});
|