fix: minimap sempre tirava a gastar standard.gif
This commit is contained in:
@@ -21,7 +21,6 @@
|
||||
MiniMap::MiniMap(Uint8 bg_color, Uint8 conn_color)
|
||||
: bg_color_(bg_color),
|
||||
conn_color_(conn_color) {
|
||||
buildTileColorTable("standard.gif");
|
||||
layoutRooms();
|
||||
buildRoomSurfaces();
|
||||
composeFinalSurface();
|
||||
@@ -34,47 +33,54 @@ void MiniMap::rebuild(Uint8 bg_color, Uint8 conn_color) {
|
||||
composeFinalSurface();
|
||||
}
|
||||
|
||||
// Analiza el tileset y crea tabla: tile_index → color predominante
|
||||
void MiniMap::buildTileColorTable(const std::string& tileset_name) {
|
||||
// Devuelve (construyendo si hace falta) la tabla de color predominante para un tileset
|
||||
auto MiniMap::getOrBuildTileColorTable(const std::string& tileset_name) -> const TileColorTable& {
|
||||
auto it = tileset_tables_.find(tileset_name);
|
||||
if (it != tileset_tables_.end()) { return it->second; }
|
||||
|
||||
// Inserta entrada vacía. Si el tileset no se puede cargar, esto evita reintentos.
|
||||
auto& table = tileset_tables_[tileset_name];
|
||||
|
||||
auto tileset = Resource::Cache::get()->getSurface(tileset_name);
|
||||
if (!tileset) { return; }
|
||||
if (!tileset) { return table; }
|
||||
|
||||
tileset_width_ = static_cast<int>(tileset->getWidth()) / Tile::SIZE;
|
||||
tileset_transparent_ = tileset->getTransparentColor();
|
||||
table.tileset_width = static_cast<int>(tileset->getWidth()) / Tile::SIZE;
|
||||
table.transparent = tileset->getTransparentColor();
|
||||
int tileset_height = static_cast<int>(tileset->getHeight()) / Tile::SIZE;
|
||||
int total_tiles = tileset_width_ * tileset_height;
|
||||
int total_tiles = table.tileset_width * tileset_height;
|
||||
|
||||
tile_colors_.resize(total_tiles, 0);
|
||||
table.colors.resize(total_tiles, 0);
|
||||
|
||||
for (int tile = 0; tile < total_tiles; ++tile) {
|
||||
int tile_x = (tile % tileset_width_) * Tile::SIZE;
|
||||
int tile_y = (tile / tileset_width_) * Tile::SIZE;
|
||||
int tile_x = (tile % table.tileset_width) * Tile::SIZE;
|
||||
int tile_y = (tile / table.tileset_width) * Tile::SIZE;
|
||||
|
||||
// Contar frecuencia de cada color en el tile (ignorar el color transparente del tileset)
|
||||
Uint8 transparent = tileset->getTransparentColor();
|
||||
std::array<int, 256> freq{};
|
||||
for (int y = 0; y < Tile::SIZE; ++y) {
|
||||
for (int x = 0; x < Tile::SIZE; ++x) {
|
||||
Uint8 pixel = tileset->getPixel(tile_x + x, tile_y + y);
|
||||
if (pixel != transparent) {
|
||||
if (pixel != table.transparent) {
|
||||
freq[pixel]++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Encontrar el color más frecuente (transparent = tile vacío, no se pinta)
|
||||
Uint8 best_color = transparent;
|
||||
Uint8 best_color = table.transparent;
|
||||
int best_count = 0;
|
||||
for (int c = 0; c < 256; ++c) {
|
||||
if (c == transparent) { continue; }
|
||||
if (c == table.transparent) { continue; }
|
||||
if (freq[c] > best_count) {
|
||||
best_count = freq[c];
|
||||
best_color = static_cast<Uint8>(c);
|
||||
}
|
||||
}
|
||||
|
||||
tile_colors_[tile] = best_color;
|
||||
table.colors[tile] = best_color;
|
||||
}
|
||||
|
||||
return table;
|
||||
}
|
||||
|
||||
// Posiciona las rooms en un grid usando BFS desde las conexiones
|
||||
@@ -178,6 +184,9 @@ auto MiniMap::getRoomMiniSurface(const std::string& room_name) -> std::shared_pt
|
||||
}
|
||||
if (!room_data) { return nullptr; }
|
||||
|
||||
// Tabla de colores específica del tileset que usa esta room (cacheada).
|
||||
const auto& table = getOrBuildTileColorTable(room_data->tile_set_file);
|
||||
|
||||
auto surface = std::make_shared<Surface>(ROOM_W, ROOM_H);
|
||||
|
||||
auto prev = Screen::get()->getRendererSurface();
|
||||
@@ -191,10 +200,10 @@ auto MiniMap::getRoomMiniSurface(const std::string& room_name) -> std::shared_pt
|
||||
if (index >= static_cast<int>(tile_map.size())) { continue; }
|
||||
|
||||
int tile = tile_map[index];
|
||||
if (tile < 0 || tile >= static_cast<int>(tile_colors_.size())) { continue; }
|
||||
if (tile < 0 || tile >= static_cast<int>(table.colors.size())) { continue; }
|
||||
|
||||
Uint8 color = tile_colors_[tile];
|
||||
if (color != tileset_transparent_) {
|
||||
Uint8 color = table.colors[tile];
|
||||
if (color != table.transparent) {
|
||||
surface->putPixel(x, y, color);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -49,7 +49,14 @@ class MiniMap {
|
||||
GridPos pos; // Posición en el grid
|
||||
};
|
||||
|
||||
void buildTileColorTable(const std::string& tileset_name);
|
||||
// Tabla de color predominante para un tileset concreto
|
||||
struct TileColorTable {
|
||||
std::vector<Uint8> colors; // tile_index → palette color
|
||||
int tileset_width{0}; // Ancho del tileset en tiles
|
||||
Uint8 transparent{16}; // Color transparente del tileset
|
||||
};
|
||||
|
||||
auto getOrBuildTileColorTable(const std::string& tileset_name) -> const TileColorTable&;
|
||||
void buildRoomSurfaces();
|
||||
void layoutRooms();
|
||||
void composeFinalSurface();
|
||||
@@ -59,10 +66,8 @@ class MiniMap {
|
||||
auto cellPixelX(int grid_x) const -> int { return PADDING + ((grid_x - min_grid_x_) * (CELL_W + GAP)); }
|
||||
auto cellPixelY(int grid_y) const -> int { return PADDING + ((grid_y - min_grid_y_) * (CELL_H + GAP)); }
|
||||
|
||||
// Tabla de color predominante por tile index
|
||||
std::vector<Uint8> tile_colors_; // tile_index → palette color index
|
||||
int tileset_width_{0}; // Ancho del tileset en tiles
|
||||
Uint8 tileset_transparent_{16}; // Color transparente del tileset
|
||||
// Caché de tablas de color por tileset (clave: nombre del fichero del tileset)
|
||||
std::unordered_map<std::string, TileColorTable> tileset_tables_;
|
||||
|
||||
// Rooms renderizadas y posicionadas
|
||||
std::unordered_map<std::string, RoomMini> room_positions_;
|
||||
|
||||
Reference in New Issue
Block a user