document.addEventListener('DOMContentLoaded', () => { const themeToggle = document.getElementById('theme-fab'); const themeIcon = document.getElementById('theme-icon'); const chapterSelects = document.querySelectorAll('.chapter-select'); const prevBtns = document.querySelectorAll('.prev-chapter'); const nextBtns = document.querySelectorAll('.next-chapter'); const comicPagesContainer = document.getElementById('comic-pages'); const storyOutline = document.querySelector('.story-outline-container'); const comicTitle = document.querySelector('.comic-title'); const modal = document.getElementById('fullscreen-modal'); const modalImg = document.getElementById('fullscreen-image'); const closeModal = document.querySelector('.close-modal'); // Protect modal image from download if (modalImg) { modalImg.draggable = false; modalImg.addEventListener('contextmenu', e => e.preventDefault()); } let comicsData = {}; let chapters = []; let currentChapterIndex = -1; let currentChapterPages = []; let currentModalPageIndex = -1; let touchStartX = 0; let touchEndX = 0; // Close modal events closeModal.addEventListener('click', () => { modal.classList.add('hidden'); }); function updateThemeIcon() { if (document.body.classList.contains('dark-mode')) { themeIcon.textContent = '🌙'; } else { themeIcon.textContent = '☀️'; } } // Theme toggle themeToggle.addEventListener('click', () => { document.body.classList.toggle('dark-mode'); updateThemeIcon(); localStorage.setItem('theme', document.body.classList.contains('dark-mode') ? 'dark' : 'light'); }); if (localStorage.getItem('theme') === 'dark') { document.body.classList.add('dark-mode'); updateThemeIcon(); } modal.addEventListener('click', (e) => { if (e.target !== modalImg) { modal.classList.add('hidden'); } }); function updateModalImage() { if (currentModalPageIndex >= 0 && currentModalPageIndex < currentChapterPages.length) { const chapterName = chapters[currentChapterIndex]; const pageFile = currentChapterPages[currentModalPageIndex]; modalImg.src = `assets/comic_book/${chapterName}/${pageFile}`; } } // Keyboard navigation document.addEventListener('keydown', (e) => { if (!modal.classList.contains('hidden')) { if (e.key === 'ArrowRight') { if (currentModalPageIndex < currentChapterPages.length - 1) { currentModalPageIndex++; updateModalImage(); } } else if (e.key === 'ArrowLeft') { if (currentModalPageIndex > 0) { currentModalPageIndex--; updateModalImage(); } } else if (e.key === 'Escape') { modal.classList.add('hidden'); } } }); // Touch navigation (swipe) modal.addEventListener('touchstart', (e) => { touchStartX = e.changedTouches[0].screenX; }); modal.addEventListener('touchend', (e) => { touchEndX = e.changedTouches[0].screenX; handleSwipe(); }); function handleSwipe() { const swipeThreshold = 50; if (touchEndX < touchStartX - swipeThreshold) { // Swipe Left (Next) if (currentModalPageIndex < currentChapterPages.length - 1) { currentModalPageIndex++; updateModalImage(); } } if (touchEndX > touchStartX + swipeThreshold) { // Swipe Right (Prev) if (currentModalPageIndex > 0) { currentModalPageIndex--; updateModalImage(); } } } // Fetch the index JSON fetch('comics_index.json') .then(response => response.json()) .then(data => { comicsData = data; chapters = Object.keys(comicsData); // Populate select chapters.forEach((chapter, index) => { // Format chapter name (e.g., 'chapter01' -> 'CHAPTER 01') const formattedName = chapter.replace(/([a-zA-Z]+)(\d+)/, '$1 $2').toUpperCase(); chapterSelects.forEach(select => { const option = document.createElement('option'); option.value = index; option.textContent = formattedName; select.appendChild(option); }); }); }) .catch(err => { console.error("Error loading comics index", err); comicPagesContainer.innerHTML = `
`; }); function loadChapter(index) { if (index < 0 || index >= chapters.length) return; currentChapterIndex = index; const chapterName = chapters[index]; const pages = comicsData[chapterName]; currentChapterPages = pages; // Update select UI chapterSelects.forEach(s => s.value = index); // Update buttons prevBtns.forEach(btn => btn.disabled = index === 0); nextBtns.forEach(btn => btn.disabled = index === chapters.length - 1); // Hide story outline when viewing comics if (storyOutline) { storyOutline.style.display = 'none'; } // Show loader comicPagesContainer.innerHTML = '