#pragma once

#include <memory>            // Para unique_ptr, shared_ptr
#include "animated_sprite.h" // Para AnimatedSprite
#include "smart_sprite.h"    // Para SmartSprite
#include "sprite.h"          // Para Sprite

class Texture;

// Clase GameLogo
class GameLogo
{
public:
    // --- Constructores y destructor ---
    GameLogo(int x, int y);
    ~GameLogo() = default;

    // --- Métodos principales ---
    void render(); // Pinta la clase en pantalla
    void update(); // Actualiza la lógica de la clase
    void enable(); // Activa la clase

    // --- Getters ---
    bool hasFinished() const; // Indica si ha terminado la animación

private:
    // --- Tipos internos ---
    enum class Status
    {
        DISABLED,
        MOVING,
        SHAKING,
        FINISHED,
    };

    struct Shake
    {
        int desp = 1;           // Pixels de desplazamiento para agitar la pantalla en el eje x
        int delay = 2;          // Retraso entre cada desplazamiento de la pantalla al agitarse
        int lenght = 8;         // Cantidad de desplazamientos a realizar
        int remaining = lenght; // Cantidad de desplazamientos pendientes a realizar
        int counter = delay;    // Contador para el retraso
        int origin = 0;         // Valor inicial de la pantalla para dejarla igual tras el desplazamiento

        Shake() = default;
        Shake(int d, int de, int l, int o)
            : desp(d), delay(de), lenght(l), remaining(l), counter(de), origin(o) {}

        void init(int d, int de, int l, int o)
        {
            desp = d;
            delay = de;
            lenght = l;
            remaining = l;
            counter = de;
            origin = o;
        }
    };

    // --- Objetos y punteros ---
    std::shared_ptr<Texture> dust_texture_;           // Textura con los graficos del polvo
    std::shared_ptr<Texture> coffee_texture_;         // Textura con los graficos de la palabra "COFFEE"
    std::shared_ptr<Texture> crisis_texture_;         // Textura con los graficos de la palabra "CRISIS"
    std::shared_ptr<Texture> arcade_edition_texture_; // Textura con los graficos de "Arcade Edition"

    std::unique_ptr<AnimatedSprite> dust_left_sprite_;  // Sprite del polvo (izquierda)
    std::unique_ptr<AnimatedSprite> dust_right_sprite_; // Sprite del polvo (derecha)
    std::unique_ptr<SmartSprite> coffee_sprite_;        // Sprite de "COFFEE"
    std::unique_ptr<SmartSprite> crisis_sprite_;        // Sprite de "CRISIS"
    std::unique_ptr<Sprite> arcade_edition_sprite_;     // Sprite de "Arcade Edition"

    // --- Variables de estado ---
    float x_;                       // Posición X del logo
    float y_;                       // Posición Y del logo
    float zoom_ = 1.0f;             // Zoom aplicado al texto "ARCADE EDITION"
    int post_finished_counter_ = 1; // Contador final tras animaciones

    Status coffee_crisis_status_ = Status::DISABLED;  // Estado de "COFFEE CRISIS"
    Status arcade_edition_status_ = Status::DISABLED; // Estado de "ARCADE EDITION"
    Shake shake_;                                     // Efecto de agitación

    // --- Métodos internos ---
    void init();                  // Inicializa las variables
    int getInitialVerticalDesp(); // Calcula el desplazamiento vertical inicial
};