424d0d2b89
Resuelve la categoría de findings de tidy que son bugs reales o cambios
de tipo concretos, no transforms automáticos:
Bugs reales (bugprone-* y clang-diagnostic-*):
- bugprone-empty-catch en postfx_config.cpp: el catch silencioso del
parser RGB era intencional (fallback a defaults si el array no parsea
como int). Marcado con @INTENTIONAL (keyword ya configurado en
.clang-tidy via bugprone-empty-catch.IgnoreCatchWithKeywords) y
comentario ampliado explicando la decisión.
- clang-diagnostic-unused-private-field en Starfield: el campo
'densitat_' se asignaba en el constructor pero nunca se leía. El
parámetro 'densitat' se reparte directamente en las CapaConfig al
construir, así que el field era código muerto. Eliminado.
- bugprone-branch-clone en vector_text.cpp: el switch de
get_shape_filename tenía dos grupos consecutivos (dígitos 0-9 y
mayúsculas A-Z) con cuerpo idéntico. Fusionados en un único case con
comentario explicando que comparten path porque la shape se llama
igual que el caracter.
- bugprone-switch-missing-default-case en Input::handleEvent: el switch
manejaba solo SDL_EVENT_GAMEPAD_ADDED/REMOVED y caía por fall-through
a un return {} fuera del switch. Añadido default: explícito con
comentario sobre qué hace Input vs el resto del sistema.
- bugprone-implicit-widening-of-multiplication-result en
GameScene::bullets_ y Collision::Context::bullets: 'MAX_BALES * 2'
es int*int y se widening implícitamente a std::size_t para el
template arg de std::array. Cast explícito a size_t en ambos sitios.
Otros mecánicos:
- performance-enum-size: 10 enums sin tipo subyacente pasaron a
': std::uint8_t' (PrimitiveType, InputAction, Mode, SceneType,
Option, AnimationState, TitleState, ModeSpawn, EstatStage,
ShipState). #include <cstdint> añadido donde faltaba.
- modernize-use-equals-default en SpawnController: el ctor por
defecto tenía cuerpo vacío ({}). Pasado a '= default;'.
Cero supresiones. La única "marca" es @INTENTIONAL en el empty-catch,
que es el mecanismo configurado en el .clang-tidy del proyecto para
distinguir intencionales de accidentales.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
122 lines
6.5 KiB
C++
122 lines
6.5 KiB
C++
// title_scene.hpp - Pantalla de título del juego
|
|
// Muestra message "PRESS BUTTON TO PLAY" y copyright
|
|
// © 2026 JailDesigner
|
|
|
|
#pragma once
|
|
|
|
#include <SDL3/SDL.h>
|
|
|
|
#include <array>
|
|
#include <cstdint>
|
|
#include <memory>
|
|
#include <vector>
|
|
|
|
#include "core/defaults.hpp"
|
|
#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/scene.hpp"
|
|
#include "core/system/scene_context.hpp"
|
|
#include "core/system/game_config.hpp"
|
|
#include "core/types.hpp"
|
|
#include "game/title/ship_animator.hpp"
|
|
|
|
// Botones para INICIAR PARTIDA desde MAIN (solo START)
|
|
static constexpr std::array<InputAction, 1> START_GAME_BUTTONS = {
|
|
InputAction::START};
|
|
|
|
class TitleScene final : public Scene {
|
|
public:
|
|
explicit TitleScene(SDLManager& sdl, SceneManager::SceneContext& context);
|
|
~TitleScene() override; // Destructor per aturar música
|
|
|
|
// Scene interface
|
|
void handleEvent(const SDL_Event& event) override;
|
|
void update(float delta_time) override;
|
|
void draw() override;
|
|
[[nodiscard]] auto isFinished() const -> bool override;
|
|
|
|
private:
|
|
// Màquina de estats per la pantalla de título
|
|
enum class TitleState : std::uint8_t {
|
|
STARFIELD_FADE_IN, // Fade-in del starfield (3.0s)
|
|
STARFIELD, // Pantalla con camp de estrelles (4.0s)
|
|
MAIN, // Pantalla de título con text (indefinit, hasta START)
|
|
PLAYER_JOIN_PHASE, // Fase de unió de jugadors: fade-out música + text parpellejant (2.5s)
|
|
BLACK_SCREEN // Pantalla negra de transición (2.0s)
|
|
};
|
|
|
|
// Estructura per emmagatzemar informació de cada lletra del título
|
|
struct LetraLogo {
|
|
std::shared_ptr<Graphics::Shape> shape; // Forma vectorial de la lletra
|
|
Vec2 position; // Posición en pantalla
|
|
float ancho; // Amplada scaled
|
|
float altura; // Altura scaled
|
|
float offset_centre; // Offset del centro per posicionament
|
|
};
|
|
|
|
SDLManager& sdl_;
|
|
SceneManager::SceneContext& context_;
|
|
GameConfig::MatchConfig match_config_; // Configuración de jugadors active
|
|
Graphics::VectorText text_; // Sistema de text vectorial
|
|
std::unique_ptr<Graphics::Starfield> starfield_; // Camp de estrelles de fons
|
|
std::unique_ptr<Title::ShipAnimator> ship_animator_; // Naves 3D flotantes
|
|
TitleState estat_actual_{TitleState::STARFIELD_FADE_IN}; // Estat actual de la màquina
|
|
float temps_acumulat_{0.0F}; // Temps acumulat per l'state INIT
|
|
|
|
// Lletres del título "ORNI ATTACK!"
|
|
std::vector<LetraLogo> lletres_orni_; // Lletres de "ORNI" (línia 1)
|
|
std::vector<LetraLogo> lletres_attack_; // Lletres de "ATTACK!" (línia 2)
|
|
float y_attack_dinamica_; // Posición Y calculada dinàmicament per "ATTACK!"
|
|
|
|
// Logo "JAILGAMES" pequeño sobre el copyright (esquinas inferiores del título).
|
|
std::vector<LetraLogo> lletres_jailgames_;
|
|
|
|
// Estat de animación del logo
|
|
float temps_animacio_{0.0F}; // Temps acumulat per animación orbital
|
|
std::vector<Vec2> posicions_originals_orni_; // Posicions originals de "ORNI"
|
|
std::vector<Vec2> posicions_originals_attack_; // Posicions originals de "ATTACK!"
|
|
|
|
// Estat de arrencada de l'animación
|
|
float temps_estat_main_{0.0F}; // Temps acumulat en state MAIN
|
|
bool animacio_activa_{false}; // Flag: true cuando animación está activa
|
|
float factor_lerp_{0.0F}; // Factor de lerp actual (0.0 → 1.0)
|
|
|
|
// Constants
|
|
static constexpr float BRIGHTNESS_STARFIELD = 1.2F; // Brightness del starfield (>1.0 = més brillant)
|
|
static constexpr float DURACIO_FADE_IN = 3.0F; // Duració del fade-in del starfield (1.5 segons)
|
|
static constexpr float DURACIO_INIT = 4.0F; // Duració de l'state INIT (2 segons)
|
|
static constexpr float DURACIO_TRANSITION = 2.5F; // Duració de la transición (1.5 segons)
|
|
static constexpr float ESPAI_ENTRE_LLETRES = 10.0F; // Espai entre lletres
|
|
static constexpr float BLINK_FREQUENCY = 3.0F; // Freqüència de parpelleig (3 Hz)
|
|
static constexpr float DURACIO_BLACK_SCREEN = 2.0F; // Duració pantalla negra (2 segons)
|
|
static constexpr int MUSIC_FADE = 1500; // Duracio del fade de la musica del titol al començar a jugar
|
|
|
|
// Constants de animación del logo
|
|
static constexpr float ORBIT_AMPLITUDE_X = 4.0F; // Amplitud oscil·lació horitzontal (píxels)
|
|
static constexpr float ORBIT_AMPLITUDE_Y = 3.0F; // Amplitud oscil·lació vertical (píxels)
|
|
static constexpr float ORBIT_FREQUENCY_X = 0.8F; // Velocidad oscil·lació horitzontal (Hz)
|
|
static constexpr float ORBIT_FREQUENCY_Y = 1.2F; // Velocidad oscil·lació vertical (Hz)
|
|
static constexpr float ORBIT_PHASE_OFFSET = 1.57F; // Desfasament entre X i Y (90° per circular)
|
|
|
|
// Constants de ombra del logo
|
|
static constexpr float SHADOW_DELAY = 0.5F; // Retard temporal de l'ombra (segons)
|
|
static constexpr float SHADOW_BRIGHTNESS = 0.4F; // Multiplicador de brightness de l'ombra (0.0-1.0)
|
|
static constexpr float SHADOW_OFFSET_X = 2.0F; // Offset espacial X fix (píxels)
|
|
static constexpr float SHADOW_OFFSET_Y = 2.0F; // Offset espacial Y fix (píxels)
|
|
|
|
// Temporització de l'arrencada de l'animación
|
|
static constexpr float DELAY_INICI_ANIMACIO = 10.0F; // 10s estàtic antes de animar
|
|
static constexpr float DURACIO_LERP = 2.0F; // 2s per arribar a amplitud completa
|
|
|
|
// Métodos privats
|
|
void actualitzar_animacio_logo(float delta_time); // Actualitza l'animación orbital del logo
|
|
auto checkSkipButtonPressed() -> bool;
|
|
auto checkStartGameButtonPressed() -> bool;
|
|
void inicialitzar_titol(); // Carrega i posiciona las lletres del título
|
|
void inicialitzarJailgames(); // Carrega i posiciona el logo JAILGAMES pequeño
|
|
void dibuixarPeuTitol(float spacing) const; // Logo JAILGAMES + línia de copyright
|
|
};
|