diff --git a/CLAUDE.md b/CLAUDE.md index 69405f4..a396f0f 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -86,8 +86,8 @@ The five current objectives are: | `source/core/input/` | New input layer | Free to modify | | `source/utils/` | New utilities | Free to modify | | `source/game/options,defines,defaults` | New config system | Free to modify | -| `data/*.gif, *.ogg` | Original assets | **Do not modify** — assets remain untouchable | -| `data/fonts/, data/ui/, data/shaders/` | New assets | Free to modify | +| `data/gfx/, data/music/` | Original assets | **Do not modify** — assets remain untouchable | +| `data/fonts/, data/shaders/, data/locale/` | New assets | Free to modify | ### Legacy "Jail" Engine (`source/core/jail/`) — modernization target @@ -265,11 +265,11 @@ Checksum: djb2-like amb seed `0x12345678`. Càrrega full-to-RAM (sense mmap). ### Data Assets (`data/`) -- `*.gif`, `*.ogg` — Original game assets (**do not modify**) +- `gfx/` — Original game GIFs (**do not modify content**): `frames.gif`/`frames2.gif` (sprite sheet del joc), `logo.gif`/`logo_new.gif` (intros), `menu.gif`/`menu2.gif`, `intro.gif`/`intro2.gif`/`intro3.gif` (slides), `ffase.gif` (banner nivells), `final.gif`/`finals.gif` (crèdits), `gameover.gif`, `tomba1.gif`/`tomba2.gif` (escena secreta) +- `music/` — 8 pistes OGG originals (`00000001.ogg`..`00000008.ogg`) - `fonts/8bithud.fnt + .gif` — Bitmap font for overlay (8×8, 124 glyphs, UTF-8 with accents) - `shaders/` — GLSL sources: `postfx.vert`, `postfx.frag`, `upscale.frag`, `downscale.frag`, `crtpi_frag.glsl` - `locale/ca.yaml` — UI strings in Valencian (menu titles/items/values, notifications). Edit freely; reload at restart -- `ui/` — Reserved for future UI graphics ### Known Issues & Technical Debt diff --git a/resource.pack b/resource.pack index 469bd28..989554b 100644 Binary files a/resource.pack and b/resource.pack differ diff --git a/source/core/resources/resource_helper.hpp b/source/core/resources/resource_helper.hpp index 2283a5b..a4df9b4 100644 --- a/source/core/resources/resource_helper.hpp +++ b/source/core/resources/resource_helper.hpp @@ -17,7 +17,7 @@ namespace ResourceHelper { // Allibera el pack carregat a memòria. void shutdownResourceSystem(); - // Llegeix un recurs per ruta relativa (p.ex. "logo.gif", "fonts/8bithud.fnt"). + // Llegeix un recurs per ruta relativa (p.ex. "gfx/logo.gif", "fonts/8bithud.fnt"). // Retorna un vector buit si no es troba. auto loadFile(const std::string& relative_path) -> std::vector; diff --git a/source/game/modulegame.cpp b/source/game/modulegame.cpp index fe5d29d..3ec2d40 100644 --- a/source/game/modulegame.cpp +++ b/source/game/modulegame.cpp @@ -7,7 +7,7 @@ #include "core/resources/resource_helper.hpp" ModuleGame::ModuleGame() { - this->gfx = JD8_LoadSurface(info::ctx.pepe_activat ? "frames2.gif" : "frames.gif"); + this->gfx = JD8_LoadSurface(info::ctx.pepe_activat ? "gfx/frames2.gif" : "gfx/frames.gif"); JG_SetUpdateTicks(10); this->sam = new Prota(this->gfx); @@ -42,10 +42,10 @@ void ModuleGame::onEnter() { // fade interpolarien cap a una paleta amb pantalla buida. this->Draw(); - const char* music = info::ctx.num_piramide == 3 ? "00000008.ogg" - : info::ctx.num_piramide == 2 ? "00000007.ogg" - : info::ctx.num_piramide == 6 ? "00000002.ogg" - : "00000006.ogg"; + const char* music = info::ctx.num_piramide == 3 ? "music/00000008.ogg" + : info::ctx.num_piramide == 2 ? "music/00000007.ogg" + : info::ctx.num_piramide == 6 ? "music/00000002.ogg" + : "music/00000006.ogg"; const char* current_music = JA_GetMusicFilename(); if ((JA_GetMusicState() != JA_MUSIC_PLAYING) || !current_music || strcmp(music, current_music) != 0) { diff --git a/source/scenes/banner_scene.cpp b/source/scenes/banner_scene.cpp index c255a6d..875c447 100644 --- a/source/scenes/banner_scene.cpp +++ b/source/scenes/banner_scene.cpp @@ -11,9 +11,9 @@ namespace scenes { void BannerScene::onEnter() { - playMusic("00000004.ogg"); + playMusic("music/00000004.ogg"); - gfx_ = SurfaceHandle("ffase.gif"); + gfx_ = SurfaceHandle("gfx/ffase.gif"); JD8_ClearScreen(0); // Títols superior i inferior del banner (compartits per tots els nivells) @@ -30,7 +30,7 @@ void BannerScene::onEnter() { } // PaletteFade copia internament amb memcpy; alliberem la paleta temporal. - JD8_Palette pal = JD8_LoadPalette("ffase.gif"); + JD8_Palette pal = JD8_LoadPalette("gfx/ffase.gif"); fade_.startFadeTo(pal); std::free(pal); diff --git a/source/scenes/banner_scene.hpp b/source/scenes/banner_scene.hpp index ab85498..bf3121e 100644 --- a/source/scenes/banner_scene.hpp +++ b/source/scenes/banner_scene.hpp @@ -9,7 +9,7 @@ namespace scenes { // Banner pre-piràmide ("PIRÀMIDE X"). Reemplaça `ModuleSequence::doBanner()`. // // Flux: -// 1. Arranca música "00000004.ogg" i carrega ffase.gif. +// 1. Arranca música "music/00000004.ogg" i carrega gfx/ffase.gif. // 2. Pinta títol, subtítol i número de piràmide segons info::ctx.num_piramide. // 3. Fade-in de paleta. // 4. Mostra ~5s o fins que es polse una tecla. diff --git a/source/scenes/credits_scene.cpp b/source/scenes/credits_scene.cpp index 78c635e..bc3a87a 100644 --- a/source/scenes/credits_scene.cpp +++ b/source/scenes/credits_scene.cpp @@ -11,7 +11,7 @@ namespace { -// Frames del cotxe: 8 posicions dins del sprite sheet final.gif. El +// Frames del cotxe: 8 posicions dins del sprite sheet gfx/final.gif. El // vell doCredits tenia aquesta taula inline — la reproduïm idèntica. struct CocheFrame { Uint16 x, y; @@ -35,18 +35,18 @@ CreditsScene::~CreditsScene() { void CreditsScene::onEnter() { // El vell doCredits no tocava música — heretava la del doSlides - // previ ("00000005.ogg"). Si l'escena s'arrenca directament (test + // previ ("music/00000005.ogg"). Si l'escena s'arrenca directament (test // amb piramide_inicial=8) no hi ha res que heretar, així que // arranquem la mateixa pista només si no sona res. Inocu en el // flux normal: JA_MUSIC_PLAYING fa que no la tornem a tocar. if (JA_GetMusicState() != JA_MUSIC_PLAYING) { - playMusic("00000005.ogg"); + playMusic("music/00000005.ogg"); } - vaddr2_ = SurfaceHandle("final.gif"); - vaddr3_ = SurfaceHandle("finals.gif"); + vaddr2_ = SurfaceHandle("gfx/final.gif"); + vaddr3_ = SurfaceHandle("gfx/finals.gif"); - JD8_Palette pal = JD8_LoadPalette("final.gif"); + JD8_Palette pal = JD8_LoadPalette("gfx/final.gif"); JD8_SetScreenPalette(pal); // `pal` passa a ser propietat de main_palette — no l'alliberem. diff --git a/source/scenes/credits_scene.hpp b/source/scenes/credits_scene.hpp index 246ea72..ee4810a 100644 --- a/source/scenes/credits_scene.hpp +++ b/source/scenes/credits_scene.hpp @@ -11,7 +11,7 @@ namespace scenes { // Crèdits finals del joc. Reemplaça `ModuleSequence::doCredits()`. // // Flux: -// 1. Carrega final.gif (sprites de crèdits) i finals.gif (fons). +// 1. Carrega gfx/final.gif (sprites de crèdits) i gfx/finals.gif (fons). // 2. Mostra els crèdits amb scroll vertical de 2 columnes durant // ~62 segons (contador 0..3100 × 20 ms). // 3. Si `info::ctx.diamants == 16`, pinta addicionalment un parallax @@ -39,8 +39,8 @@ class CreditsScene : public Scene { void render(); void writeTrickIni(); - SurfaceHandle vaddr2_; // final.gif (sprites i coches) - SurfaceHandle vaddr3_; // finals.gif (fons / parallax) + SurfaceHandle vaddr2_; // gfx/final.gif (sprites i coches) + SurfaceHandle vaddr3_; // gfx/finals.gif (fons / parallax) PaletteFade fade_; FrameAnimator coche_{8, 60, true}; // 8 frames × 60 ms (~3 × 20 ms tick vell) diff --git a/source/scenes/intro_new_logo_scene.cpp b/source/scenes/intro_new_logo_scene.cpp index cc648b4..653b95c 100644 --- a/source/scenes/intro_new_logo_scene.cpp +++ b/source/scenes/intro_new_logo_scene.cpp @@ -9,7 +9,7 @@ namespace { -// Coordenades mesurades del wordmark "Jailgames" dins logo/logo_new.gif. +// Coordenades mesurades del wordmark "Jailgames" dins gfx/logo_new.gif. // Idèntiques a les del doIntroNewLogo vell — si canvies el logo, aquí i // al GIF són els únics llocs a tocar. constexpr int LOGO_SRC_X = 60; @@ -44,10 +44,10 @@ IntroNewLogoScene::~IntroNewLogoScene() { } void IntroNewLogoScene::onEnter() { - playMusic("00000003.ogg"); + playMusic("music/00000003.ogg"); - gfx_ = SurfaceHandle("logo/logo_new.gif"); - pal_ = JD8_LoadPalette("logo/logo_new.gif"); + gfx_ = SurfaceHandle("gfx/logo_new.gif"); + pal_ = JD8_LoadPalette("gfx/logo_new.gif"); JD8_SetScreenPalette(pal_); // Surface auxiliar omplida amb el color del cursor — permet pintar diff --git a/source/scenes/intro_new_logo_scene.hpp b/source/scenes/intro_new_logo_scene.hpp index 654e3c4..66aa23e 100644 --- a/source/scenes/intro_new_logo_scene.hpp +++ b/source/scenes/intro_new_logo_scene.hpp @@ -13,7 +13,7 @@ namespace scenes { // ciclo de paleta final. Reemplaça `ModuleSequence::doIntroNewLogo()`. // // Flux: -// 1. Carrega logo/logo_new.gif, arranca música "00000003.ogg" i posa +// 1. Carrega gfx/logo_new.gif, arranca música "music/00000003.ogg" i posa // la paleta directament (sense fade-in). Mostra pantalla negra 1s. // 2. Revelat: 9 lletres × 2 frames (amb cursor / sense cursor), 150 ms // cada frame. diff --git a/source/scenes/intro_scene.cpp b/source/scenes/intro_scene.cpp index 1cf0766..eae8638 100644 --- a/source/scenes/intro_scene.cpp +++ b/source/scenes/intro_scene.cpp @@ -66,10 +66,10 @@ IntroScene::~IntroScene() { } void IntroScene::onEnter() { - playMusic("00000003.ogg"); + playMusic("music/00000003.ogg"); - gfx_ = SurfaceHandle("logo.gif"); - pal_ = JD8_LoadPalette("logo.gif"); + gfx_ = SurfaceHandle("gfx/logo.gif"); + pal_ = JD8_LoadPalette("gfx/logo.gif"); JD8_SetScreenPalette(pal_); JD8_ClearScreen(0); diff --git a/source/scenes/intro_scene.hpp b/source/scenes/intro_scene.hpp index a5cf3b1..656b6b2 100644 --- a/source/scenes/intro_scene.hpp +++ b/source/scenes/intro_scene.hpp @@ -15,7 +15,7 @@ namespace scenes { // `IntroNewLogoScene`. // // Flux: -// 1. Carrega logo.gif, arranca música "00000003.ogg", pantalla negra +// 1. Carrega gfx/logo.gif, arranca música "music/00000003.ogg", pantalla negra // 1000 ms. // 2. Revelat: 15 passos (100 o 200 ms) que van acumulant les lletres // "JAILGAMES" d'esquerra a dreta amb un avió escombrant al final diff --git a/source/scenes/intro_sprites_scene.cpp b/source/scenes/intro_sprites_scene.cpp index 7b96235..bfc6273 100644 --- a/source/scenes/intro_sprites_scene.cpp +++ b/source/scenes/intro_sprites_scene.cpp @@ -14,7 +14,7 @@ namespace { constexpr int TICK_MS = 20; // Taules de frames. Ubicacions de cada sprite dins el gfx de la intro -// (logo.gif o logo/logo_new.gif — el layout de sprites és el mateix). +// (gfx/logo.gif o gfx/logo_new.gif — el layout de sprites és el mateix). // Cada sprite ocupa 15×15 px, disposats horitzontalment per fila. // Els valors són els offsets x (la y la posa l'invocador al src_y). // Derivats dels `fr_ani_N[i] = ...` del vell doIntroSprites. diff --git a/source/scenes/menu_scene.cpp b/source/scenes/menu_scene.cpp index 8a65cdd..4a1d336 100644 --- a/source/scenes/menu_scene.cpp +++ b/source/scenes/menu_scene.cpp @@ -9,8 +9,8 @@ namespace scenes { void MenuScene::onEnter() { - fondo_ = SurfaceHandle("menu.gif"); - gfx_ = SurfaceHandle("menu2.gif"); + fondo_ = SurfaceHandle("gfx/menu.gif"); + gfx_ = SurfaceHandle("gfx/menu2.gif"); // Pintat inicial (congelat durant el fade-in de paleta). El loop // d'animació repintarà tot des de zero en el primer tick de Showing. @@ -19,7 +19,7 @@ void MenuScene::onEnter() { JD8_BlitCK(130, 100, gfx_, 0, 0, 80, 74, 255); // camell (frame 0) JD8_BlitCK(0, 150, gfx_, 0, 150, 320, 50, 255); // base "jdes" - JD8_Palette pal = JD8_LoadPalette("menu2.gif"); + JD8_Palette pal = JD8_LoadPalette("gfx/menu2.gif"); fade_.startFadeTo(pal); std::free(pal); diff --git a/source/scenes/menu_scene.hpp b/source/scenes/menu_scene.hpp index 1ff4748..66f0617 100644 --- a/source/scenes/menu_scene.hpp +++ b/source/scenes/menu_scene.hpp @@ -10,7 +10,7 @@ namespace scenes { // Menú del títol. Reemplaça `ModuleSequence::doMenu()`. // // Flux: -// 1. Carrega menu.gif (fondo) i menu2.gif (sprites) + paleta. +// 1. Carrega gfx/menu.gif (fondo) i gfx/menu2.gif (sprites) + paleta. // 2. Pintat inicial estàtic (fondo, logo, camell frame 0, base "jdes"), // fade-in de paleta. // 3. Loop d'animació: escroll parallax de horitzó (cada 320 ms) i diff --git a/source/scenes/mort_scene.cpp b/source/scenes/mort_scene.cpp index fd663cc..e624244 100644 --- a/source/scenes/mort_scene.cpp +++ b/source/scenes/mort_scene.cpp @@ -10,17 +10,17 @@ namespace scenes { void MortScene::onEnter() { - playMusic("00000001.ogg"); + playMusic("music/00000001.ogg"); JI_DisableKeyboard(60); info::ctx.vida = 5; - gfx_ = SurfaceHandle("gameover.gif"); + gfx_ = SurfaceHandle("gfx/gameover.gif"); JD8_ClearScreen(0); JD8_Blit(gfx_); // PaletteFade en fa una còpia interna via memcpy, així que alliberem // la paleta temporal immediatament. - JD8_Palette pal = JD8_LoadPalette("gameover.gif"); + JD8_Palette pal = JD8_LoadPalette("gfx/gameover.gif"); fade_.startFadeTo(pal); std::free(pal); @@ -44,7 +44,7 @@ void MortScene::tick(int delta_ms) { if (remaining_ms_ <= 0) { // Arrenca música del següent mòdul abans del fade out, // igual que la versió vella feia al final de doMort(). - playMusic("00000003.ogg"); + playMusic("music/00000003.ogg"); info::ctx.num_piramide = 0; fade_.startFadeOut(); phase_ = Phase::FadingOut; diff --git a/source/scenes/mort_scene.hpp b/source/scenes/mort_scene.hpp index d121c52..b2f6fe3 100644 --- a/source/scenes/mort_scene.hpp +++ b/source/scenes/mort_scene.hpp @@ -9,9 +9,9 @@ namespace scenes { // Pantalla de "game over". Reemplaça `ModuleSequence::doMort()`. // // Flux: -// 1. Carrega gameover.gif, arranca música "00000001.ogg", fade-in de paleta. +// 1. Carrega gfx/gameover.gif, arranca música "music/00000001.ogg", fade-in de paleta. // 2. Mostra la pantalla ~10 segons o fins que l'usuari polse una tecla. -// 3. Arranca música del menú ("00000003.ogg") i fade-out de paleta. +// 3. Arranca música del menú ("music/00000003.ogg") i fade-out de paleta. // 4. Marca num_piramide=0 i retorna nextState=1 perquè el Director // passe a l'escena del menú. class MortScene : public Scene { diff --git a/source/scenes/secreta_scene.cpp b/source/scenes/secreta_scene.cpp index dda784e..2807dfc 100644 --- a/source/scenes/secreta_scene.cpp +++ b/source/scenes/secreta_scene.cpp @@ -42,15 +42,15 @@ SecretaScene::~SecretaScene() { } void SecretaScene::onEnter() { - playMusic("00000002.ogg"); + playMusic("music/00000002.ogg"); // Fade-out de la paleta anterior. Els assets es carreguen ja // però no fem SetScreenPalette fins que acabe el fade — així // el fade opera sobre la paleta del mòdul anterior. fade_.startFadeOut(); - gfx_ = SurfaceHandle("tomba1.gif"); - pal_aux_ = JD8_LoadPalette("tomba1.gif"); + gfx_ = SurfaceHandle("gfx/tomba1.gif"); + pal_aux_ = JD8_LoadPalette("gfx/tomba1.gif"); pal_active_ = static_cast(std::malloc(768)); std::memcpy(pal_active_, pal_aux_, 768); @@ -60,10 +60,10 @@ void SecretaScene::onEnter() { void SecretaScene::swapToTomba2() { JD8_ClearScreen(255); - gfx_.reset("tomba2.gif"); + gfx_.reset("gfx/tomba2.gif"); std::free(pal_aux_); - pal_aux_ = JD8_LoadPalette("tomba2.gif"); + pal_aux_ = JD8_LoadPalette("gfx/tomba2.gif"); // pal_active_ continua sent el mateix buffer: només actualitzem // el seu contingut. main_palette ja apunta ací. std::memcpy(pal_active_, pal_aux_, 768); diff --git a/source/scenes/secreta_scene.hpp b/source/scenes/secreta_scene.hpp index 2ba8ff1..0b67bf4 100644 --- a/source/scenes/secreta_scene.hpp +++ b/source/scenes/secreta_scene.hpp @@ -10,11 +10,11 @@ namespace scenes { // Pre-Secreta. Reemplaça `ModuleSequence::doSecreta()`. // // Flux: -// 1. Arranca música "00000002.ogg" i fa fade-out de la paleta anterior. -// 2. Carrega tomba1.gif + paleta i pinta un scroll vertical doble +// 1. Arranca música "music/00000002.ogg" i fa fade-out de la paleta anterior. +// 2. Carrega gfx/tomba1.gif + paleta i pinta un scroll vertical doble // (dos blits solapats, un a velocitat meitat que l'altre) durant // ~2.5 s + ~2.5 s de pausa. -// 3. Swap a tomba2.gif + reset de paleta, scroll vertical del segon +// 3. Swap a gfx/tomba2.gif + reset de paleta, scroll vertical del segon // asset (~1.9 s + ~1.9 s de pausa). // 4. ClearScreen a 0, set colors 253/254 a vermell fosc (12,11,11) // i pinta un revelat horitzontal (~1.6 s + ~1.6 s de pausa). diff --git a/source/scenes/slides_scene.cpp b/source/scenes/slides_scene.cpp index 8b51717..528fb12 100644 --- a/source/scenes/slides_scene.cpp +++ b/source/scenes/slides_scene.cpp @@ -41,10 +41,10 @@ void SlidesScene::onEnter() { const char* arxiu = nullptr; if (num_piramide_at_start_ == 7) { // loop=1 per replicar el vell `play_music("00000005.ogg", 1)`. - playMusic("00000005.ogg", 1); - arxiu = (info::ctx.diners < 200) ? "intro2.gif" : "intro3.gif"; + playMusic("music/00000005.ogg", 1); + arxiu = (info::ctx.diners < 200) ? "gfx/intro2.gif" : "gfx/intro3.gif"; } else { - arxiu = "intro.gif"; + arxiu = "gfx/intro.gif"; } gfx_ = SurfaceHandle(arxiu); diff --git a/source/scenes/slides_scene.hpp b/source/scenes/slides_scene.hpp index 43fc1de..3497adf 100644 --- a/source/scenes/slides_scene.hpp +++ b/source/scenes/slides_scene.hpp @@ -11,9 +11,9 @@ namespace scenes { // fade-out. Reemplaça `ModuleSequence::doSlides()`. // // Tria d'asset segons context: -// - num_piramide == 7 i diners < 200: intro2.gif + música "00000005.ogg" -// - num_piramide == 7 i diners >= 200: intro3.gif + música "00000005.ogg" -// - altre cas (num_piramide == 1): intro.gif, sense música nova +// - num_piramide == 7 i diners < 200: gfx/intro2.gif + música "music/00000005.ogg" +// - num_piramide == 7 i diners >= 200: gfx/intro3.gif + música "music/00000005.ogg" +// - altre cas (num_piramide == 1): gfx/intro.gif, sense música nova // // Flux: // Slide1Enter (1600 ms scroll dreta→centre, easing outCubic)