From ea072322fa099509b5e8aeb1d9c8be9f857dd972 Mon Sep 17 00:00:00 2001 From: rubidium Date: Sat, 24 Nov 2007 08:45:04 +0000 Subject: (svn r11504) -Fix [FS#1467]: removing docks/ship depots could result in non-canal water where canals should have been build. --- src/dock_gui.cpp | 1 + src/functions.h | 4 ---- src/industry_cmd.cpp | 1 + src/rail_cmd.cpp | 1 + src/station_cmd.cpp | 13 +++---------- src/water.h | 13 +++++++++++++ src/water_cmd.cpp | 40 ++++++++++++++++++++++++++++++++++++++-- 7 files changed, 57 insertions(+), 16 deletions(-) create mode 100644 src/water.h diff --git a/src/dock_gui.cpp b/src/dock_gui.cpp index 5fbdc47b0..64822ea3f 100644 --- a/src/dock_gui.cpp +++ b/src/dock_gui.cpp @@ -16,6 +16,7 @@ #include "sound.h" #include "command.h" #include "variables.h" +#include "water.h" static void ShowBuildDockStationPicker(); static void ShowBuildDocksDepotPicker(); diff --git a/src/functions.h b/src/functions.h index 191ad7708..461f89335 100644 --- a/src/functions.h +++ b/src/functions.h @@ -17,10 +17,6 @@ void DrawClearLandTile(const TileInfo *ti, byte set); void DrawClearLandFence(const TileInfo *ti); void TileLoopClearHelper(TileIndex tile); -/* water_land.cpp */ -void DrawShipDepotSprite(int x, int y, int image); -void TileLoop_Water(TileIndex tile); - /* players.cpp */ bool CheckPlayerHasMoney(CommandCost cost); void SubtractMoneyFromPlayer(CommandCost cost); diff --git a/src/industry_cmd.cpp b/src/industry_cmd.cpp index 99f52c13d..ec8f6c104 100644 --- a/src/industry_cmd.cpp +++ b/src/industry_cmd.cpp @@ -40,6 +40,7 @@ #include "misc/autoptr.hpp" #include "autoslope.h" #include "transparency.h" +#include "water.h" void ShowIndustryViewWindow(int industry); void BuildOilRig(TileIndex tile); diff --git a/src/rail_cmd.cpp b/src/rail_cmd.cpp index 30f67e63e..953c594cc 100644 --- a/src/rail_cmd.cpp +++ b/src/rail_cmd.cpp @@ -41,6 +41,7 @@ #include "misc/autoptr.hpp" #include "autoslope.h" #include "transparency.h" +#include "water.h" const byte _track_sloped_sprites[14] = { 14, 15, 22, 13, diff --git a/src/station_cmd.cpp b/src/station_cmd.cpp index 6f3eb7e11..c969ef459 100644 --- a/src/station_cmd.cpp +++ b/src/station_cmd.cpp @@ -44,6 +44,7 @@ #include "strings.h" #include "autoslope.h" #include "transparency.h" +#include "water.h" DEFINE_OLD_POOL_GENERIC(Station, Station) DEFINE_OLD_POOL_GENERIC(RoadStop, RoadStop) @@ -1899,12 +1900,7 @@ static CommandCost RemoveBuoy(Station *st, uint32 flags) /* We have to set the water tile's state to the same state as before the * buoy was placed. Otherwise one could plant a buoy on a canal edge, * remove it and flood the land (if the canal edge is at level 0) */ - Owner o = GetTileOwner(tile); - if (o == OWNER_WATER) { - MakeWater(tile); - } else { - MakeCanal(tile, o); - } + MakeWaterOrCanalDependingOnSurroundings(tile, GetTileOwner(tile)); MarkTileDirtyByTile(tile); UpdateStationVirtCoordDirty(st); @@ -2040,7 +2036,7 @@ static CommandCost RemoveDock(Station *st, uint32 flags) if (flags & DC_EXEC) { DoClearSquare(tile1); - MakeWater(tile2); + MakeWaterOrCanalDependingOnSurroundings(tile2, st->owner); st->rect.AfterRemoveTile(st, tile1); st->rect.AfterRemoveTile(st, tile2); @@ -2064,9 +2060,6 @@ const DrawTileSprites *GetStationTileLayout(StationType st, byte gfx) return &_station_display_datas[st][gfx]; } -/* For drawing canal edges on buoys */ -extern void DrawCanalWater(TileIndex tile); - static void DrawTile_Station(TileInfo *ti) { const DrawTileSprites *t = NULL; diff --git a/src/water.h b/src/water.h new file mode 100644 index 000000000..e279119f1 --- /dev/null +++ b/src/water.h @@ -0,0 +1,13 @@ +/* $Id$ */ + +/** @file water.h Functions related to water (management) */ + +#ifndef WATER_H +#define WATER_H + +void TileLoop_Water(TileIndex tile); +void DrawShipDepotSprite(int x, int y, int image); +void DrawCanalWater(TileIndex tile); +void MakeWaterOrCanalDependingOnSurroundings(TileIndex t, Owner o); + +#endif /* WATER_H */ diff --git a/src/water_cmd.cpp b/src/water_cmd.cpp index f91682449..92b33a837 100644 --- a/src/water_cmd.cpp +++ b/src/water_cmd.cpp @@ -55,6 +55,42 @@ static const SpriteID _water_shore_sprites[] = { static Vehicle *FindFloodableVehicleOnTile(TileIndex tile); static void FloodVehicle(Vehicle *v); +/** + * Makes a tile canal or water depending on the surroundings. + * This as for example docks and shipdepots do not store + * whether the tile used to be canal or 'normal' water. + * @param t the tile to change. + * @param o the owner of the new tile. + */ +void MakeWaterOrCanalDependingOnSurroundings(TileIndex t, Owner o) +{ + assert(GetTileSlope(t, NULL) == SLOPE_FLAT); + + /* Non-sealevel -> canal */ + if (TileHeight(t) != 0) { + MakeCanal(t, o); + return; + } + + bool has_water = false; + bool has_canal = false; + + for (DiagDirection dir = DIAGDIR_BEGIN; dir < DIAGDIR_END; dir++) { + TileIndex neighbour = TileAddByDiagDir(t, dir); + if (IsTileType(neighbour, MP_WATER)) { + has_water |= IsSea(neighbour) || IsCoast(neighbour); + has_canal |= IsCanal(neighbour); + } + } + if (has_canal || !has_water) { + MakeCanal(t, o); + } else { + MakeWater(t); + } + MarkTileDirtyByTile(t); +} + + /** Build a ship depot. * @param tile tile where ship depot is built * @param flags type of operation @@ -178,8 +214,8 @@ static CommandCost RemoveShiplift(TileIndex tile, uint32 flags) if (flags & DC_EXEC) { DoClearSquare(tile); - DoClearSquare(tile + delta); - DoClearSquare(tile - delta); + MakeWaterOrCanalDependingOnSurroundings(tile + delta, _current_player); + MakeWaterOrCanalDependingOnSurroundings(tile - delta, _current_player); } return CommandCost(_price.clear_water * 2); -- cgit v1.2.3-54-g00ecf