diff --git a/src/roadstop_base.h b/src/roadstop_base.h --- a/src/roadstop_base.h +++ b/src/roadstop_base.h @@ -25,9 +25,46 @@ struct RoadStop : RoadStopPool::PoolItem RSSFB_BAY0_FREE = 0, ///< Non-zero when bay 0 is free RSSFB_BAY1_FREE = 1, ///< Non-zero when bay 1 is free RSSFB_BAY_COUNT = 2, ///< Max. number of bays + RSSFB_BASE_ENTRY = 6, ///< Non-zero when the entries on this road stop are the primary, i.e. the ones to delete RSSFB_ENTRY_BUSY = 7, ///< Non-zero when roadstop entry is busy }; + /** Container for each entry point of a drive through road stop */ + struct Entry { + private: + int length; ///< The length of the stop in tile 'units' + int occupied; ///< The amount of occupied stop in tile 'units' + + public: + friend class RoadStop; ///< Oh yeah, the road stop may play with me. + + /** Create an entry */ + Entry() : length(0), occupied(0) {} + + /** + * Get the length of this drive through stop. + * @return the length in tile units. + */ + FORCEINLINE int GetLength() const + { + return this->length; + } + + /** + * Get the amount of occupied space in this drive through stop. + * @return the occupied space in tile units. + */ + FORCEINLINE int GetOccupied() const + { + return this->occupied; + } + + void Leave(const RoadVehicle *rv); + void Enter(const RoadVehicle *rv); + void CheckIntegrity(const RoadStop *rs) const; + void Rebuild(const RoadStop *rs, int side = -1); + }; + static const uint LIMIT = 16; ///< The maximum amount of roadstops that are allowed at a single station TileIndex xy; ///< Position on the map @@ -80,6 +117,29 @@ struct RoadStop : RoadStopPool::PoolItem SB(this->status, RSSFB_ENTRY_BUSY, 1, busy); } + /** + * Get the drive through road stop entry struct for the given direction. + * @param direction the direciton to get the entry for + * @return the entry + */ + FORCEINLINE const Entry *GetEntry(DiagDirection dir) const + { + return HasBit((int)dir, 1) ? this->west : this->east; + } + + /** + * Get the drive through road stop entry struct for the given direction. + * @param direction the direciton to get the entry for + * @return the entry + */ + FORCEINLINE Entry *GetEntry(DiagDirection dir) + { + return HasBit((int)dir, 1) ? this->west : this->east; + } + + void MakeDriveThrough(); + void ClearDriveThrough(); + void Leave(RoadVehicle *rv); bool Enter(RoadVehicle *rv); @@ -87,7 +147,12 @@ struct RoadStop : RoadStopPool::PoolItem static RoadStop *GetByTile(TileIndex tile, RoadStopType type); + static bool IsDriveThroughRoadStopContinuation(TileIndex rs, TileIndex next); + private: + Entry *east; ///< The vehicles that entered from the east + Entry *west; ///< The vehicles that entered from the west + /** * Allocates a bay * @return the allocated bay number