From cff94ff255f5756602ea891048bb883b84214533 Mon Sep 17 00:00:00 2001 From: Sergio Valor Date: Sat, 16 May 2026 08:42:53 +0200 Subject: [PATCH] Multifase amb transicions i atalls de debug --- maps/1.map | 1 + maps/2.map | 1 + pepe_pintor.lua | 94 ++++++++++++++++++++++++++++++++++++------------- 3 files changed, 71 insertions(+), 25 deletions(-) create mode 100644 maps/1.map create mode 100644 maps/2.map diff --git a/maps/1.map b/maps/1.map new file mode 100644 index 0000000..12a844f --- /dev/null +++ b/maps/1.map @@ -0,0 +1 @@ +±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±±±±±±±±±±±Û±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±± \ No newline at end of file diff --git a/maps/2.map b/maps/2.map new file mode 100644 index 0000000..826e0ba --- /dev/null +++ b/maps/2.map @@ -0,0 +1 @@ +±±±±±±±±±±±±±±±±±±±±±±±±±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛ±Û±ÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛ±Û±ÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛ±±Û±±ÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛ±±Û±±ÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛ±±±Û±±±ÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛ±±±Û±±±ÛÛÛÛÛÛÛÛÛ±±±±±Û±±±±±±Û±±±±±±ÛÛ±±ÛÛ±±±±±Û±±±±±±Û±±±±±±ÛÛ±±ÛÛ±±ÛÛÛÛÛÛÛ±±±Û±±±ÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛ±±Û±±ÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛ±±Û±±ÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛ±Û±ÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛ±Û±ÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ±±±±±±±±±±±±Û±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±±± \ No newline at end of file diff --git a/pepe_pintor.lua b/pepe_pintor.lua index f5e186d..e9cf362 100644 --- a/pepe_pintor.lua +++ b/pepe_pintor.lua @@ -1,13 +1,9 @@ -- Pepe el Pintor — port a ascii/Lua del joc original en Turbo Pascal -- (Sergi Valor Martínez, 1999). Base: PINTOR3.PAS. -- --- ITER 2: motor base + enemics + vides. --- - Fase única (la 3 = rectangle gran) --- - O P Q A per a moure, pinta al pas, gasta el pot --- - Recàrrega al tornar al pot (fidel al Pascal: sound(i*10)) --- - 3 enemics amb spawn diferit per llindar de blocs pintats --- - Moviment IA dels enemics fidel a moure_malos (random eix + perseguir) --- - 5 vides, animació de mort, game over, victòria +-- ITER 3: multifase. 3 mapes (rect xicotet, creu+rombe, rect gran) amb +-- transició "ENHORABONA!" entre fases. En acabar la fase 3, loop a la fase 1 +-- mantenint el flux infinit del Pascal original. -- ==================================================================== -- CONSTANTS @@ -32,10 +28,12 @@ TICS_OMPLIR = 3 -- frames entre +1 de pot al recarregar NUM_MALOS = 3 VIDES_INI = 5 +NUM_FASES = 3 --- Llindars d'aparició dels enemics (proporcionals al PINTOR3 escalat als --- nostres ~829 blocs). Apareixen quan total_blocs baixa per sota d'aquests. -BLOCS_SPAWN = { 750, 520, 370 } +-- Llindars d'aparició dels enemics expressats com a *fracció* del total +-- inicial de la fase. PINTOR3 tenia 1000/700/500 blocs sobre ~1320 → 76% / +-- 53% / 38%. Apareixen quan total_blocs baixa per sota. +SPAWN_FRAC = { 0.76, 0.53, 0.38 } -- Animació de mort: 10000 Hz → 1000 Hz, restant 250 cada pas MORT_FREQ_INI = 10000 @@ -47,7 +45,8 @@ MORT_FRAMES = 36 -- ~600 ms d'animació de mort ESTAT_PLAYING = "playing" ESTAT_MURIGUENT = "muriguent" ESTAT_GAMEOVER = "gameover" -ESTAT_VICTORIA = "victoria" +ESTAT_INTERFASE = "interfase" -- "ENHORABONA!" entre fases (fidel al Pascal) +INTERFASE_FRAMES = 240 -- ~4 segons (l'original feia delay(5000) = 5s) -- ==================================================================== -- ESTAT GLOBAL @@ -62,6 +61,9 @@ omplir_max = 0 malos = {} -- { {x, y, viu=bool, aparegut=bool}, ... } vides = VIDES_INI +fase = 1 -- 1..NUM_FASES, loop al final +total_inicial = 0 -- valor de total_blocs al començar la fase (per als llindars) +truco = false -- invulnerabilitat (mode debug, l'original ho tenia comentat amb tecla I) estat_joc = ESTAT_PLAYING estat_t = 0 -- contador de frames dins de l'estat actual @@ -131,6 +133,7 @@ function carregar_mapa(num) -- La cel·la del pot no es pinta: ja "pintada" per a la condició de victòria mapa[PEPE_INI_X][PEPE_INI_Y].pintat = true total_blocs = total_blocs - 1 + total_inicial = total_blocs -- per a calcular llindars d'spawn end function pintar_mapa() @@ -180,7 +183,7 @@ function pintar_malos() end end --- HUD: pintura, blocs restants, vides (com a ☻), controls +-- HUD: pintura, blocs restants, vides (com a ☻), fase, controls function pintar_hud() color(COLOR_LIGHT_GRAY, COLOR_BLUE) local blank = " " @@ -197,8 +200,14 @@ function pintar_hud() print(chr(PEPE_PLE), 32 + i, 26) end + color(COLOR_LIGHT_GREEN, COLOR_BLUE) + print("FASE "..tostr(fase), 1, 28) color(COLOR_LIGHT_CYAN, COLOR_BLUE) - print("O P Q A: moure", 1, 28) + print("O P Q A: moure", 12, 28) + if truco then + color(COLOR_WHITE, COLOR_RED) + print("INVULN", 30, 28) + end end -- ==================================================================== @@ -302,12 +311,13 @@ function jingle_malo() play("l0o3cdefgab>cl0o3cdefgab>c") end --- Check spawn: si total_blocs ha baixat per sota del llindar i el malo no --- ha aparegut encara, el fem aparèixer. +-- Check spawn: si total_blocs ha baixat per sota del llindar proporcional al +-- total inicial de la fase, i el malo encara no ha aparegut, el fem aparèixer. function check_spawn() for i = 1, NUM_MALOS do local m = malos[i] - if not m.aparegut and total_blocs <= BLOCS_SPAWN[i] then + local llindar = flr(total_inicial * SPAWN_FRAC[i]) + if not m.aparegut and total_blocs <= llindar then m.x, m.y = naiximent() m.viu = true m.aparegut = true @@ -381,6 +391,7 @@ function set_estat(nou) end function mort_pepe() + if truco then return end -- invulnerabilitat de debug vides = vides - 1 set_estat(ESTAT_MURIGUENT) end @@ -389,15 +400,38 @@ function reset_partida() pot = POT_MAX total_blocs = 0 vides = VIDES_INI + fase = 1 omplint = false pepe.x, pepe.y = PEPE_INI_X, PEPE_INI_Y pepe.pinta = true init_malos() - carregar_mapa(3) + carregar_mapa(fase) reset_input() set_estat(ESTAT_PLAYING) end +-- Carrega una fase concreta (reinicia vides i pot, ja siga per la transició +-- normal o per l'atall de debug). Si n > NUM_FASES, loop a 1. +function anar_a_fase(n) + if n > NUM_FASES then n = 1 end + if n < 1 then n = NUM_FASES end + fase = n + vides = VIDES_INI + pot = POT_MAX + omplint = false + pepe.x, pepe.y = PEPE_INI_X, PEPE_INI_Y + pepe.pinta = true + init_malos() + carregar_mapa(fase) + reset_input() + set_estat(ESTAT_PLAYING) +end + +-- Avança a la fase següent (fidel al PINTOR3: nfase++ i si > 3, loop a 1). +function avancar_fase() + anar_a_fase(fase + 1) +end + -- Respawn després de mort (sense reset complet, sols Pepe a casa i pot ple) function respawn_pepe() pepe.x, pepe.y = PEPE_INI_X, PEPE_INI_Y @@ -413,6 +447,13 @@ end function update_playing() sample_input() + -- Atalls de debug: 1/2/3 = salta a fase, I = toggle invulnerable + if btnp(KEY_1) then anar_a_fase(1); return + elseif btnp(KEY_2) then anar_a_fase(2); return + elseif btnp(KEY_3) then anar_a_fase(3); return + end + if btnp(KEY_I) then truco = not truco end + if omplint and (cnt() % TICS_OMPLIR) == 0 then tic_omplir() end if not omplint and (cnt() % TICS_MOVIMENT) == 0 then @@ -425,7 +466,7 @@ function update_playing() reset_input() if total_blocs <= 0 then - set_estat(ESTAT_VICTORIA) + set_estat(ESTAT_INTERFASE) play("l3o4ceg>c") return end @@ -478,19 +519,21 @@ function update_gameover() end end -function update_victoria() +-- Transició entre fases: ENHORABONA! parpadejant, després passa a la fase +-- següent automàticament (fidel al delay(5000) del PINTOR3). +function update_interfase() cls() pintar_mapa() pintar_pot() pintar_pepe() pintar_hud() - if (estat_t // 10) % 2 == 0 then - color(COLOR_GREEN, COLOR_BLACK) + if (estat_t // 12) % 2 == 0 then + color(COLOR_LIGHT_GREEN, COLOR_BLACK) print("ENHORABONA!", 14, 11) end - if estat_t > 180 and btnp(KEY_SPACE) then - reset_partida() + if estat_t >= INTERFASE_FRAMES then + avancar_fase() end end @@ -502,7 +545,8 @@ function init() border(COLOR_BLUE) definir_glifs() init_malos() - carregar_mapa(3) + fase = 1 + carregar_mapa(fase) cls() end @@ -511,6 +555,6 @@ function update() if estat_joc == ESTAT_PLAYING then update_playing() elseif estat_joc == ESTAT_MURIGUENT then update_muriguent() elseif estat_joc == ESTAT_GAMEOVER then update_gameover() - elseif estat_joc == ESTAT_VICTORIA then update_victoria() + elseif estat_joc == ESTAT_INTERFASE then update_interfase() end end