Fix #15495: unable to build bridge over default waypoints

This commit is contained in:
Peter Nelson
2026-04-30 21:43:10 +01:00
committed by Peter Nelson
parent b5abd08a52
commit 1be2cd0c9a
3 changed files with 28 additions and 13 deletions
+4 -11
View File
@@ -1226,16 +1226,9 @@ CommandCost CanExpandRailStation(const BaseStation *st, TileArea &new_ta)
return CommandCost();
}
RailStationTileLayout::RailStationTileLayout(const StationSpec *spec, uint8_t platforms, uint8_t length) : platforms(platforms), length(length)
{
if (spec == nullptr) return;
/* Look for a predefined layout for the required size. */
auto found = spec->layouts.find(GetStationLayoutKey(platforms, length));
if (found != std::end(spec->layouts)) this->layout = found->second;
}
StationGfx RailStationTileLayout::Iterator::operator*() const
/** @copydoc RailStationTileLayout::Iterator::operator* */
template <>
StationGfx RailStationTileLayout<StationType::Rail>::Iterator::operator*() const
{
/* Use predefined layout if it exists. Mask bit zero which will indicate axis. */
if (!stl.layout.empty()) return this->stl.layout[this->position] & ~1;
@@ -1515,7 +1508,7 @@ CommandCost CmdBuildRailStation(DoCommandFlags flags, TileIndex tile_org, RailTy
TileIndexDiff tile_delta = TileOffsByAxis(axis); // offset to go to the next platform tile
TileIndexDiff track_delta = TileOffsByAxis(OtherAxis(axis)); // offset to go to the next track
RailStationTileLayout stl{statspec, numtracks, plat_len};
RailStationTileLayout<StationType::Rail> stl{statspec, numtracks, plat_len};
for (auto [i, it, tile_track] = std::make_tuple(0, stl.begin(), tile_org); i != numtracks; ++i, tile_track += track_delta) {
for (auto [j, tile] = std::make_tuple(0, tile_track); j != plat_len; ++j, tile += tile_delta, ++it) {
/* Don't check the layout if there's no bridge above anyway. */
+13 -1
View File
@@ -13,13 +13,21 @@
#include "newgrf_station.h"
#include "station_map.h"
template <StationType T>
class RailStationTileLayout {
private:
std::span<const StationGfx> layout{}; ///< Predefined tile layout.
uint platforms; ///< Number of platforms.
uint length; ///< Length of platforms.
public:
RailStationTileLayout(const StationSpec *spec, uint8_t platforms, uint8_t length);
RailStationTileLayout(const StationSpec *spec, uint8_t platforms, uint8_t length) : platforms(platforms), length(length)
{
if (spec == nullptr) return;
/* Look for a predefined layout for the required size. */
auto found = spec->layouts.find(GetStationLayoutKey(platforms, length));
if (found != std::end(spec->layouts)) this->layout = found->second;
}
class Iterator {
const RailStationTileLayout &stl; ///< Station tile layout being iterated.
@@ -36,6 +44,10 @@ public:
bool operator==(const Iterator &rhs) const { return this->position == rhs.position; }
bool operator==(const std::default_sentinel_t &) const { return this->position == this->stl.platforms * this->stl.length; }
/**
* Dereference operator.
* @return The StationGfx value associated with the index this iterator points to.
*/
StationGfx operator*() const;
Iterator &operator++()
+11 -1
View File
@@ -192,6 +192,16 @@ extern CommandCost IsBuoyBridgeAboveOk(TileIndex tile);
extern CommandCost RemoveRoadWaypointStop(TileIndex tile, DoCommandFlags flags, int replacement_spec_index);
/** @copydoc RailStationTileLayout::Iterator::operator* */
template <>
StationGfx RailStationTileLayout<StationType::RailWaypoint>::Iterator::operator*() const
{
/* Use predefined layout if it exists. Mask bit zero which will indicate axis. */
if (!stl.layout.empty()) return this->stl.layout[this->position] & ~1;
return 0;
}
/**
* Convert existing rail to waypoint. Eg build a waypoint station over
* piece of rail
@@ -239,7 +249,7 @@ CommandCost CmdBuildRailWaypoint(DoCommandFlags flags, TileIndex start_tile, Axi
StationID est = StationID::Invalid();
const StationSpec *spec = StationClass::Get(spec_class)->GetSpec(spec_index);
RailStationTileLayout stl{spec, count, 1};
RailStationTileLayout<StationType::RailWaypoint> stl{spec, count, 1};
/* Check whether the tiles we're building on are valid rail or not. */
TileIndexDiff offset = TileOffsByAxis(OtherAxis(axis));