diff --git a/app.js b/app.js index 82a4905..26763d2 100644 --- a/app.js +++ b/app.js @@ -211,6 +211,16 @@ document.addEventListener('DOMContentLoaded', function () { page.style.display = 'flex'; window.scroll(0, 0); + // Reset Read Me tabs to About when entering + if (pageId === '#read-me-page') { + document.querySelectorAll('.tab-btn').forEach(btn => { + btn.classList.toggle('active', btn.dataset.tab === 'about'); + }); + document.querySelectorAll('.tab-panel').forEach(panel => { + panel.classList.toggle('active', panel.id === 'tab-about'); + }); + } + if (pushState) { const newPath = pageId.replace('-page', ''); history.pushState({ page: pageId }, '', newPath); @@ -239,6 +249,28 @@ document.addEventListener('DOMContentLoaded', function () { }); }); + // --- Read Me Tabs --- + const tabButtons = document.querySelectorAll('.tab-btn'); + const tabPanels = document.querySelectorAll('.tab-panel'); + + tabButtons.forEach(button => { + button.addEventListener('click', () => { + const targetTab = button.dataset.tab; + + // Update button states + tabButtons.forEach(btn => btn.classList.remove('active')); + button.classList.add('active'); + + // Update panel visibility + tabPanels.forEach(panel => { + panel.classList.remove('active'); + if (panel.id === 'tab-' + targetTab) { + panel.classList.add('active'); + } + }); + }); + }); + window.addEventListener('popstate', (e) => { if (e.state && e.state.page && e.state.page !== 'main') { showPage(e.state.page, false); diff --git a/callfail.webp b/callfail.webp new file mode 100644 index 0000000..46f26c9 Binary files /dev/null and b/callfail.webp differ diff --git a/getinfo.webp b/getinfo.webp new file mode 100644 index 0000000..23bf4d3 Binary files /dev/null and b/getinfo.webp differ diff --git a/index.html b/index.html index 3600ce5..0fcd9f6 100644 --- a/index.html +++ b/index.html @@ -82,21 +82,48 @@ ← Back

Read Me

-

Welcome to the LEGO Island web port project! This is a recreation of the classic 1997 PC game, - rebuilt to run in modern web browsers using Emscripten.

-

This incredible project stands on the shoulders of giants. It was made possible by the original decompilation project, which was then adapted into a portable version. This represents a year-long effort, involving - thousands of hours of work from many awesome contributors dedicated to preserving this piece of - gaming history.

-

Our goal is to make this classic accessible to everyone. The project is still in development, so you - may encounter bugs. Your patience and feedback are greatly appreciated!

-
-

Frequently Asked Questions

-
+
+
+ + + +
+ +
+

Welcome to the LEGO Island web port project! This is a recreation of the classic 1997 PC game, + rebuilt to run in modern web browsers using Emscripten and WebAssembly.

+

This incredible project stands on the shoulders of giants. It was made possible by the original decompilation project, which achieved 100% decompilation of the + original game. This was then adapted into a portable version that eliminated all Windows dependencies and + replaced them with modern, cross-platform alternatives.

+

The technical work involved replacing Windows-specific systems with SDL for window management and input, + migrating audio from DirectSound to the miniaudio library, converting Windows Registry configuration + to INI files, and creating a modular graphics layer supporting multiple rendering backends including + WebGL. This represents years of effort from many awesome contributors dedicated to preserving this + piece of gaming history.

+

Thanks to this work, LEGO Island now runs on over 10 platforms including Windows, Linux, macOS, iOS, + Android, Nintendo Switch, PlayStation Vita, and of course, web browsers. The web version uses the + original, unmodified Interleaf streaming code, enabling progressive content loading just like the + original CD-ROM.

+

Our goal is to make this classic accessible to everyone. The project is still in development, so you + may encounter bugs. Your patience and feedback are greatly appreciated!

+
+ +
+
Is this the full, original game?

This is a complete port of the original 1997 PC game. You can select from multiple languages, including both the 1.0 and 1.1 versions of English, from the "Configure" menu before @@ -162,13 +189,12 @@ rel="noopener noreferrer">LEGO Island (portable) project, and the code for this website is also available here.

-
-
+
+
-
-

Changelog

-
- January 2026 +
+
+ January 2026
  • New: Debug menu for developers and power users. Tap the LEGO Island logo 5 times to unlock OGEL mode and access debug features like teleporting to locations, switching acts, and playing animations
@@ -264,8 +290,9 @@
  • Improved: Backface culling enabled for faster rendering
  • Improved: SIMD-optimized z-buffer clearing
  • Improved: Edge-walking triangle rasterization
  • - -
    + +
    +
    @@ -745,7 +772,7 @@ diff --git a/style.css b/style.css index 3b6e82b..5cd85fb 100644 --- a/style.css +++ b/style.css @@ -677,22 +677,86 @@ select { transition: background 0.2s ease-out; } -.faq-section { +/* Read Me Tabs */ +.readme-tabs { margin-top: 30px; - padding-top: 10px; + padding-top: 20px; border-top: 1px solid #444; width: 100%; +} + +.tab-buttons { + display: flex; + justify-content: center; + gap: 10px; + margin-bottom: 20px; +} + +.tab-btn { + display: flex; + align-items: center; + gap: 10px; + padding: 12px 24px; + background-color: #1c1c1c; + border: 2px solid #333; + border-radius: 8px; + color: #888; + font-size: 1em; + font-weight: bold; + cursor: pointer; + transition: all 0.2s ease; +} + +.tab-btn:hover { + background-color: #252525; + border-color: #555; + color: #c0c0c0; +} + +.tab-btn.active { + background-color: #2a2a00; + border-color: #FFD700; + color: #FFD700; +} + +.tab-icon { + width: 52px; + height: 52px; + object-fit: cover; + border-radius: 6px; + border: 1px solid #444; +} + +.tab-btn.active .tab-icon { + border-color: #FFD700; +} + +.tab-panel { + display: none; text-align: left; } -.faq-section h2 { - color: #FFD700; - font-size: 1.5em; - margin-bottom: 20px; - text-align: center; +.tab-panel.active { + display: block; } -.faq-section details { +.tab-panel > p { + color: #c0c0c0; + line-height: 1.6; + font-size: 1em; + margin-bottom: 15px; +} + +.tab-panel > p a { + color: #FFD700; + text-decoration: none; +} + +.tab-panel > p a:hover { + text-decoration: underline; +} + +.tab-panel details { background-color: #1c1c1c; border: 1px solid #333; border-radius: 8px; @@ -700,11 +764,11 @@ select { transition: background-color 0.2s ease; } -.faq-section details[open] { +.tab-panel details[open] { background-color: #252525; } -.faq-section summary { +.tab-panel summary { padding: 20px; cursor: pointer; font-weight: bold; @@ -716,22 +780,22 @@ select { align-items: center; } -.faq-section summary::-webkit-details-marker { +.tab-panel summary::-webkit-details-marker { display: none; } -.faq-section summary::after { +.tab-panel summary::after { content: '+'; font-size: 1.5em; color: #FFD700; transition: transform 0.2s ease-in-out; } -.faq-section details[open] summary::after { +.tab-panel details[open] summary::after { transform: rotate(45deg); } -.faq-section details p { +.tab-panel details p { padding: 0 20px 20px 20px; margin: 0; color: #b0b0b0; @@ -739,77 +803,23 @@ select { line-height: 1.5; } -.changelog-section { - margin-top: 30px; - padding-top: 10px; - border-top: 1px solid #444; - width: 100%; - text-align: left; -} - -.changelog-section h2 { - color: #FFD700; - font-size: 1.5em; - margin-bottom: 20px; - text-align: center; -} - -.changelog-section details { - background-color: #1c1c1c; - border: 1px solid #333; - border-radius: 8px; - margin-bottom: 10px; - transition: background-color 0.2s ease; -} - -.changelog-section details[open] { - background-color: #252525; -} - -.changelog-section summary { - padding: 20px; - cursor: pointer; - font-weight: bold; - color: #e0e0e0; - font-size: 1.1em; - list-style: none; - display: flex; - justify-content: space-between; - align-items: center; -} - -.changelog-section summary::-webkit-details-marker { - display: none; -} - -.changelog-section summary::after { - content: '+'; - font-size: 1.5em; - color: #FFD700; - transition: transform 0.2s ease-in-out; -} - -.changelog-section details[open] summary::after { - transform: rotate(45deg); -} - -.changelog-section details ul { +.tab-panel details ul { padding: 0 20px 20px 40px; margin: 0; } -.changelog-section details li { +.tab-panel details li { color: #b0b0b0; font-size: 0.9em; line-height: 1.6; margin-bottom: 8px; } -.changelog-section details li:last-child { +.tab-panel details li:last-child { margin-bottom: 0; } -.changelog-section details li strong { +.tab-panel details li strong { color: #FFD700; } @@ -870,6 +880,16 @@ select { .offline-play-text p { text-align: center; } + + .tab-btn { + padding: 10px 18px; + font-size: 0.9em; + } + + .tab-icon { + width: 42px; + height: 42px; + } } @media (max-width: 480px) { @@ -909,6 +929,21 @@ select { grid-template-columns: 1fr; gap: 25px; } + + .tab-buttons { + gap: 8px; + } + + .tab-btn { + padding: 8px 14px; + font-size: 0.85em; + gap: 8px; + } + + .tab-icon { + width: 36px; + height: 36px; + } } /* Debug UI Panel */ diff --git a/sw.js b/sw.js index a7a5e4a..22c1588 100644 --- a/sw.js +++ b/sw.js @@ -10,7 +10,7 @@ const { Strategy } = workbox.strategies; const { CacheableResponsePlugin } = workbox.cacheableResponse; const { RangeRequestsPlugin } = workbox.rangeRequests; -precacheAndRoute([{"revision":"0ef4d2c1ee11cc3d138d408267249252","url":"index.html"},{"revision":"013ceb7d67293d532e979dde0347f3af","url":"cancel_off.webp"},{"revision":"bfc1563be018d82685716c6130529129","url":"cancel_on.webp"},{"revision":"d282c260fd35522036936bb6faf8ad21","url":"cdspin.gif"},{"revision":"3d820bf72b19bd4e437a61e75f317b83","url":"configure_off.webp"},{"revision":"e2c0c5e6aa1f7703c385a433a2d2a519","url":"configure_on.webp"},{"revision":"88e1e81c930d8e6c24dfdc7af274e812","url":"favicon.png"},{"revision":"d16b293eca457e2fb1e7ef2caca8c904","url":"favicon.svg"},{"revision":"d2b9c2e128ef1e5e4265c603b0bc3305","url":"free_stuff_off.webp"},{"revision":"cbc6a6779897f932c3a3c8dceb329804","url":"free_stuff_on.webp"},{"revision":"05fba4ef1884cbbd6afe09ea3325efc0","url":"install_off.webp"},{"revision":"11247e92082ba3d978a2e3785b0acf51","url":"install_on.webp"},{"revision":"d23ea8243c18eb217ef08fe607097824","url":"island.webp"},{"revision":"b4754844f694858c2c08307a197c5434","url":"isle.js"},{"revision":"e66ee40529da22100b5f3d55d9aa1850","url":"isle.wasm"},{"revision":"6d4248f1a08c218943e582673179b7be","url":"poster.pdf"},{"revision":"a6fcac24a24996545c039a1755af33ea","url":"read_me_off.webp"},{"revision":"aae783d064996b4322e23b092d97ea4a","url":"read_me_on.webp"},{"revision":"766a9e6e6d890f24cef252e81753b29d","url":"run_game_off.webp"},{"revision":"70208e00e9ea641e4c98699f74100db3","url":"run_game_on.webp"},{"revision":"0a65c71d9983c9bb1bc6a5f405fd6fd9","url":"shark.webp"},{"revision":"88c1fd032e6fc16814690712a26c1ede","url":"uninstall_off.webp"},{"revision":"0118a4aca04c5fb0a525bf00b001844e","url":"uninstall_on.webp"},{"revision":"ca996b5ba6b648c6539758a669e83407","url":"app.js"},{"revision":"d2b2227044d4630c8f6f749a57b17d1d","url":"style.css"},{"revision":"060210979e13e305510de6285e085db1","url":"manifest.json"},{"revision":"4f0172bc7007d34cebf681cc233ab57f","url":"install.webp"},{"revision":"6a70d35dadf51d2ec6e38a6202d7fb0b","url":"install.mp3"},{"revision":"eac041a0b8835bfea706d997b0b7b224","url":"downloader.js"},{"revision":"6899f72755d4e84c707b93ac54a8fb06","url":"debug.js"},{"revision":"7817b36ddda9f07797c05a0ff6cacb21","url":"debug.html"},{"revision":"4ea2aac9446188b8a588811bc593919e","url":"ogel.webp"},{"revision":"c57d24598537443c5b8276c8dd5dbdc9","url":"bonus.webp"}]); +precacheAndRoute([{"revision":"4bcb2b00de15518f01e19e306fe5c427","url":"index.html"},{"revision":"013ceb7d67293d532e979dde0347f3af","url":"cancel_off.webp"},{"revision":"bfc1563be018d82685716c6130529129","url":"cancel_on.webp"},{"revision":"d282c260fd35522036936bb6faf8ad21","url":"cdspin.gif"},{"revision":"3d820bf72b19bd4e437a61e75f317b83","url":"configure_off.webp"},{"revision":"e2c0c5e6aa1f7703c385a433a2d2a519","url":"configure_on.webp"},{"revision":"88e1e81c930d8e6c24dfdc7af274e812","url":"favicon.png"},{"revision":"d16b293eca457e2fb1e7ef2caca8c904","url":"favicon.svg"},{"revision":"d2b9c2e128ef1e5e4265c603b0bc3305","url":"free_stuff_off.webp"},{"revision":"cbc6a6779897f932c3a3c8dceb329804","url":"free_stuff_on.webp"},{"revision":"05fba4ef1884cbbd6afe09ea3325efc0","url":"install_off.webp"},{"revision":"11247e92082ba3d978a2e3785b0acf51","url":"install_on.webp"},{"revision":"d23ea8243c18eb217ef08fe607097824","url":"island.webp"},{"revision":"c97d78e159b8bff44d41e56d0aa20220","url":"isle.js"},{"revision":"068bc71fd65d0d0f5b0006e3eba93f12","url":"isle.wasm"},{"revision":"6d4248f1a08c218943e582673179b7be","url":"poster.pdf"},{"revision":"a6fcac24a24996545c039a1755af33ea","url":"read_me_off.webp"},{"revision":"aae783d064996b4322e23b092d97ea4a","url":"read_me_on.webp"},{"revision":"766a9e6e6d890f24cef252e81753b29d","url":"run_game_off.webp"},{"revision":"70208e00e9ea641e4c98699f74100db3","url":"run_game_on.webp"},{"revision":"0a65c71d9983c9bb1bc6a5f405fd6fd9","url":"shark.webp"},{"revision":"88c1fd032e6fc16814690712a26c1ede","url":"uninstall_off.webp"},{"revision":"0118a4aca04c5fb0a525bf00b001844e","url":"uninstall_on.webp"},{"revision":"5c265d887349dca70d05a7a698cbc904","url":"app.js"},{"revision":"51c3e428a43da7caec47be6f88d095b3","url":"style.css"},{"revision":"060210979e13e305510de6285e085db1","url":"manifest.json"},{"revision":"4f0172bc7007d34cebf681cc233ab57f","url":"install.webp"},{"revision":"6a70d35dadf51d2ec6e38a6202d7fb0b","url":"install.mp3"},{"revision":"eac041a0b8835bfea706d997b0b7b224","url":"downloader.js"},{"revision":"6899f72755d4e84c707b93ac54a8fb06","url":"debug.js"},{"revision":"7817b36ddda9f07797c05a0ff6cacb21","url":"debug.html"},{"revision":"4ea2aac9446188b8a588811bc593919e","url":"ogel.webp"},{"revision":"c57d24598537443c5b8276c8dd5dbdc9","url":"bonus.webp"},{"revision":"d11c8c893d5525c8842555dc2861c393","url":"callfail.webp"},{"revision":"be9a89fb567b632cf8d4661cbf8afd9e","url":"getinfo.webp"},{"revision":"fe986681f41e96631f39f3288b23e538","url":"sysinfo.webp"}]); const gameFiles = [ "/LEGO/Scripts/CREDITS.SI", "/LEGO/Scripts/INTRO.SI", "/LEGO/Scripts/NOCD.SI", "/LEGO/Scripts/SNDANIM.SI", diff --git a/sysinfo.webp b/sysinfo.webp new file mode 100644 index 0000000..695a449 Binary files /dev/null and b/sysinfo.webp differ diff --git a/workbox-config.js b/workbox-config.js index f9c0294..2e6e158 100644 --- a/workbox-config.js +++ b/workbox-config.js @@ -8,7 +8,7 @@ module.exports = { 'read_me_on.webp', 'run_game_off.webp', 'run_game_on.webp', 'shark.webp', 'uninstall_off.webp', 'uninstall_on.webp', 'app.js', 'style.css', 'manifest.json', 'install.webp', 'install.mp3', 'downloader.js', 'debug.js', 'debug.html', 'ogel.webp', - 'bonus.webp' + 'bonus.webp', 'callfail.webp', 'getinfo.webp', 'sysinfo.webp' ], swSrc: 'src/sw.js', swDest: 'sw.js',