Files
jaildoctors_dilemma/source/game/gameplay/room_loader.cpp.yaml-cpp-backup

298 lines
10 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#include "room_loader.hpp"
#include <exception> // Para exception
#include <iostream> // Para cout, cerr
#include <yaml-cpp/yaml.h> // Para YAML::Node, YAML::LoadFile
#include "core/resources/resource_helper.hpp" // Para Resource::Helper
#include "utils/defines.hpp" // Para TILE_SIZE
#include "utils/utils.hpp" // Para stringToColor
// Convierte room connection de YAML a formato con extensión
auto RoomLoader::convertRoomConnection(const std::string& value) -> std::string {
if (value == "null" || value.empty()) {
return "0";
}
// "02" → "02.yaml"
return value + ".yaml";
}
// Convierte un tilemap 2D a vector 1D flat
auto RoomLoader::flattenTilemap(const std::vector<std::vector<int>>& tilemap_2d) -> std::vector<int> {
std::vector<int> tilemap_flat;
tilemap_flat.reserve(512); // 16 rows × 32 cols
for (const auto& row : tilemap_2d) {
for (int tile : row) {
tilemap_flat.push_back(tile);
}
}
return tilemap_flat;
}
// Carga un archivo de room en formato YAML
auto RoomLoader::loadYAML(const std::string& file_path, bool verbose) -> Room::Data {
Room::Data room;
// Extract filename for logging
const std::string FILE_NAME = file_path.substr(file_path.find_last_of("\\/") + 1);
try {
// Load YAML file using ResourceHelper (supports both filesystem and pack)
auto file_data = Resource::Helper::loadFile(file_path);
if (file_data.empty()) {
std::cerr << "Error: Unable to load file " << FILE_NAME << '\n';
return room;
}
// Parse YAML from string
std::string yaml_content(file_data.begin(), file_data.end());
YAML::Node yaml = YAML::Load(yaml_content);
// --- Parse room configuration ---
if (yaml["room"]) {
const YAML::Node& room_node = yaml["room"];
// Extract room number from filename (e.g., "01.yaml" → "01")
room.number = FILE_NAME.substr(0, FILE_NAME.find_last_of('.'));
// Basic properties
if (room_node["name"]) {
room.name = room_node["name"].as<std::string>();
}
if (room_node["bgColor"]) {
room.bg_color = room_node["bgColor"].as<std::string>();
}
if (room_node["border"]) {
room.border_color = room_node["border"].as<std::string>();
}
if (room_node["tileSetFile"]) {
room.tile_set_file = room_node["tileSetFile"].as<std::string>();
}
// Room connections
if (room_node["connections"]) {
const YAML::Node& conn = room_node["connections"];
if (conn["up"]) {
room.upper_room = convertRoomConnection(conn["up"].as<std::string>("null"));
} else {
room.upper_room = "0";
}
if (conn["down"]) {
room.lower_room = convertRoomConnection(conn["down"].as<std::string>("null"));
} else {
room.lower_room = "0";
}
if (conn["left"]) {
room.left_room = convertRoomConnection(conn["left"].as<std::string>("null"));
} else {
room.left_room = "0";
}
if (conn["right"]) {
room.right_room = convertRoomConnection(conn["right"].as<std::string>("null"));
} else {
room.right_room = "0";
}
}
// Item colors
if (room_node["itemColor1"]) {
room.item_color1 = room_node["itemColor1"].as<std::string>("yellow");
} else {
room.item_color1 = "yellow";
}
if (room_node["itemColor2"]) {
room.item_color2 = room_node["itemColor2"].as<std::string>("magenta");
} else {
room.item_color2 = "magenta";
}
// Conveyor belt direction
if (room_node["autoSurface"]) {
room.conveyor_belt_direction = room_node["autoSurface"].as<int>(0);
} else {
room.conveyor_belt_direction = 0;
}
}
// --- Parse tilemap ---
if (yaml["tilemap"]) {
const YAML::Node& tilemap_node = yaml["tilemap"];
// Read 2D array
std::vector<std::vector<int>> tilemap_2d;
tilemap_2d.reserve(16);
for (const auto& row_node : tilemap_node) {
std::vector<int> row;
row.reserve(32);
for (const auto& tile_node : row_node) {
row.push_back(tile_node.as<int>());
}
tilemap_2d.push_back(row);
}
// Convert to 1D flat array
room.tile_map = flattenTilemap(tilemap_2d);
if (verbose) {
std::cout << "Loaded tilemap: " << room.tile_map.size() << " tiles\n";
}
} else {
std::cerr << "Warning: No tilemap found in " << FILE_NAME << '\n';
}
// --- Parse enemies ---
if (yaml["enemies"] && !yaml["enemies"].IsNull()) {
const YAML::Node& enemies_node = yaml["enemies"];
for (const auto& enemy_node : enemies_node) {
Enemy::Data enemy;
// Animation path
if (enemy_node["animation"]) {
enemy.animation_path = enemy_node["animation"].as<std::string>();
}
// Position (in tiles, convert to pixels)
if (enemy_node["position"]) {
const YAML::Node& pos = enemy_node["position"];
if (pos["x"]) {
enemy.x = pos["x"].as<float>() * TILE_SIZE;
}
if (pos["y"]) {
enemy.y = pos["y"].as<float>() * TILE_SIZE;
}
}
// Velocity (already in pixels/second)
if (enemy_node["velocity"]) {
const YAML::Node& vel = enemy_node["velocity"];
if (vel["x"]) {
enemy.vx = vel["x"].as<float>();
}
if (vel["y"]) {
enemy.vy = vel["y"].as<float>();
}
}
// Boundaries (in tiles, convert to pixels)
if (enemy_node["boundaries"]) {
const YAML::Node& bounds = enemy_node["boundaries"];
if (bounds["x1"]) {
enemy.x1 = bounds["x1"].as<int>() * TILE_SIZE;
}
if (bounds["y1"]) {
enemy.y1 = bounds["y1"].as<int>() * TILE_SIZE;
}
if (bounds["x2"]) {
enemy.x2 = bounds["x2"].as<int>() * TILE_SIZE;
}
if (bounds["y2"]) {
enemy.y2 = bounds["y2"].as<int>() * TILE_SIZE;
}
}
// Color
if (enemy_node["color"]) {
enemy.color = enemy_node["color"].as<std::string>("white");
} else {
enemy.color = "white";
}
// Optional fields
if (enemy_node["flip"]) {
enemy.flip = enemy_node["flip"].as<bool>(false);
} else {
enemy.flip = false;
}
if (enemy_node["mirror"]) {
enemy.mirror = enemy_node["mirror"].as<bool>(false);
} else {
enemy.mirror = false;
}
if (enemy_node["frame"]) {
enemy.frame = enemy_node["frame"].as<int>(-1);
} else {
enemy.frame = -1;
}
room.enemies.push_back(enemy);
}
if (verbose) {
std::cout << "Loaded " << room.enemies.size() << " enemies\n";
}
}
// --- Parse items ---
if (yaml["items"] && !yaml["items"].IsNull()) {
const YAML::Node& items_node = yaml["items"];
for (const auto& item_node : items_node) {
Item::Data item;
// Tileset file
if (item_node["tileSetFile"]) {
item.tile_set_file = item_node["tileSetFile"].as<std::string>();
}
// Tile index
if (item_node["tile"]) {
item.tile = item_node["tile"].as<int>();
}
// Position (in tiles, convert to pixels)
if (item_node["position"]) {
const YAML::Node& pos = item_node["position"];
if (pos["x"]) {
item.x = pos["x"].as<float>() * TILE_SIZE;
}
if (pos["y"]) {
item.y = pos["y"].as<float>() * TILE_SIZE;
}
}
// Counter
if (item_node["counter"]) {
item.counter = item_node["counter"].as<int>(0);
} else {
item.counter = 0;
}
// Colors (assigned from room defaults)
item.color1 = stringToColor(room.item_color1);
item.color2 = stringToColor(room.item_color2);
room.items.push_back(item);
}
if (verbose) {
std::cout << "Loaded " << room.items.size() << " items\n";
}
}
if (verbose) {
std::cout << "Room loaded successfully: " << FILE_NAME << '\n';
}
} catch (const YAML::Exception& e) {
std::cerr << "YAML parsing error in " << FILE_NAME << ": " << e.what() << '\n';
} catch (const std::exception& e) {
std::cerr << "Error loading room " << FILE_NAME << ": " << e.what() << '\n';
}
return room;
}