arreglada la logica d'estats en Ending2

This commit is contained in:
2025-03-21 13:24:32 +01:00
parent 0f8de0d8b5
commit 428fe664bd
5 changed files with 155 additions and 82 deletions

View File

@@ -17,12 +17,7 @@
#include "utils.h" // Para PaletteColor, stringToColor #include "utils.h" // Para PaletteColor, stringToColor
// Constructor // Constructor
Ending2::Ending2() Ending2::Ending2() : state_(EndingState::PRE_CREDITS, SDL_GetTicks(), STATE_PRE_CREDITS_DURATION_)
: counter_enabled_(false),
pre_counter_(0),
post_counter_(0),
post_counter_enabled_(false),
ticks_(0)
{ {
options.section.section = Section::ENDING2; options.section.section = Section::ENDING2;
options.section.subsection = Subsection::NONE; options.section.subsection = Subsection::NONE;
@@ -65,26 +60,31 @@ void Ending2::update()
// Comprueba las entradas // Comprueba las entradas
checkInput(); checkInput();
// Actualiza los contadores // Actualiza el estado
updateCounters(); updateState();
if (counter_enabled_) switch (state_.state)
{
case EndingState::CREDITS:
// Actualiza los sprites, los textos y los textos del final
for (int i = 0; i < 25; ++i)
{ {
// Actualiza los sprites
updateSprites(); updateSprites();
// Actualiza los sprites de texto
updateTextSprites(); updateTextSprites();
// Actualiza los sprites de texto del final
updateTexts(); updateTexts();
} }
break;
// Actualiza el fade final case EndingState::FADING:
// Actualiza el fade final y el volumen de la música
updateFinalFade(); updateFinalFade();
// Actualiza el volumen de la musica
updateMusicVolume(); updateMusicVolume();
break;
default:
// No hacer nada si el estado no corresponde a un caso manejado
break;
}
// Actualiza el objeto // Actualiza el objeto
Screen::get()->update(); Screen::get()->update();
@@ -167,29 +167,43 @@ void Ending2::run()
JA_SetVolume(128); JA_SetVolume(128);
} }
// Actualiza los contadores // Actualiza el estado
void Ending2::updateCounters() void Ending2::updateState()
{ {
// Incrementa el contador switch (state_.state)
if (pre_counter_ < 200)
{ {
pre_counter_++; case EndingState::PRE_CREDITS:
} if (state_.hasEnded(EndingState::PRE_CREDITS))
else {
{ state_.set(EndingState::CREDITS, 0);
counter_enabled_ = true;
} }
break;
if (post_counter_enabled_) case EndingState::CREDITS:
if (texts_.back()->getPosY() <= GAMECANVAS_CENTER_Y)
{ {
post_counter_++; state_.set(EndingState::POST_CREDITS, STATE_POST_CREDITS_DURATION_);
} }
break;
if (post_counter_ > 600) case EndingState::POST_CREDITS:
if (state_.hasEnded(EndingState::POST_CREDITS))
{
state_.set(EndingState::FADING, STATE_FADE_DURATION_);
}
break;
case EndingState::FADING:
if (state_.hasEnded(EndingState::FADING))
{ {
options.section.section = Section::LOGO; options.section.section = Section::LOGO;
options.section.subsection = Subsection::LOGO_TO_INTRO; options.section.subsection = Subsection::LOGO_TO_INTRO;
} }
break;
default:
break;
}
} }
// Inicializa la lista de sprites // Inicializa la lista de sprites
@@ -306,19 +320,12 @@ void Ending2::updateTextSprites()
// Actualiza los sprites de texto del final // Actualiza los sprites de texto del final
void Ending2::updateTexts() void Ending2::updateTexts()
{
if (texts_.back()->getPosY() > GAMECANVAS_CENTER_Y)
{ {
for (auto sprite : texts_) for (auto sprite : texts_)
{ {
sprite->update(); sprite->update();
} }
} }
else
{
post_counter_enabled_ = true;
}
}
// Dibuja los sprites // Dibuja los sprites
void Ending2::renderSprites() void Ending2::renderSprites()
@@ -498,25 +505,34 @@ void Ending2::createTexts()
// Actualiza el fade final // Actualiza el fade final
void Ending2::updateFinalFade() void Ending2::updateFinalFade()
{ /*
// La variable step va de 0 a 40 en el tramo de postCounter que va de 500 a 540. Al dividirlo por 40, va de 0.0f a 1.0f
const float STEP = std::min(std::max(post_counter_, 500) - 500, 40) / 40.0f;
const int INDEX = (colors_.size() - 1) * STEP;
for (const auto &text : texts_)
{ {
text->getTexture()->setColor(colors_.at(INDEX).r, colors_.at(INDEX).g, colors_.at(INDEX).b); for (auto sprite : texts_)
{
sprite->getSurface()->fadeSubPalette(0);
} }
*/
} }
// Actualiza el volumen de la musica // Actualiza el volumen de la musica
void Ending2::updateMusicVolume() void Ending2::updateMusicVolume()
{ {
if (post_counter_ > 0) // Constante para la duración en milisegundos
{ constexpr Uint32 VOLUME_FADE_DURATION = 3000;
const float step = (600.0f - post_counter_) / 600.0f;
const int volume = 128 * step; // Tiempo actual
JA_SetVolume(volume); const Uint32 CURRENT_TICKS = SDL_GetTicks();
}
// Calcular el tiempo transcurrido desde init_ticks
Uint32 elapsed_ticks = CURRENT_TICKS - state_.init_ticks;
// Limitar el tiempo máximo a la duración definida
elapsed_ticks = std::min(elapsed_ticks, VOLUME_FADE_DURATION);
// Calcular el step basado en la duración
const float STEP = (static_cast<float>(VOLUME_FADE_DURATION) - elapsed_ticks) / VOLUME_FADE_DURATION;
// Calcular el volumen en función del step
const int VOLUME = static_cast<int>(128 * STEP);
// Actualizar el volumen
JA_SetVolume(VOLUME);
} }

View File

@@ -11,12 +11,57 @@ class SMovingSprite; // lines 10-10
class Ending2 class Ending2
{ {
private: private:
// Enum para representar los estados del final
enum class EndingState : int
{
PRE_CREDITS, // Estado previo a los créditos
CREDITS, // Estado de los créditos
POST_CREDITS, // Estado posterior a los créditos
FADING, // Estado de fundido de los textos a negrp
};
// Estructura para controlar los estados y su duración
struct State
{
EndingState state; // Estado actual
Uint32 init_ticks; // Ticks en los que se inicializó el estado
Uint32 duration; // Duración en milisegundos para el estado actual
// Constructor parametrizado para inicializar la estructura
State(EndingState initialState, Uint32 initialTicks, Uint32 stateDuration)
: state(initialState), init_ticks(initialTicks), duration(stateDuration) {}
// Método para comprobar si el estado ha terminado y verifica el nombre del estado
bool hasEnded(EndingState expectedState) const
{
// Comprobar si el estado actual coincide con el estado esperado
if (state != expectedState)
{
return false; // Si no coincide, considerar que no ha terminado
}
// Comprobar si el tiempo transcurrido excede la duración
return (SDL_GetTicks() - init_ticks) >= duration;
}
// Método para establecer un nuevo estado
void set(EndingState newState, Uint32 newDuration)
{
state = newState; // Actualizar el estado
init_ticks = SDL_GetTicks(); // Reiniciar el tiempo de inicio
duration = newDuration; // Actualizar la duración
}
};
// Constantes // Constantes
static constexpr int FIRST_COL_ = GAMECANVAS_FIRST_QUARTER_X + (GAMECANVAS_WIDTH / 16); // Primera columna por donde desfilan los sprites static constexpr int FIRST_COL_ = GAMECANVAS_FIRST_QUARTER_X + (GAMECANVAS_WIDTH / 16); // Primera columna por donde desfilan los sprites
static constexpr int SECOND_COL_ = GAMECANVAS_THIRD_QUARTER_X - (GAMECANVAS_WIDTH / 16); // Segunda columna por donde desfilan los sprites static constexpr int SECOND_COL_ = GAMECANVAS_THIRD_QUARTER_X - (GAMECANVAS_WIDTH / 16); // Segunda columna por donde desfilan los sprites
static constexpr int DIST_SPRITE_TEXT_ = 8; // Distancia entre el sprite y el texto que lo acompaña static constexpr int DIST_SPRITE_TEXT_ = 8; // Distancia entre el sprite y el texto que lo acompaña
static constexpr int DIST_SPRITE_SPRITE_ = 0; // Distancia entre dos sprites de la misma columna static constexpr int DIST_SPRITE_SPRITE_ = 0; // Distancia entre dos sprites de la misma columna
static constexpr float SPRITE_DESP_SPEED_ = -0.2f; // Velocidad de desplazamiento de los sprites static constexpr float SPRITE_DESP_SPEED_ = -0.2f; // Velocidad de desplazamiento de los sprites
static constexpr int STATE_PRE_CREDITS_DURATION_ = 3000;
static constexpr int STATE_POST_CREDITS_DURATION_ = 5000;
static constexpr int STATE_FADE_DURATION_ = 5000;
// Objetos y punteros // Objetos y punteros
std::vector<std::shared_ptr<SAnimatedSprite>> sprites_; // Vector con todos los sprites a dibujar std::vector<std::shared_ptr<SAnimatedSprite>> sprites_; // Vector con todos los sprites a dibujar
@@ -24,15 +69,12 @@ private:
std::vector<std::shared_ptr<SMovingSprite>> texts_; // Vector con los sprites de texto std::vector<std::shared_ptr<SMovingSprite>> texts_; // Vector con los sprites de texto
// Variables // Variables
bool counter_enabled_; // Indica si está el contador habilitado Uint32 ticks_ = 0; // Contador de ticks para ajustar la velocidad del programa
int pre_counter_; // Contador previo
int post_counter_; // Contador posterior
bool post_counter_enabled_; // Indica si está habilitado el contador
Uint32 ticks_; // Contador de ticks para ajustar la velocidad del programa
std::vector<std::string> sprite_list_; // Lista con todos los sprites a dibujar std::vector<std::string> sprite_list_; // Lista con todos los sprites a dibujar
std::vector<Uint8> colors_; // Vector con los colores para el fade std::vector<Uint8> colors_; // Vector con los colores para el fade
int sprite_max_width_; // El valor de ancho del sprite mas ancho int sprite_max_width_ = 0; // El valor de ancho del sprite mas ancho
int sprite_max_height_; // El valor de alto del sprite mas alto int sprite_max_height_ = 0; // El valor de alto del sprite mas alto
State state_; // Controla el estado de la clase
// Actualiza el objeto // Actualiza el objeto
void update(); void update();
@@ -46,8 +88,8 @@ private:
// Comprueba las entradas // Comprueba las entradas
void checkInput(); void checkInput();
// Actualiza los contadores // Actualiza el estado
void updateCounters(); void updateState();
// Inicializa la lista de sprites // Inicializa la lista de sprites
void iniSpriteList(); void iniSpriteList();

View File

@@ -21,7 +21,7 @@ void initOptions()
options = Options(); options = Options();
#ifdef DEBUG #ifdef DEBUG
options.section = SectionState(Section::LOGO, Subsection::LOGO_TO_INTRO); options.section = SectionState(Section::ENDING2, Subsection::LOGO_TO_INTRO);
options.console = true; options.console = true;
#else #else
options.section = SectionState(Section::LOGO, Subsection::LOGO_TO_INTRO); options.section = SectionState(Section::LOGO, Subsection::LOGO_TO_INTRO);

View File

@@ -1,7 +1,8 @@
// IWYU pragma: no_include <bits/std_abs.h>
#include "surface.h" #include "surface.h"
#include <SDL2/SDL_error.h> // Para SDL_GetError #include <SDL2/SDL_error.h> // Para SDL_GetError
#include <bits/std_abs.h> // Para abs #include <SDL2/SDL_timer.h> // Para SDL_GetTicks
#include <stdlib.h> // Para abs #include <cmath> // Para abs
#include <algorithm> // Para min, max, copy_n, fill #include <algorithm> // Para min, max, copy_n, fill
#include <cstdint> // Para uint32_t #include <cstdint> // Para uint32_t
#include <cstring> // Para memcpy, size_t #include <cstring> // Para memcpy, size_t
@@ -566,7 +567,6 @@ void Surface::copyToTexture(SDL_Renderer *renderer, SDL_Texture *texture, SDL_Re
} }
} }
// Realiza un efecto de fundido en la paleta principal // Realiza un efecto de fundido en la paleta principal
bool Surface::fadePalette() bool Surface::fadePalette()
{ {
@@ -591,8 +591,23 @@ bool Surface::fadePalette()
} }
// Realiza un efecto de fundido en la paleta secundaria // Realiza un efecto de fundido en la paleta secundaria
bool Surface::fadeSubPalette() bool Surface::fadeSubPalette(Uint32 delay)
{ {
// Variable estática para almacenar el último tick
static Uint32 last_tick = 0;
// Obtener el tiempo actual
Uint32 current_tick = SDL_GetTicks();
// Verificar si ha pasado el tiempo de retardo
if (current_tick - last_tick < delay)
{
return false; // No se realiza el fade
}
// Actualizar el último tick
last_tick = current_tick;
// Verificar que el tamaño mínimo de sub_palette_ sea adecuado // Verificar que el tamaño mínimo de sub_palette_ sea adecuado
static constexpr int sub_palette_size = 19; static constexpr int sub_palette_size = 19;
if (sizeof(sub_palette_) / sizeof(sub_palette_[0]) < sub_palette_size) if (sizeof(sub_palette_) / sizeof(sub_palette_[0]) < sub_palette_size)

View File

@@ -91,7 +91,7 @@ public:
// Realiza un efecto de fundido en las paletas // Realiza un efecto de fundido en las paletas
bool fadePalette(); bool fadePalette();
bool fadeSubPalette(); bool fadeSubPalette(Uint32 delay = 0);
// Pone un pixel en la SurfaceData // Pone un pixel en la SurfaceData
void putPixel(int x, int y, Uint8 color); void putPixel(int x, int y, Uint8 color);