integrada classe Input

This commit is contained in:
2025-12-11 12:41:03 +01:00
parent 087b8d346d
commit 0ceaa75862
16 changed files with 3437 additions and 124 deletions

View File

@@ -11,6 +11,7 @@
#include <vector>
#include "core/audio/audio.hpp"
#include "core/input/input.hpp"
#include "core/input/mouse.hpp"
#include "core/math/easing.hpp"
#include "core/rendering/line_renderer.hpp"
@@ -74,6 +75,9 @@ void EscenaJoc::executar() {
// Actualitzar visibilitat del cursor (auto-ocultar)
Mouse::updateCursorVisibility();
// Actualitzar sistema d'input ABANS del event loop
Input::get()->update();
// Processar events SDL
while (SDL_PollEvent(&event)) {
// Manejo de finestra
@@ -82,12 +86,7 @@ void EscenaJoc::executar() {
}
// Events globals (F1/F2/F3/ESC/QUIT)
if (GlobalEvents::handle(event, sdl_, context_)) {
continue;
}
// Processament específic del joc (SPACE per disparar)
processar_input(event);
GlobalEvents::handle(event, sdl_, context_);
}
// Actualitzar física del joc amb delta_time real
@@ -180,6 +179,21 @@ void EscenaJoc::inicialitzar() {
}
void EscenaJoc::actualitzar(float delta_time) {
// Processar disparos (state-based, no event-based)
if (!game_over_) {
auto* input = Input::get();
// Jugador 1 dispara
if (input->checkActionPlayer1(InputAction::SHOOT, Input::DO_NOT_ALLOW_REPEAT)) {
disparar_bala(0);
}
// Jugador 2 dispara
if (input->checkActionPlayer2(InputAction::SHOOT, Input::DO_NOT_ALLOW_REPEAT)) {
disparar_bala(1);
}
}
// Check game over state first
if (game_over_) {
// Game over: only update timer, enemies, bullets, and debris
@@ -534,28 +548,6 @@ void EscenaJoc::dibuixar() {
}
}
void EscenaJoc::processar_input(const SDL_Event& event) {
// Ignore ship controls during game over
if (game_over_) {
return;
}
// Processament d'input per events puntuals (no continus)
// L'input continu (fletxes/WASD) es processa en actualitzar() amb
// SDL_GetKeyboardState()
if (event.type == SDL_EVENT_KEY_DOWN) {
// P1 shoot
if (event.key.key == Defaults::Controls::P1::SHOOT) {
disparar_bala(0);
}
// P2 shoot
else if (event.key.key == Defaults::Controls::P2::SHOOT) {
disparar_bala(1);
}
}
}
void EscenaJoc::tocado(uint8_t player_id) {
// Death sequence: 3 phases
// Phase 1: First call (itocado_per_jugador_[player_id] == 0) - trigger explosion

View File

@@ -34,7 +34,6 @@ class EscenaJoc {
void inicialitzar();
void actualitzar(float delta_time);
void dibuixar();
void processar_input(const SDL_Event& event);
private:
SDLManager& sdl_;

View File

@@ -11,6 +11,7 @@
#include "core/audio/audio.hpp"
#include "core/graphics/shape_loader.hpp"
#include "core/input/input.hpp"
#include "core/input/mouse.hpp"
#include "core/rendering/shape_renderer.hpp"
#include "core/system/context_escenes.hpp"
@@ -82,6 +83,9 @@ void EscenaLogo::executar() {
// Actualitzar visibilitat del cursor (auto-ocultar)
Mouse::updateCursorVisibility();
// Actualitzar sistema d'input ABANS del event loop
Input::get()->update();
// Processar events SDL
while (SDL_PollEvent(&event)) {
// Manejo de finestra
@@ -312,6 +316,12 @@ void EscenaLogo::actualitzar(float delta_time) {
break;
}
// Verificar botones de skip (SHOOT P1/P2)
if (checkSkipButtonPressed()) {
context_.canviar_escena(Escena::TITOL, Opcio::JUMP_TO_TITLE_MAIN);
GestorEscenes::actual = Escena::TITOL;
}
// Actualitzar animacions de debris
debris_manager_->actualitzar(delta_time);
}
@@ -404,16 +414,17 @@ void EscenaLogo::dibuixar() {
sdl_.presenta();
}
void EscenaLogo::processar_events(const SDL_Event& event) {
// Qualsevol tecla o clic de ratolí salta a la pantalla de títol
if (event.type == SDL_EVENT_KEY_DOWN ||
event.type == SDL_EVENT_MOUSE_BUTTON_DOWN) {
// Utilitzar context per especificar escena i opció
context_.canviar_escena(
Escena::TITOL,
Opcio::JUMP_TO_TITLE_MAIN
);
// Backward compatibility: També actualitzar GestorEscenes::actual
GestorEscenes::actual = Escena::TITOL;
auto EscenaLogo::checkSkipButtonPressed() -> bool {
auto* input = Input::get();
for (auto action : SKIP_BUTTONS_LOGO) {
if (input->checkActionPlayer1(action, Input::DO_NOT_ALLOW_REPEAT) ||
input->checkActionPlayer2(action, Input::DO_NOT_ALLOW_REPEAT)) {
return true;
}
}
return false;
}
void EscenaLogo::processar_events(const SDL_Event& event) {
// No procesar eventos genéricos aquí - la lógica se movió a actualitzar()
}

View File

@@ -6,16 +6,23 @@
#include <SDL3/SDL.h>
#include <array>
#include <memory>
#include <vector>
#include "game/effects/debris_manager.hpp"
#include "core/defaults.hpp"
#include "core/graphics/shape.hpp"
#include "core/input/input_types.hpp"
#include "core/rendering/sdl_manager.hpp"
#include "core/system/context_escenes.hpp"
#include "core/types.hpp"
// Botones que permiten saltar la escena (extensible)
static constexpr std::array<InputAction, 1> SKIP_BUTTONS_LOGO = {
InputAction::SHOOT
};
class EscenaLogo {
public:
explicit EscenaLogo(SDLManager& sdl, GestorEscenes::ContextEscenes& context);
@@ -80,6 +87,7 @@ class EscenaLogo {
void actualitzar_explosions(float delta_time);
void dibuixar();
void processar_events(const SDL_Event& event);
auto checkSkipButtonPressed() -> bool;
// Mètodes de gestió d'estats
void canviar_estat(EstatAnimacio nou_estat);

View File

@@ -10,6 +10,7 @@
#include "core/audio/audio.hpp"
#include "core/graphics/shape_loader.hpp"
#include "core/input/input.hpp"
#include "core/input/mouse.hpp"
#include "core/rendering/shape_renderer.hpp"
#include "core/system/context_escenes.hpp"
@@ -254,6 +255,9 @@ void EscenaTitol::executar() {
// Actualitzar visibilitat del cursor (auto-ocultar)
Mouse::updateCursorVisibility();
// Actualitzar sistema d'input ABANS del event loop
Input::get()->update();
// Processar events SDL
while (SDL_PollEvent(&event)) {
// Manejo de finestra
@@ -368,6 +372,37 @@ void EscenaTitol::actualitzar(float delta_time) {
}
break;
}
// Verificar botones de skip (SHOOT P1/P2)
if (checkSkipButtonPressed()) {
switch (estat_actual_) {
case EstatTitol::STARFIELD_FADE_IN:
// Saltar fade-in, ir a MAIN
estat_actual_ = EstatTitol::MAIN;
starfield_->set_brightness(BRIGHTNESS_STARFIELD);
temps_estat_main_ = 0.0f;
break;
case EstatTitol::STARFIELD:
// Saltar starfield, ir a MAIN
estat_actual_ = EstatTitol::MAIN;
temps_estat_main_ = 0.0f;
break;
case EstatTitol::MAIN:
// Iniciar partida (transición a JOC)
context_.canviar_escena(Escena::JOC);
estat_actual_ = EstatTitol::TRANSITION_TO_GAME;
temps_acumulat_ = 0.0f;
Audio::get()->fadeOutMusic(MUSIC_FADE);
Audio::get()->playSound(Defaults::Sound::LASER, Audio::Group::GAME);
break;
case EstatTitol::TRANSITION_TO_GAME:
// Ignorar inputs durante transición
break;
}
}
}
void EscenaTitol::actualitzar_animacio_logo(float delta_time) {
@@ -540,40 +575,17 @@ void EscenaTitol::dibuixar() {
}
}
void EscenaTitol::processar_events(const SDL_Event& event) {
// Qualsevol tecla o clic de ratolí
if (event.type == SDL_EVENT_KEY_DOWN ||
event.type == SDL_EVENT_MOUSE_BUTTON_DOWN) {
switch (estat_actual_) {
case EstatTitol::STARFIELD_FADE_IN:
// Saltar directament a MAIN (ometre fade-in i starfield)
estat_actual_ = EstatTitol::MAIN;
starfield_->set_brightness(BRIGHTNESS_STARFIELD); // Assegurar brightness final
temps_estat_main_ = 0.0f; // Reset timer per animació de títol
break;
case EstatTitol::STARFIELD:
// Saltar a MAIN
estat_actual_ = EstatTitol::MAIN;
temps_estat_main_ = 0.0f; // Reset timer
break;
case EstatTitol::MAIN:
// Utilitzar context per transició a JOC
context_.canviar_escena(Escena::JOC);
// NO actualitzar GestorEscenes::actual aquí!
// La transició es fa en l'estat TRANSITION_TO_GAME
// Iniciar transició amb fade-out de música
estat_actual_ = EstatTitol::TRANSITION_TO_GAME;
temps_acumulat_ = 0.0f; // Reset del comptador
Audio::get()->fadeOutMusic(MUSIC_FADE); // Fade
Audio::get()->playSound(Defaults::Sound::LASER, Audio::Group::GAME);
break;
case EstatTitol::TRANSITION_TO_GAME:
// Ignorar inputs durant la transició
break;
auto EscenaTitol::checkSkipButtonPressed() -> bool {
auto* input = Input::get();
for (auto action : SKIP_BUTTONS_TITOL) {
if (input->checkActionPlayer1(action, Input::DO_NOT_ALLOW_REPEAT) ||
input->checkActionPlayer2(action, Input::DO_NOT_ALLOW_REPEAT)) {
return true;
}
}
return false;
}
void EscenaTitol::processar_events(const SDL_Event& event) {
// No procesar eventos genéricos aquí - la lógica se movió a actualitzar()
}

View File

@@ -6,6 +6,7 @@
#include <SDL3/SDL.h>
#include <array>
#include <memory>
#include <vector>
@@ -13,10 +14,16 @@
#include "core/graphics/shape.hpp"
#include "core/graphics/starfield.hpp"
#include "core/graphics/vector_text.hpp"
#include "core/input/input_types.hpp"
#include "core/rendering/sdl_manager.hpp"
#include "core/system/context_escenes.hpp"
#include "core/types.hpp"
// Botones que permiten saltar/avanzar la escena (extensible)
static constexpr std::array<InputAction, 1> SKIP_BUTTONS_TITOL = {
InputAction::SHOOT
};
class EscenaTitol {
public:
explicit EscenaTitol(SDLManager& sdl, GestorEscenes::ContextEscenes& context);
@@ -97,5 +104,6 @@ class EscenaTitol {
void actualitzar_animacio_logo(float delta_time); // Actualitza l'animació orbital del logo
void dibuixar();
void processar_events(const SDL_Event& event);
auto checkSkipButtonPressed() -> bool;
void inicialitzar_titol(); // Carrega i posiciona les lletres del títol
};