summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/newgrf_station.cpp107
-rw-r--r--src/newgrf_station.h4
-rw-r--r--src/station_base.h16
-rw-r--r--src/station_cmd.cpp36
-rw-r--r--src/waypoint.cpp15
-rw-r--r--src/waypoint.h2
6 files changed, 126 insertions, 54 deletions
diff --git a/src/newgrf_station.cpp b/src/newgrf_station.cpp
index 0b195e0fd..f34012359 100644
--- a/src/newgrf_station.cpp
+++ b/src/newgrf_station.cpp
@@ -31,6 +31,48 @@ enum {
MAX_SPECLIST = 255,
};
+enum TriggerArea {
+ TA_TILE,
+ TA_PLATFORM,
+ TA_WHOLE,
+};
+
+struct ETileArea : TileArea {
+ ETileArea(const BaseStation *st, TileIndex tile, TriggerArea ta)
+ {
+ switch (ta) {
+ default: NOT_REACHED();
+
+ case TA_TILE:
+ this->tile = tile;
+ this->w = 1;
+ this->h = 1;
+ break;
+
+ case TA_PLATFORM: {
+ TileIndex start, end;
+ Axis axis = GetRailStationAxis(tile);
+ TileIndexDiff delta = TileOffsByDiagDir(AxisToDiagDir(axis));
+
+ for (end = tile; IsRailwayStationTile(end + delta) && IsCompatibleTrainStationTile(tile, end + delta); end += delta) { /* Nothing */ }
+ for (start = tile; IsRailwayStationTile(start - delta) && IsCompatibleTrainStationTile(tile, start - delta); start -= delta) { /* Nothing */ }
+
+ this->tile = start;
+ this->w = TileX(end) - TileX(start) + 1;
+ this->h = TileY(end) - TileY(start) + 1;
+ break;
+ }
+
+ case TA_WHOLE:
+ st->GetTileArea(this, Station::IsExpected(st) ? STATION_RAIL : STATION_WAYPOINT);
+ this->w++;
+ this->h++;
+ break;
+ }
+ }
+};
+
+
/**
* Reset station classes to their default state.
* This includes initialising the Default and Waypoint classes with an empty
@@ -734,7 +776,7 @@ uint16 GetStationCallback(CallbackID callback, uint32 param1, uint32 param2, con
* @param exec Whether to actually allocate the spec.
* @return Index within the Station's spec list, or -1 if the allocation failed.
*/
-int AllocateSpecToStation(const StationSpec *statspec, Station *st, bool exec)
+int AllocateSpecToStation(const StationSpec *statspec, BaseStation *st, bool exec)
{
uint i;
@@ -784,17 +826,22 @@ int AllocateSpecToStation(const StationSpec *statspec, Station *st, bool exec)
* @param specindex Index of the custom station within the Station's spec list.
* @return Indicates whether the StationSpec was deallocated.
*/
-void DeallocateSpecFromStation(Station *st, byte specindex)
+void DeallocateSpecFromStation(BaseStation *st, byte specindex)
{
/* specindex of 0 (default) is never freeable */
if (specindex == 0) return;
+ ETileArea area = ETileArea(st, INVALID_TILE, TA_WHOLE);
/* Check all tiles over the station to check if the specindex is still in use */
- BEGIN_TILE_LOOP(tile, st->trainst_w, st->trainst_h, st->train_tile) {
- if (IsRailwayStationTile(tile) && GetStationIndex(tile) == st->index && GetCustomStationSpecIndex(tile) == specindex) {
- return;
+ for (uint y = 0; y < area.h; y++) {
+ for (uint x = 0; x < area.w; x++) {
+ if (st->TileBelongsToRailStation(area.tile) && GetCustomStationSpecIndex(area.tile) == specindex) {
+ return;
+ }
+ area.tile += TileDiffXY(1, 0);
}
- } END_TILE_LOOP(tile, st->trainst_w, st->trainst_h, st->train_tile)
+ area.tile += TileDiffXY(-area.w, 1);
+ }
/* This specindex is no longer in use, so deallocate it */
st->speclist[specindex].spec = NULL;
@@ -1020,51 +1067,6 @@ static void ChangeStationAnimationFrame(const StationSpec *ss, const BaseStation
if (GB(callback, 8, 7) != 0) PlayTileSound(ss->grffile, GB(callback, 8, 7), tile);
}
-enum TriggerArea {
- TA_TILE,
- TA_PLATFORM,
- TA_WHOLE,
-};
-
-struct TileArea {
- TileIndex tile;
- uint8 w;
- uint8 h;
-
- TileArea(const Station *st, TileIndex tile, TriggerArea ta)
- {
- switch (ta) {
- default: NOT_REACHED();
-
- case TA_TILE:
- this->tile = tile;
- this->w = 1;
- this->h = 1;
- break;
-
- case TA_PLATFORM: {
- TileIndex start, end;
- Axis axis = GetRailStationAxis(tile);
- TileIndexDiff delta = TileOffsByDiagDir(AxisToDiagDir(axis));
-
- for (end = tile; IsRailwayStationTile(end + delta) && IsCompatibleTrainStationTile(tile, end + delta); end += delta) { /* Nothing */ }
- for (start = tile; IsRailwayStationTile(start - delta) && IsCompatibleTrainStationTile(tile, start - delta); start -= delta) { /* Nothing */ }
-
- this->tile = start;
- this->w = TileX(end) - TileX(start) + 1;
- this->h = TileY(end) - TileY(start) + 1;
- break;
- }
-
- case TA_WHOLE:
- this->tile = st->train_tile;
- this->w = st->trainst_w + 1;
- this->h = st->trainst_h + 1;
- break;
- }
- }
-};
-
void StationAnimationTrigger(const BaseStation *st, TileIndex tile, StatAnimTrigger trigger, CargoID cargo_type)
{
/* List of coverage areas for each animation trigger */
@@ -1080,8 +1082,9 @@ void StationAnimationTrigger(const BaseStation *st, TileIndex tile, StatAnimTrig
if (!HasBit(st->cached_anim_triggers, trigger)) return;
uint16 random_bits = Random();
- TileArea area = TileArea(Station::From(st), tile, tas[trigger]);
+ ETileArea area = ETileArea(st, tile, tas[trigger]);
+ /* Check all tiles over the station to check if the specindex is still in use */
for (uint y = 0; y < area.h; y++) {
for (uint x = 0; x < area.w; x++) {
if (st->TileBelongsToRailStation(area.tile)) {
diff --git a/src/newgrf_station.h b/src/newgrf_station.h
index 3031a4ca9..bc84b4983 100644
--- a/src/newgrf_station.h
+++ b/src/newgrf_station.h
@@ -136,10 +136,10 @@ SpriteID GetCustomStationGroundRelocation(const StationSpec *statspec, const Bas
uint16 GetStationCallback(CallbackID callback, uint32 param1, uint32 param2, const StationSpec *statspec, const BaseStation *st, TileIndex tile);
/* Allocate a StationSpec to a Station. This is called once per build operation. */
-int AllocateSpecToStation(const StationSpec *statspec, Station *st, bool exec);
+int AllocateSpecToStation(const StationSpec *statspec, BaseStation *st, bool exec);
/* Deallocate a StationSpec from a Station. Called when removing a single station tile. */
-void DeallocateSpecFromStation(Station *st, byte specindex);
+void DeallocateSpecFromStation(BaseStation *st, byte specindex);
/* Draw representation of a station tile for GUI purposes. */
bool DrawStationTile(int x, int y, RailType railtype, Axis axis, StationClassID sclass, uint station);
diff --git a/src/station_base.h b/src/station_base.h
index b68858a59..18f7c9ca5 100644
--- a/src/station_base.h
+++ b/src/station_base.h
@@ -77,6 +77,13 @@ struct StationRect : public Rect {
StationRect& operator = (Rect src);
};
+/** Represents the covered area */
+struct TileArea {
+ TileIndex tile; ///< The base tile of the area
+ uint8 w; ///< The width of the area
+ uint8 h; ///< The height of the area
+};
+
/** Base class for all station-ish types */
struct BaseStation {
TileIndex xy; ///< Base tile of the station
@@ -126,6 +133,13 @@ struct BaseStation {
virtual void UpdateVirtCoord() = 0;
/**
+ * Get the tile area for a given station type.
+ * @param ta tile area to fill.
+ * @param type the type of the area
+ */
+ virtual void GetTileArea(TileArea *ta, StationType type) const = 0;
+
+ /**
* Get the base station belonging to a specific tile.
* @param tile The tile to get the base station from.
* @return the station associated with that tile.
@@ -258,6 +272,8 @@ public:
/* virtual */ uint32 GetNewGRFVariable(const ResolverObject *object, byte variable, byte parameter, bool *available) const;
+ /* virtual */ void GetTileArea(TileArea *ta, StationType type) const;
+
/**
* Determines whether a station is a buoy only.
* @todo Ditch this encoding of buoys
diff --git a/src/station_cmd.cpp b/src/station_cmd.cpp
index 877e705b6..f21a2e1e1 100644
--- a/src/station_cmd.cpp
+++ b/src/station_cmd.cpp
@@ -368,6 +368,42 @@ static Station *GetClosestDeletedStation(TileIndex tile)
return best_station;
}
+
+void Station::GetTileArea(TileArea *ta, StationType type) const
+{
+ switch (type) {
+ case STATION_RAIL:
+ ta->tile = this->train_tile;
+ ta->w = this->trainst_w;
+ ta->h = this->trainst_h;
+ return;
+
+ case STATION_AIRPORT:
+ ta->tile = this->airport_tile;
+ ta->w = this->Airport()->size_x;
+ ta->h = this->Airport()->size_y;
+
+ case STATION_TRUCK:
+ ta->tile = this->truck_stops != NULL ? this->truck_stops->xy : INVALID_TILE;
+ break;
+
+ case STATION_BUS:
+ ta->tile = this->bus_stops != NULL ? this->bus_stops->xy : INVALID_TILE;
+ break;
+
+ case STATION_DOCK:
+ case STATION_OILRIG:
+ case STATION_BUOY:
+ ta->tile = this->dock_tile;
+ break;
+
+ default: NOT_REACHED();
+ }
+
+ ta->w = 1;
+ ta->h = 1;
+}
+
/**
* Update the virtual coords needed to draw the station sign.
*/
diff --git a/src/waypoint.cpp b/src/waypoint.cpp
index 9e8e7da13..70ec5c3f5 100644
--- a/src/waypoint.cpp
+++ b/src/waypoint.cpp
@@ -44,6 +44,21 @@ void DrawWaypointSprite(int x, int y, int stat_id, RailType railtype)
}
}
+void Waypoint::GetTileArea(TileArea *ta, StationType type) const
+{
+ switch (type) {
+ case STATION_BUOY:
+ case STATION_WAYPOINT:
+ break;
+
+ default: NOT_REACHED();
+ }
+
+ ta->tile = this->xy;
+ ta->w = 1;
+ ta->h = 1;
+}
+
Waypoint::~Waypoint()
{
if (CleaningPool()) return;
diff --git a/src/waypoint.h b/src/waypoint.h
index c7d151350..f6d5a317d 100644
--- a/src/waypoint.h
+++ b/src/waypoint.h
@@ -32,6 +32,8 @@ struct Waypoint : WaypointPool::PoolItem<&_waypoint_pool>, SpecializedStation<Wa
/* virtual */ uint32 GetNewGRFVariable(const struct ResolverObject *object, byte variable, byte parameter, bool *available) const;
+ /* virtual */ void GetTileArea(TileArea *ta, StationType type) const;
+
void AssignStationSpec(uint index);
/**