#pragma once #include #include "utils/defines.hpp" class TileCollider { public: enum class Tile : int { EMPTY = 0, WALL = 1, PASSABLE = 2, SLOPE_L = 3, SLOPE_R = 4, KILL = 5 }; struct FloorHit { float y{-1}; Tile type{Tile::EMPTY}; int tile_x{0}; int tile_y{0}; }; struct SlopeInfo { bool on_slope{false}; Tile type{Tile::EMPTY}; int tile_x{0}; int tile_y{0}; float surface_y{0}; }; // Constructor: recibe el tilemap extendido y sus dimensiones. // border_px es el offset en píxeles para traducir coordenadas de room-space a extended-map. TileCollider(const std::vector& extended_tile_map, int width, int height, int border_px); // Queries básicas [[nodiscard]] auto getTileAt(int tile_x, int tile_y) const -> Tile; [[nodiscard]] auto isSolid(int tile_x, int tile_y) const -> bool; [[nodiscard]] auto getSlopeY(int tile_x, int tile_y, float px) const -> float; // Colisión para el Player [[nodiscard]] auto checkWallLeft(float x, float y, float w, float h) const -> float; [[nodiscard]] auto checkWallRight(float x, float y, float w, float h) const -> float; [[nodiscard]] auto checkCeiling(float x, float y, float w) const -> float; [[nodiscard]] auto checkFloor(float x, float foot_y_current, float w, float foot_y_new) const -> FloorHit; [[nodiscard]] auto hasGroundBelow(float x, float foot_y, float w) const -> bool; [[nodiscard]] auto checkSlopeBelow(float x, float foot_y, float w) const -> SlopeInfo; // Devuelve true si el jugador está parcialmente dentro de algún tile de slope [[nodiscard]] auto isInsideAnySlope(float x, float foot_y, float w) const -> bool; // Devuelve true si el rectángulo del jugador solapa algún tile KILL [[nodiscard]] auto touchesKillTile(float x, float y, float w, float h) const -> bool; private: static constexpr int TS = ::Tile::SIZE; int width_; // Ancho total del tilemap extendido (en tiles) int height_; // Alto total del tilemap extendido (en tiles) int border_px_; // Offset en píxeles (CollisionBorder::PX) const std::vector& tile_map_; // Convierte píxeles en room-space a índice de tile en el mapa extendido. // Nota: asume que px >= -border_px_ (el jugador no puede estar más allá del borde). [[nodiscard]] auto toTile(int px) const -> int { return (px + border_px_) / TS; } // Convierte índice de tile del mapa extendido a píxeles en room-space. [[nodiscard]] auto toPixel(int tile) const -> float { return static_cast((tile * TS) - border_px_); } };