|
@@ -61,12 +61,14 @@
|
|
|
#include "rail_cmd.h"
|
|
|
|
|
|
#include "table/strings.h"
|
|
|
|
|
|
#include "safeguards.h"
|
|
|
|
|
|
#include "company_func.h"
|
|
|
|
|
|
/**
|
|
|
* Static instance of FlowStat::SharesMap.
|
|
|
* Note: This instance is created on task start.
|
|
|
* Lazy creation on first usage results in a data race between the CDist threads.
|
|
|
*/
|
|
|
/* static */ const FlowStat::SharesMap FlowStat::empty_sharesmap;
|
|
@@ -235,29 +237,15 @@ static bool FindNearIndustryName(TileInd
|
|
|
/* In all cases if an industry that provides a name is found two of
|
|
|
* the standard names will be disabled. */
|
|
|
sni->free_names &= ~(1 << M(STR_SV_STNAME_OILFIELD) | 1 << M(STR_SV_STNAME_MINES));
|
|
|
return !sni->indtypes[indtype];
|
|
|
}
|
|
|
|
|
|
static StringID GenerateStationName(Station *st, TileIndex tile, StationNaming name_class)
|
|
|
/** Fetch the available station names. Patchpack moves this code from GenerateStationName. Should be easy to see what was moved if you do a diff :) */
|
|
|
static void FetchAvailableStationNames(uint32& free_names, bool* indtypes, Station* st, const Town* t)
|
|
|
{
|
|
|
static const uint32 _gen_station_name_bits[] = {
|
|
|
0, // STATIONNAMING_RAIL
|
|
|
0, // STATIONNAMING_ROAD
|
|
|
1U << M(STR_SV_STNAME_AIRPORT), // STATIONNAMING_AIRPORT
|
|
|
1U << M(STR_SV_STNAME_OILFIELD), // STATIONNAMING_OILRIG
|
|
|
1U << M(STR_SV_STNAME_DOCKS), // STATIONNAMING_DOCK
|
|
|
1U << M(STR_SV_STNAME_HELIPORT), // STATIONNAMING_HELIPORT
|
|
|
};
|
|
|
|
|
|
const Town *t = st->town;
|
|
|
uint32 free_names = UINT32_MAX;
|
|
|
|
|
|
bool indtypes[NUM_INDUSTRYTYPES];
|
|
|
memset(indtypes, 0, sizeof(indtypes));
|
|
|
|
|
|
for (const Station *s : Station::Iterate()) {
|
|
|
if (s != st && s->town == t) {
|
|
|
if (s->indtype != IT_INVALID) {
|
|
|
indtypes[s->indtype] = true;
|
|
|
StringID name = GetIndustrySpec(s->indtype)->station_name;
|
|
|
if (name != STR_UNDEFINED) {
|
|
@@ -275,21 +263,71 @@ static StringID GenerateStationName(Stat
|
|
|
str = M(STR_SV_STNAME_WOODS);
|
|
|
}
|
|
|
ClrBit(free_names, str);
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/** Callback proc for CircularTileSearch */
|
|
|
static bool FindNearPatchpackIndustryName(TileIndex tile, void *user_data)
|
|
|
{
|
|
|
/* Is this an industry tile? If not, skip it */
|
|
|
if (!IsTileType(tile, MP_INDUSTRY)) return false;
|
|
|
|
|
|
uint32 free_names = UINT32_MAX;
|
|
|
bool indtypes[NUM_INDUSTRYTYPES];
|
|
|
memset(indtypes, 0, sizeof(indtypes));
|
|
|
FetchAvailableStationNames(free_names, indtypes, (Station*)user_data, Industry::GetByTile(tile)->town);
|
|
|
|
|
|
IndustryType indtype = GetIndustryType(tile);
|
|
|
|
|
|
return !indtypes[indtype];
|
|
|
}
|
|
|
|
|
|
/** Generates station names */
|
|
|
static StringID GenerateStationName(Station *st, TileIndex tile, StationNaming name_class)
|
|
|
{
|
|
|
if (_settings_game.construction.name_stations_based_on_industries == 2)
|
|
|
{
|
|
|
/** I love having this as an in-game patch setting. DEM SETTINGS */
|
|
|
TileIndex indtile = tile;
|
|
|
if (CircularTileSearch(&indtile, 7, FindNearPatchpackIndustryName, (void*)st)) {
|
|
|
IndustryType indtype = GetIndustryType(indtile);
|
|
|
const IndustrySpec *indsp = GetIndustrySpec(indtype);
|
|
|
st->indtype = indtype;
|
|
|
st->town = Industry::GetByTile(indtile)->town;
|
|
|
return STR_SV_STNAME_FALLBACK;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
static const uint32 _gen_station_name_bits[] = {
|
|
|
0, // STATIONNAMING_RAIL
|
|
|
0, // STATIONNAMING_ROAD
|
|
|
1U << M(STR_SV_STNAME_AIRPORT), // STATIONNAMING_AIRPORT
|
|
|
1U << M(STR_SV_STNAME_OILFIELD), // STATIONNAMING_OILRIG
|
|
|
1U << M(STR_SV_STNAME_DOCKS), // STATIONNAMING_DOCK
|
|
|
1U << M(STR_SV_STNAME_HELIPORT), // STATIONNAMING_HELIPORT
|
|
|
};
|
|
|
|
|
|
const Town *t = st->town;
|
|
|
|
|
|
/* Fetch a list of available station names so we know which ones have already been used and are unavailable (including industry newGRF names) */
|
|
|
uint32 free_names = UINT32_MAX;
|
|
|
bool indtypes[NUM_INDUSTRYTYPES];
|
|
|
memset(indtypes, 0, sizeof(indtypes));
|
|
|
FetchAvailableStationNames(free_names, indtypes, st, t);
|
|
|
|
|
|
TileIndex indtile = tile;
|
|
|
StationNameInformation sni = { free_names, indtypes };
|
|
|
if (CircularTileSearch(&indtile, 7, FindNearIndustryName, &sni)) {
|
|
|
/* An industry has been found nearby */
|
|
|
IndustryType indtype = GetIndustryType(indtile);
|
|
|
const IndustrySpec *indsp = GetIndustrySpec(indtype);
|
|
|
/* STR_NULL means it only disables oil rig/mines */
|
|
|
if (indsp->station_name != STR_NULL) {
|
|
|
if (indsp->station_name != STR_NULL && (_settings_game.construction.name_stations_based_on_industries == 1)) {
|
|
|
st->indtype = indtype;
|
|
|
return STR_SV_STNAME_FALLBACK;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/* Oil rigs/mines name could be marked not free by looking for a near by industry. */
|
|
@@ -840,13 +878,13 @@ CommandCost CheckBuildableTile(TileIndex
|
|
|
* @param tile_iter Airport tile iterator.
|
|
|
* @param flags Operation to perform.
|
|
|
* @return The cost in case of success, or an error code if it failed.
|
|
|
*/
|
|
|
static CommandCost CheckFlatLandAirport(AirportTileTableIterator tile_iter, DoCommandFlag flags)
|
|
|
{
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_AIRCRAFT_CON);
|
|
|
int allowed_z = -1;
|
|
|
|
|
|
for (; tile_iter != INVALID_TILE; ++tile_iter) {
|
|
|
CommandCost ret = CheckBuildableTile(tile_iter, 0, allowed_z, true);
|
|
|
if (ret.Failed()) return ret;
|
|
|
cost.AddCost(ret);
|
|
@@ -872,13 +910,13 @@ static CommandCost CheckFlatLandAirport(
|
|
|
* @param plat_len Platform length.
|
|
|
* @param numtracks Number of platforms.
|
|
|
* @return The cost in case of success, or an error code if it failed.
|
|
|
*/
|
|
|
static CommandCost CheckFlatLandRailStation(TileArea tile_area, DoCommandFlag flags, Axis axis, StationID *station, RailType rt, std::vector<Train *> &affected_vehicles, StationClassID spec_class, byte spec_index, byte plat_len, byte numtracks)
|
|
|
{
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_TRAIN_CON);
|
|
|
int allowed_z = -1;
|
|
|
uint invalid_dirs = 5 << axis;
|
|
|
|
|
|
const StationSpec *statspec = StationClass::Get(spec_class)->GetSpec(spec_index);
|
|
|
bool slope_cb = statspec != nullptr && HasBit(statspec->callback_mask, CBM_STATION_SLOPE_CHECK);
|
|
|
|
|
@@ -958,13 +996,13 @@ static CommandCost CheckFlatLandRailStat
|
|
|
* @param station StationID to be queried and returned if available.
|
|
|
* @param rt Road type to build.
|
|
|
* @return The cost in case of success, or an error code if it failed.
|
|
|
*/
|
|
|
static CommandCost CheckFlatLandRoadStop(TileArea tile_area, DoCommandFlag flags, uint invalid_dirs, bool is_drive_through, bool is_truck_stop, Axis axis, StationID *station, RoadType rt)
|
|
|
{
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_ROAD_CON);
|
|
|
int allowed_z = -1;
|
|
|
|
|
|
for (TileIndex cur_tile : tile_area) {
|
|
|
CommandCost ret = CheckBuildableTile(cur_tile, invalid_dirs, allowed_z, !is_drive_through);
|
|
|
if (ret.Failed()) return ret;
|
|
|
cost.AddCost(ret);
|
|
@@ -1549,13 +1587,13 @@ static void MakeShipStationAreaSmaller(S
|
|
|
*/
|
|
|
template <class T>
|
|
|
CommandCost RemoveFromRailBaseStation(TileArea ta, std::vector<T *> &affected_stations, DoCommandFlag flags, Money removal_cost, bool keep_rail)
|
|
|
{
|
|
|
/* Count of the number of tiles removed */
|
|
|
int quantity = 0;
|
|
|
CommandCost total_cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost total_cost(EXPENSES_T_TRAIN_CON);
|
|
|
/* Accumulator for the errors seen during clearing. If no errors happen,
|
|
|
* and the quantity is 0 there is no station. Otherwise it will be one
|
|
|
* of the other error that got accumulated. */
|
|
|
CommandCost error;
|
|
|
|
|
|
/* Do the action for every tile into the area */
|
|
@@ -1718,13 +1756,13 @@ CommandCost RemoveRailStation(T *st, DoC
|
|
|
|
|
|
/* determine width and height of platforms */
|
|
|
TileArea ta = st->train_station;
|
|
|
|
|
|
assert(ta.w != 0 && ta.h != 0);
|
|
|
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_TRAIN_CON);
|
|
|
/* clear all areas of the station */
|
|
|
for (TileIndex tile : ta) {
|
|
|
/* only remove tiles that are actually train station tiles */
|
|
|
if (st->TileBelongsToRailStation(tile)) {
|
|
|
std::vector<T*> affected_stations; // dummy
|
|
|
CommandCost ret = RemoveFromRailBaseStation(TileArea(tile, 1, 1), affected_stations, flags, removal_cost, false);
|
|
@@ -1850,13 +1888,13 @@ CommandCost CmdBuildRoadStop(DoCommandFl
|
|
|
CommandCost ret = CheckIfAuthorityAllowsNewStation(tile, flags);
|
|
|
if (ret.Failed()) return ret;
|
|
|
|
|
|
bool is_truck_stop = stop_type != ROADSTOP_BUS;
|
|
|
|
|
|
/* Total road stop cost. */
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION, roadstop_area.w * roadstop_area.h * _price[is_truck_stop ? PR_BUILD_STATION_TRUCK : PR_BUILD_STATION_BUS]);
|
|
|
CommandCost cost(EXPENSES_T_ROAD_CON, roadstop_area.w * roadstop_area.h * _price[is_truck_stop ? PR_BUILD_STATION_TRUCK : PR_BUILD_STATION_BUS]);
|
|
|
StationID est = INVALID_STATION;
|
|
|
ret = CheckFlatLandRoadStop(roadstop_area, flags, is_drive_through ? 5 << axis : 1 << ddir, is_drive_through, is_truck_stop, axis, &est, rt);
|
|
|
if (ret.Failed()) return ret;
|
|
|
cost.AddCost(ret);
|
|
|
|
|
|
Station *st = nullptr;
|
|
@@ -2042,13 +2080,13 @@ static CommandCost RemoveRoadStop(TileIn
|
|
|
} else {
|
|
|
st->bus_station.Clear();
|
|
|
for (const RoadStop *rs = st->bus_stops; rs != nullptr; rs = rs->next) st->bus_station.Add(rs->xy);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
return CommandCost(EXPENSES_CONSTRUCTION, _price[is_truck ? PR_CLEAR_STATION_TRUCK : PR_CLEAR_STATION_BUS]);
|
|
|
return CommandCost(EXPENSES_T_ROAD_CON, _price[is_truck ? PR_CLEAR_STATION_TRUCK : PR_CLEAR_STATION_BUS]);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Remove bus or truck stops.
|
|
|
* @param flags Operation to perform.
|
|
|
* @param tile Northernmost tile of the removal area.
|
|
@@ -2067,13 +2105,13 @@ CommandCost CmdRemoveRoadStop(DoCommandF
|
|
|
if (!IsValidTile(tile) || TileAddWrap(tile, width - 1, height - 1) == INVALID_TILE) return CMD_ERROR;
|
|
|
/* Bankrupting company is not supposed to remove roads, there may be road vehicles. */
|
|
|
if (remove_road && (flags & DC_BANKRUPT)) return CMD_ERROR;
|
|
|
|
|
|
TileArea roadstop_area(tile, width, height);
|
|
|
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_ROAD_CON);
|
|
|
CommandCost last_error(STR_ERROR_THERE_IS_NO_STATION);
|
|
|
bool had_success = false;
|
|
|
|
|
|
for (TileIndex cur_tile : roadstop_area) {
|
|
|
/* Make sure the specified tile is a road stop of the correct type */
|
|
|
if (!IsTileType(cur_tile, MP_STATION) || !IsRoadStop(cur_tile) || GetRoadStopType(cur_tile) != stop_type) continue;
|
|
@@ -2347,13 +2385,13 @@ static CommandCost RemoveAirport(TileInd
|
|
|
CommandCost ret = CheckOwnership(st->owner);
|
|
|
if (ret.Failed()) return ret;
|
|
|
}
|
|
|
|
|
|
tile = st->airport.tile;
|
|
|
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION);
|
|
|
CommandCost cost(EXPENSES_T_AIRCRAFT_CON);
|
|
|
|
|
|
for (const Aircraft *a : Aircraft::Iterate()) {
|
|
|
if (!a->IsNormalAircraft()) continue;
|
|
|
if (a->targetairport == st->index && a->state != FLYING) {
|
|
|
return_cmd_error(STR_ERROR_AIRCRAFT_IN_THE_WAY);
|
|
|
}
|
|
@@ -2493,13 +2531,13 @@ CommandCost CmdBuildDock(DoCommandFlag f
|
|
|
|
|
|
CommandCost ret = CheckIfAuthorityAllowsNewStation(tile, flags);
|
|
|
if (ret.Failed()) return ret;
|
|
|
|
|
|
if (IsBridgeAbove(tile)) return_cmd_error(STR_ERROR_MUST_DEMOLISH_BRIDGE_FIRST);
|
|
|
|
|
|
CommandCost cost(EXPENSES_CONSTRUCTION, _price[PR_BUILD_STATION_DOCK]);
|
|
|
CommandCost cost(EXPENSES_T_SHIP_CON, _price[PR_BUILD_STATION_DOCK]);
|
|
|
ret = Command<CMD_LANDSCAPE_CLEAR>::Do(flags, tile);
|
|
|
if (ret.Failed()) return ret;
|
|
|
cost.AddCost(ret);
|
|
|
|
|
|
TileIndex tile_cur = tile + TileOffsByDiagDir(direction);
|
|
|
|
|
@@ -2693,13 +2731,13 @@ static CommandCost RemoveDock(TileIndex
|
|
|
if (s->current_order.IsType(OT_GOTO_STATION) && !(st->facilities & FACIL_DOCK)) {
|
|
|
s->SetDestTile(s->GetOrderStationLocation(st->index));
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
return CommandCost(EXPENSES_CONSTRUCTION, _price[PR_CLEAR_STATION_DOCK]);
|
|
|
return CommandCost(EXPENSES_T_SHIP_CON, _price[PR_CLEAR_STATION_DOCK]);
|
|
|
}
|
|
|
|
|
|
#include "table/station_land.h"
|
|
|
|
|
|
const DrawTileSprites *GetStationTileLayout(StationType st, byte gfx)
|
|
|
{
|
|
@@ -2991,13 +3029,12 @@ draw_default_foundation:
|
|
|
DrawGroundSprite(GetRailStationAxis(ti->tile) == AXIS_X ? rti->base_sprites.single_x : rti->base_sprites.single_y, PALETTE_CRASH);
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
if (HasStationRail(ti->tile) && HasRailCatenaryDrawn(GetRailType(ti->tile))) DrawRailCatenary(ti);
|
|
|
|
|
|
if (IsRoadStop(ti->tile)) {
|
|
|
RoadType road_rt = GetRoadTypeRoad(ti->tile);
|
|
|
RoadType tram_rt = GetRoadTypeTram(ti->tile);
|
|
|
const RoadTypeInfo* road_rti = road_rt == INVALID_ROADTYPE ? nullptr : GetRoadTypeInfo(road_rt);
|
|
|
const RoadTypeInfo* tram_rti = tram_rt == INVALID_ROADTYPE ? nullptr : GetRoadTypeInfo(tram_rt);
|
|
|
|
|
@@ -3562,12 +3599,70 @@ static void UpdateStationRating(Station
|
|
|
ge->max_waiting_cargo = waiting_avg;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
// station dilapidation
|
|
|
{
|
|
|
if (_settings_game.economy.dilapidation_max_amount > 0) {
|
|
|
bool dilapidation_calc = false;
|
|
|
uint16 dilapidation_pop = 0;
|
|
|
uint pop_count = st->goods[CT_PASSENGERS].cargo.AvailableCount();
|
|
|
if (Company::IsValidID(st->owner)) {
|
|
|
if ((st->facilities & FACIL_TRAIN) != 0) {
|
|
|
dilapidation_calc = true;
|
|
|
if (_settings_game.economy.dilapidation_pop_rail > dilapidation_pop) {
|
|
|
dilapidation_pop = _settings_game.economy.dilapidation_pop_rail;
|
|
|
}
|
|
|
}
|
|
|
if (((st->facilities & FACIL_BUS_STOP) != 0) || ((st->facilities & FACIL_TRUCK_STOP) != 0)) {
|
|
|
dilapidation_calc = true;
|
|
|
if (_settings_game.economy.dilapidation_pop_road > dilapidation_pop) {
|
|
|
dilapidation_pop = _settings_game.economy.dilapidation_pop_road;
|
|
|
}
|
|
|
}
|
|
|
if ((st->facilities & FACIL_DOCK) != 0) {
|
|
|
dilapidation_calc = true;
|
|
|
if (_settings_game.economy.dilapidation_pop_water > dilapidation_pop) {
|
|
|
dilapidation_pop = _settings_game.economy.dilapidation_pop_water;
|
|
|
}
|
|
|
}
|
|
|
if ((st->facilities & FACIL_AIRPORT) != 0) {
|
|
|
dilapidation_calc = true;
|
|
|
if (_settings_game.economy.dilapidation_pop_air > dilapidation_pop) {
|
|
|
dilapidation_pop = _settings_game.economy.dilapidation_pop_air;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
if (dilapidation_calc && pop_count > (uint)dilapidation_pop) {
|
|
|
// increase the dilapidation, preventing overflow
|
|
|
uint16 top_boundary = 65535 - _settings_game.economy.dilapidation_increase;
|
|
|
if (st->dilapidation >= top_boundary) {
|
|
|
st->dilapidation = 65535;
|
|
|
}
|
|
|
else {
|
|
|
st->dilapidation += _settings_game.economy.dilapidation_increase;
|
|
|
}
|
|
|
}
|
|
|
else
|
|
|
{
|
|
|
// decrease the dilapidation, preventing underflow
|
|
|
if (st->dilapidation <= _settings_game.economy.dilapidation_decrease) {
|
|
|
st->dilapidation = 0;
|
|
|
}
|
|
|
else {
|
|
|
st->dilapidation -= _settings_game.economy.dilapidation_decrease;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
if (st->dilapidation > _settings_game.economy.dilapidation_max_amount) {
|
|
|
st->dilapidation = _settings_game.economy.dilapidation_max_amount;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
StationID index = st->index;
|
|
|
if (waiting_changed) {
|
|
|
SetWindowDirty(WC_STATION_VIEW, index); // update whole window
|
|
|
} else {
|
|
|
SetWindowWidgetDirty(WC_STATION_VIEW, index, WID_SV_ACCEPT_RATING_LIST); // update only ratings list
|
|
|
}
|
|
@@ -3800,21 +3895,56 @@ void OnTick_Station()
|
|
|
TriggerStationAnimation(st, st->xy, SAT_250_TICKS);
|
|
|
if (Station::IsExpected(st)) AirportAnimationTrigger(Station::From(st), AAT_STATION_250_TICKS);
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/** Charges player for dilapidation at station */
|
|
|
void ChargePlayerForDilapidation(Station *st)
|
|
|
{
|
|
|
if (st->dilapidation > 0 && Company::IsValidID(st->owner)) {
|
|
|
uint32 dilapidation_fine = 0;
|
|
|
if ((st->facilities & FACIL_TRAIN) != 0) {
|
|
|
if (_settings_game.economy.dilapidation_fine_rail > dilapidation_fine) {
|
|
|
dilapidation_fine = _settings_game.economy.dilapidation_fine_rail;
|
|
|
}
|
|
|
}
|
|
|
if (((st->facilities & FACIL_BUS_STOP) != 0) || ((st->facilities & FACIL_TRUCK_STOP) != 0)) {
|
|
|
if (_settings_game.economy.dilapidation_fine_road > dilapidation_fine) {
|
|
|
dilapidation_fine = _settings_game.economy.dilapidation_fine_road;
|
|
|
}
|
|
|
}
|
|
|
if ((st->facilities & FACIL_DOCK) != 0) {
|
|
|
if (_settings_game.economy.dilapidation_fine_water > dilapidation_fine) {
|
|
|
dilapidation_fine = _settings_game.economy.dilapidation_fine_water;
|
|
|
}
|
|
|
}
|
|
|
if ((st->facilities & FACIL_AIRPORT) != 0) {
|
|
|
if (_settings_game.economy.dilapidation_fine_air > dilapidation_fine) {
|
|
|
dilapidation_fine = _settings_game.economy.dilapidation_fine_air;
|
|
|
}
|
|
|
}
|
|
|
Money actual_fine = dilapidation_fine;
|
|
|
actual_fine *= st->dilapidation;
|
|
|
actual_fine *= (_economy.inflation_prices >> 16);
|
|
|
if (actual_fine > 0) {
|
|
|
SubtractMoneyFromCompanyFract(st->owner, CommandCost(EXPENSES_T_DILAPIDATION, actual_fine << 8));
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/** Monthly loop for stations. */
|
|
|
void StationMonthlyLoop()
|
|
|
{
|
|
|
for (Station *st : Station::Iterate()) {
|
|
|
for (CargoID i = 0; i < NUM_CARGO; i++) {
|
|
|
GoodsEntry *ge = &st->goods[i];
|
|
|
SB(ge->status, GoodsEntry::GES_LAST_MONTH, 1, GB(ge->status, GoodsEntry::GES_CURRENT_MONTH, 1));
|
|
|
ClrBit(ge->status, GoodsEntry::GES_CURRENT_MONTH);
|
|
|
}
|
|
|
ChargePlayerForDilapidation(st);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
|
|
|
void ModifyStationRatingAround(TileIndex tile, Owner owner, int amount, uint radius)
|
|
|
{
|
|
@@ -4299,26 +4429,26 @@ static CommandCost TerraformTile_Station
|
|
|
switch (GetStationType(tile)) {
|
|
|
case STATION_WAYPOINT:
|
|
|
case STATION_RAIL: {
|
|
|
DiagDirection direction = AxisToDiagDir(GetRailStationAxis(tile));
|
|
|
if (!AutoslopeCheckForEntranceEdge(tile, z_new, tileh_new, direction)) break;
|
|
|
if (!AutoslopeCheckForEntranceEdge(tile, z_new, tileh_new, ReverseDiagDir(direction))) break;
|
|
|
return CommandCost(EXPENSES_CONSTRUCTION, _price[PR_BUILD_FOUNDATION]);
|
|
|
return CommandCost(EXPENSES_T_TRAIN_CON, _price[PR_BUILD_FOUNDATION]);
|
|
|
}
|
|
|
|
|
|
case STATION_AIRPORT:
|
|
|
return CommandCost(EXPENSES_CONSTRUCTION, _price[PR_BUILD_FOUNDATION]);
|
|
|
return CommandCost(EXPENSES_T_AIRCRAFT_CON, _price[PR_BUILD_FOUNDATION]);
|
|
|
|
|
|
case STATION_TRUCK:
|
|
|
case STATION_BUS: {
|
|
|
DiagDirection direction = GetRoadStopDir(tile);
|
|
|
if (!AutoslopeCheckForEntranceEdge(tile, z_new, tileh_new, direction)) break;
|
|
|
if (IsDriveThroughStopTile(tile)) {
|
|
|
if (!AutoslopeCheckForEntranceEdge(tile, z_new, tileh_new, ReverseDiagDir(direction))) break;
|
|
|
}
|
|
|
return CommandCost(EXPENSES_CONSTRUCTION, _price[PR_BUILD_FOUNDATION]);
|
|
|
return CommandCost(EXPENSES_T_ROAD_CON, _price[PR_BUILD_FOUNDATION]);
|
|
|
}
|
|
|
|
|
|
default: break;
|
|
|
}
|
|
|
}
|
|
|
}
|