Files
coffee_crisis_arcade_edition/source/game_logo.cpp

206 lines
6.5 KiB
C++

#include "game_logo.h"
#include <SDL2/SDL_render.h> // for SDL_FLIP_HORIZONTAL
#include <algorithm> // for max
#include "animated_sprite.h" // for SpriteAnimated
#include "asset.h" // for Asset
#include "jail_audio.h" // for JA_DeleteSound, JA_LoadSound, JA_PlaySound
#include "param.h" // for param
#include "screen.h" // for Screen
#include "smart_sprite.h" // for SpriteSmart
#include "sprite.h" // for Sprite
#include "texture.h" // for Texture
#include "utils.h" // for Param, ParamGame, ParamTitle
// Constructor
GameLogo::GameLogo(int x, int y)
: dust_texture_(std::make_shared<Texture>(Screen::get()->getRenderer(), Asset::get()->get("title_dust.png"))),
coffee_texture_(std::make_shared<Texture>(Screen::get()->getRenderer(), Asset::get()->get("title_coffee.png"))),
crisis_texture_(std::make_shared<Texture>(Screen::get()->getRenderer(), Asset::get()->get("title_crisis.png"))),
arcade_edition_texture_(std::make_shared<Texture>(Screen::get()->getRenderer(), Asset::get()->get("title_arcade_edition.png"))),
dust_left_sprite_(std::make_unique<AnimatedSprite>(dust_texture_, Asset::get()->get("title_dust.ani"))),
dust_right_sprite_(std::make_unique<AnimatedSprite>(dust_texture_, Asset::get()->get("title_dust.ani"))),
coffee_sprite_(std::make_unique<SmartSprite>(coffee_texture_)),
crisis_sprite_(std::make_unique<SmartSprite>(crisis_texture_)),
arcade_edition_sprite_(std::make_unique<Sprite>(arcade_edition_texture_, (param.game.width - arcade_edition_texture_->getWidth()) / 2, param.title.arcade_edition_position, arcade_edition_texture_->getWidth(), arcade_edition_texture_->getHeight())),
crash_sound_(JA_LoadSound(Asset::get()->get("title.wav").c_str())),
x_(x),
y_(y)
{
// Inicializa las variables
init();
}
// Destructor
GameLogo::~GameLogo()
{
JA_DeleteSound(crash_sound_);
}
// Inicializa las variables
void GameLogo::init()
{
const auto xp = x_ - coffee_sprite_->getWidth() / 2;
const auto desp = getInitialVerticalDesp();
// Variables
status_ = Status::DISABLED;
shake_.desp = 1;
shake_.delay = 2;
shake_.lenght = 8;
shake_.remaining = shake_.lenght;
shake_.counter = shake_.delay;
shake_.origin = xp;
// Inicializa el bitmap de 'Coffee'
coffee_sprite_->init();
coffee_sprite_->setPosX(xp);
coffee_sprite_->setPosY(y_ - coffee_texture_->getHeight() - desp);
coffee_sprite_->setWidth(coffee_texture_->getWidth());
coffee_sprite_->setHeight(coffee_texture_->getHeight());
coffee_sprite_->setVelX(0.0f);
coffee_sprite_->setVelY(2.5f);
coffee_sprite_->setAccelX(0.0f);
coffee_sprite_->setAccelY(0.1f);
coffee_sprite_->setSpriteClip(0, 0, coffee_texture_->getWidth(), coffee_texture_->getHeight());
coffee_sprite_->setEnabled(true);
coffee_sprite_->setFinishedCounter(0);
coffee_sprite_->setDestX(xp);
coffee_sprite_->setDestY(y_ - coffee_texture_->getHeight());
// Inicializa el bitmap de 'Crisis'
crisis_sprite_->init();
crisis_sprite_->setPosX(xp + 15);
crisis_sprite_->setPosY(y_ + desp);
crisis_sprite_->setWidth(crisis_texture_->getWidth());
crisis_sprite_->setHeight(crisis_texture_->getHeight());
crisis_sprite_->setVelX(0.0f);
crisis_sprite_->setVelY(-2.5f);
crisis_sprite_->setAccelX(0.0f);
crisis_sprite_->setAccelY(-0.1f);
crisis_sprite_->setSpriteClip(0, 0, crisis_texture_->getWidth(), crisis_texture_->getHeight());
crisis_sprite_->setEnabled(true);
crisis_sprite_->setFinishedCounter(0);
crisis_sprite_->setDestX(xp + 15);
crisis_sprite_->setDestY(y_);
// Inicializa el bitmap de 'DustRight'
dust_right_sprite_->resetAnimation();
dust_right_sprite_->setPosX(coffee_sprite_->getPosX() + coffee_sprite_->getWidth());
dust_right_sprite_->setPosY(y_);
dust_right_sprite_->setWidth(16);
dust_right_sprite_->setHeight(16);
dust_right_sprite_->setFlip(SDL_FLIP_HORIZONTAL);
// Inicializa el bitmap de 'DustLeft'
dust_left_sprite_->resetAnimation();
dust_left_sprite_->setPosX(coffee_sprite_->getPosX() - 16);
dust_left_sprite_->setPosY(y_);
dust_left_sprite_->setWidth(16);
dust_left_sprite_->setHeight(16);
}
// Pinta la clase en pantalla
void GameLogo::render()
{
// Dibuja el logo
coffee_sprite_->render();
crisis_sprite_->render();
if (status_ == Status::FINISHED)
{
arcade_edition_sprite_->render();
}
// Dibuja el polvillo del logo
dust_right_sprite_->render();
dust_left_sprite_->render();
}
// Actualiza la lógica de la clase
void GameLogo::update()
{
if (status_ == Status::MOVING)
{
coffee_sprite_->update();
crisis_sprite_->update();
// Si los objetos han llegado a su destino, cambiamos de Sección
if (coffee_sprite_->hasFinished() && crisis_sprite_->hasFinished())
{
status_ = Status::SHAKING;
// Reproduce el efecto sonoro
JA_PlaySound(crash_sound_);
}
}
else if (status_ == Status::SHAKING)
{
// Agita el logo
if (shake_.remaining > 0)
{
if (shake_.counter > 0)
{
shake_.counter--;
}
else
{
shake_.counter = shake_.delay;
const auto desp = shake_.remaining % 2 == 0 ? shake_.desp * (-1) : shake_.desp;
coffee_sprite_->setPosX(shake_.origin + desp);
crisis_sprite_->setPosX(shake_.origin + desp + 15);
shake_.remaining--;
}
}
else
{
coffee_sprite_->setPosX(shake_.origin);
crisis_sprite_->setPosX(shake_.origin + 15);
status_ = Status::FINISHED;
}
dust_right_sprite_->update();
dust_left_sprite_->update();
}
else if (status_ == Status::FINISHED)
{
dust_right_sprite_->update();
dust_left_sprite_->update();
}
}
// Activa la clase
void GameLogo::enable()
{
init();
status_ = Status::MOVING;
}
// Indica si ha terminado la animación
bool GameLogo::hasFinished() const
{
return status_ == Status::FINISHED;
}
// Recarga las texturas
void GameLogo::reLoad()
{
dust_texture_->reLoad();
coffee_texture_->reLoad();
crisis_texture_->reLoad();
}
// Calcula el desplazamiento vertical inicial
int GameLogo::getInitialVerticalDesp()
{
auto desp_up = y_;
auto desp_down = param.game.height - y_;
return std::max(desp_up, desp_down);
}