diff --git a/source/scoreboard.cpp b/source/scoreboard.cpp index f07cc72e..06122534 100644 --- a/source/scoreboard.cpp +++ b/source/scoreboard.cpp @@ -9,6 +9,7 @@ #include "screen.h" // for Screen #include "text.h" // for Text #include "texture.h" // for Texture +#include // Constructor Scoreboard::Scoreboard(std::shared_ptr data) @@ -17,6 +18,9 @@ Scoreboard::Scoreboard(std::shared_ptr data) asset_(Asset::get()), data_(data) { + const int TEXTURE_WIDTH_ = options.game.width; + constexpr int TEXTURE_HEIGHT_ = 6 * BLOCK; + // Reserva memoria para los objetos item_texture_ = resource_->getTexture("items.png"); auto player_texture = resource_->getTexture(options.cheats.alternate_skin == Cheat::CheatState::ENABLED ? "player2.png" : "player.png"); @@ -25,6 +29,16 @@ Scoreboard::Scoreboard(std::shared_ptr data) player_sprite_->setCurrentAnimation("walk_menu"); text_ = resource_->getText("smb2"); + texture_ = SDL_CreateTexture(renderer_, SDL_PIXELFORMAT_RGBA8888, SDL_TEXTUREACCESS_TARGET, TEXTURE_WIDTH_, TEXTURE_HEIGHT_); + if (texture_ == nullptr) + { + if (options.console) + { + std::cout << "Scorebard::texture_ could not be created!\nSDL Error: " << SDL_GetError() << std::endl; + } + } + texture_dest_ = {0, options.game.height - TEXTURE_HEIGHT_, TEXTURE_WIDTH_, TEXTURE_HEIGHT_}; + // Inicializa las variables counter_ = 0; change_color_speed_ = 4; @@ -41,51 +55,16 @@ Scoreboard::Scoreboard(std::shared_ptr data) } } +// Destructor +Scoreboard::~Scoreboard() +{ + SDL_DestroyTexture(texture_); +} + // Pinta el objeto en pantalla void Scoreboard::render() { - // Anclas - const int line1 = 19 * BLOCK; - const int line2 = line1 + (2 * BLOCK); - - // Dibuja el fondo del marcador - const SDL_Rect rect = {0, 18 * BLOCK, PLAY_AREA_WIDTH, GAMECANVAS_HEIGHT - PLAY_AREA_HEIGHT}; - SDL_SetRenderDrawColor(renderer_, 0, 0, 0, 255); - SDL_RenderFillRect(renderer_, &rect); - - // Dibuja las vidas - const int desp = (counter_ / 40) % 8; - const int frame = desp % 4; - player_sprite_->setCurrentAnimationFrame(frame); - player_sprite_->setPosY(line2); - for (int i = 0; i < data_->lives; ++i) - { - player_sprite_->setPosX(8 + (16 * i) + desp); - const int index = i % color_.size(); - player_sprite_->getTexture()->setColor(color_[index].r, color_[index].g, color_[index].b); - player_sprite_->render(); - } - - // Muestra si suena la música - if (data_->music) - { - const Color c = data_->color; - SDL_Rect clip = {0, 8, 8, 8}; - item_texture_->setColor(c.r, c.g, c.b); - item_texture_->render(20 * BLOCK, line2, &clip); - } - - // Escribe los textos - const std::string timeTxt = std::to_string((clock_.minutes % 100) / 10) + std::to_string(clock_.minutes % 10) + clock_.separator + std::to_string((clock_.seconds % 60) / 10) + std::to_string(clock_.seconds % 10); - const std::string itemsTxt = std::to_string(data_->items / 100) + std::to_string((data_->items % 100) / 10) + std::to_string(data_->items % 10); - this->text_->writeColored(BLOCK, line1, "Items collected ", data_->color); - this->text_->writeColored(17 * BLOCK, line1, itemsTxt, items_color_); - this->text_->writeColored(20 * BLOCK, line1, " Time ", data_->color); - this->text_->writeColored(26 * BLOCK, line1, timeTxt, stringToColor(options.video.palette, "white")); - - const std::string roomsTxt = std::to_string(data_->rooms / 100) + std::to_string((data_->rooms % 100) / 10) + std::to_string(data_->rooms % 10); - this->text_->writeColored(22 * BLOCK, line2, "Rooms", stringToColor(options.video.palette, "white")); - this->text_->writeColored(28 * BLOCK, line2, roomsTxt, stringToColor(options.video.palette, "white")); + SDL_RenderCopy(renderer_, texture_, nullptr, &texture_dest_); } // Actualiza las variables del objeto @@ -97,6 +76,9 @@ void Scoreboard::update() // Actualiza el color de la cantidad de items recogidos updateItemsColor(); + // Dibuja la textura + fillTexture(); + if (!is_paused_) { // Si está en pausa no se actualiza el reloj @@ -175,4 +157,57 @@ void Scoreboard::updateItemsColor() int Scoreboard::getMinutes() { return getTime().minutes; +} + +// Dibuja los elementos del marcador en la textura +void Scoreboard::fillTexture() +{ + // Empieza a dibujar en la textura + auto temp = SDL_GetRenderTarget(renderer_); + SDL_SetRenderTarget(renderer_, texture_); + + // Limpia la textura + SDL_SetRenderDrawColor(renderer_, 0, 0, 0, 255); + SDL_RenderFillRect(renderer_, nullptr); + + // Anclas + constexpr int LINE1 = BLOCK; + constexpr int LINE2 = 3 * BLOCK; + + // Dibuja las vidas + const int desp = (counter_ / 40) % 8; + const int frame = desp % 4; + player_sprite_->setCurrentAnimationFrame(frame); + player_sprite_->setPosY(LINE2); + for (int i = 0; i < data_->lives; ++i) + { + player_sprite_->setPosX(8 + (16 * i) + desp); + const int index = i % color_.size(); + player_sprite_->getTexture()->setColor(color_[index].r, color_[index].g, color_[index].b); + player_sprite_->render(); + } + + // Muestra si suena la música + if (data_->music) + { + const Color c = data_->color; + SDL_Rect clip = {0, 8, 8, 8}; + item_texture_->setColor(c.r, c.g, c.b); + item_texture_->render(20 * BLOCK, LINE2, &clip); + } + + // Escribe los textos + const std::string timeTxt = std::to_string((clock_.minutes % 100) / 10) + std::to_string(clock_.minutes % 10) + clock_.separator + std::to_string((clock_.seconds % 60) / 10) + std::to_string(clock_.seconds % 10); + const std::string itemsTxt = std::to_string(data_->items / 100) + std::to_string((data_->items % 100) / 10) + std::to_string(data_->items % 10); + text_->writeColored(BLOCK, LINE1, "Items collected ", data_->color); + text_->writeColored(17 * BLOCK, LINE1, itemsTxt, items_color_); + text_->writeColored(20 * BLOCK, LINE1, " Time ", data_->color); + text_->writeColored(26 * BLOCK, LINE1, timeTxt, stringToColor(options.video.palette, "white")); + + const std::string roomsTxt = std::to_string(data_->rooms / 100) + std::to_string((data_->rooms % 100) / 10) + std::to_string(data_->rooms % 10); + text_->writeColored(22 * BLOCK, LINE2, "Rooms", stringToColor(options.video.palette, "white")); + text_->writeColored(28 * BLOCK, LINE2, roomsTxt, stringToColor(options.video.palette, "white")); + + // Deja el renderizador como estaba + SDL_SetRenderTarget(renderer_, temp); } \ No newline at end of file diff --git a/source/scoreboard.h b/source/scoreboard.h index 593b147f..715a20c0 100644 --- a/source/scoreboard.h +++ b/source/scoreboard.h @@ -46,6 +46,7 @@ private: std::shared_ptr player_sprite_; // Sprite para mostrar las vidas en el marcador std::shared_ptr item_texture_; // Textura con los graficos para las vidas std::shared_ptr data_; // Contiene las variables a mostrar en el marcador + SDL_Texture *texture_; // Textura donde dibujar el marcador; // Variables std::vector color_; // Vector con los colores del objeto @@ -56,6 +57,7 @@ private: Uint32 paused_time_elapsed_; // Tiempo acumulado en pausa ClockData clock_; // Contiene las horas, minutos y segundos transcurridos desde el inicio de la partida Color items_color_; // Color de la cantidad de items recogidos + SDL_Rect texture_dest_; // Rectangulo donde dibujar la textura del marcador // Obtiene el tiempo transcurrido de partida ClockData getTime(); @@ -63,12 +65,15 @@ private: // Actualiza el color de la cantidad de items recogidos void updateItemsColor(); + // Dibuja los elementos del marcador en la textura + void fillTexture(); + public: // Constructor Scoreboard(std::shared_ptr data); // Destructor - ~Scoreboard() = default; + ~Scoreboard(); // Pinta el objeto en pantalla void render();