diff --git a/src/openrct2/actions/FootpathPlaceAction.cpp b/src/openrct2/actions/FootpathPlaceAction.cpp index be84fabf90..5b1894b9b8 100644 --- a/src/openrct2/actions/FootpathPlaceAction.cpp +++ b/src/openrct2/actions/FootpathPlaceAction.cpp @@ -248,16 +248,17 @@ GameActions::Result::Ptr FootpathPlaceAction::ElementInsertQuery(GameActions::Re uint8_t crossingMode = (_type & FOOTPATH_ELEMENT_INSERT_QUEUE) || (_slope != TILE_ELEMENT_SLOPE_FLAT) ? CREATE_CROSSING_MODE_NONE : CREATE_CROSSING_MODE_PATH_OVER_TRACK; - if (!entrancePath - && !map_can_construct_with_clear_at( - { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), &res->Cost, crossingMode)) + auto canBuild = MapCanConstructWithClearAt( + { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), crossingMode); + if (!entrancePath && canBuild->Error != GameActions::Status::Ok) { - return MakeResult( - GameActions::Status::NoClearance, STR_CANT_BUILD_FOOTPATH_HERE, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_CANT_BUILD_FOOTPATH_HERE; + return canBuild; } + res->Cost += canBuild->Cost; - gFootpathGroundFlags = gMapGroundFlags; - if (!gCheatsDisableClearanceChecks && (gMapGroundFlags & ELEMENT_IS_UNDERWATER)) + gFootpathGroundFlags = canBuild->GroundFlags; + if (!gCheatsDisableClearanceChecks && (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER)) { return MakeResult(GameActions::Status::Disallowed, STR_CANT_BUILD_FOOTPATH_HERE, STR_CANT_BUILD_THIS_UNDERWATER); } @@ -318,11 +319,12 @@ GameActions::Result::Ptr FootpathPlaceAction::ElementInsertExecute(GameActions:: crossingMode); if (!entrancePath && canBuild->Error != GameActions::Status::Ok) { + canBuild->ErrorTitle = STR_CANT_BUILD_FOOTPATH_HERE; return canBuild; } res->Cost += canBuild->Cost; - gFootpathGroundFlags = gMapGroundFlags; + gFootpathGroundFlags = canBuild->GroundFlags; auto surfaceElement = map_get_surface_element_at(_loc); if (surfaceElement == nullptr) diff --git a/src/openrct2/actions/FootpathPlaceFromTrackAction.cpp b/src/openrct2/actions/FootpathPlaceFromTrackAction.cpp index fa89fd0aed..80249c155f 100644 --- a/src/openrct2/actions/FootpathPlaceFromTrackAction.cpp +++ b/src/openrct2/actions/FootpathPlaceFromTrackAction.cpp @@ -132,17 +132,17 @@ GameActions::Result::Ptr FootpathPlaceFromTrackAction::ElementInsertQuery(GameAc uint8_t crossingMode = (_type & FOOTPATH_ELEMENT_INSERT_QUEUE) || (_slope != TILE_ELEMENT_SLOPE_FLAT) ? CREATE_CROSSING_MODE_NONE : CREATE_CROSSING_MODE_PATH_OVER_TRACK; - if (!entrancePath - && !map_can_construct_with_clear_at( - { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), &res->Cost, crossingMode)) + auto canBuild = MapCanConstructWithClearAt( + { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), crossingMode); + if (!entrancePath && canBuild->Error != GameActions::Status::Ok) { - return MakeResult( - GameActions::Status::NoClearance, STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE, gGameCommandErrorText, - gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } + res->Cost += canBuild->Cost; + gFootpathGroundFlags = canBuild->GroundFlags; - gFootpathGroundFlags = gMapGroundFlags; - if (!gCheatsDisableClearanceChecks && (gMapGroundFlags & ELEMENT_IS_UNDERWATER)) + if (!gCheatsDisableClearanceChecks && (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER)) { return MakeResult( GameActions::Status::Disallowed, STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE, STR_CANT_BUILD_THIS_UNDERWATER); @@ -199,17 +199,16 @@ GameActions::Result::Ptr FootpathPlaceFromTrackAction::ElementInsertExecute(Game uint8_t crossingMode = (_type & FOOTPATH_ELEMENT_INSERT_QUEUE) || (_slope != TILE_ELEMENT_SLOPE_FLAT) ? CREATE_CROSSING_MODE_NONE : CREATE_CROSSING_MODE_PATH_OVER_TRACK; - if (!entrancePath - && !map_can_construct_with_clear_at( - { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GAME_COMMAND_FLAG_APPLY | GetFlags(), - &res->Cost, crossingMode)) + auto canBuild = MapCanConstructWithClearAt( + { _loc, zLow, zHigh }, &map_place_non_scenery_clear_func, quarterTile, GAME_COMMAND_FLAG_APPLY | GetFlags(), + crossingMode); + if (!entrancePath && canBuild->Error != GameActions::Status::Ok) { - return MakeResult( - GameActions::Status::NoClearance, STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE, gGameCommandErrorText, - gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } - - gFootpathGroundFlags = gMapGroundFlags; + res->Cost += canBuild->Cost; + gFootpathGroundFlags = canBuild->GroundFlags; auto surfaceElement = map_get_surface_element_at(_loc); if (surfaceElement == nullptr) diff --git a/src/openrct2/actions/LargeSceneryPlaceAction.cpp b/src/openrct2/actions/LargeSceneryPlaceAction.cpp index e2c877f03c..dd637c86d8 100644 --- a/src/openrct2/actions/LargeSceneryPlaceAction.cpp +++ b/src/openrct2/actions/LargeSceneryPlaceAction.cpp @@ -160,18 +160,22 @@ GameActions::Result::Ptr LargeSceneryPlaceAction::Query() const int32_t zHigh = tile->z_clearance + zLow; QuarterTile quarterTile = QuarterTile{ static_cast(tile->flags >> 12), 0 }.Rotate(_loc.direction); - if (!map_can_construct_with_clear_at( - { curTile, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), &supportsCost, - CREATE_CROSSING_MODE_NONE, (sceneryEntry->flags & LARGE_SCENERY_FLAG_IS_TREE) != 0)) + const auto isTree = (sceneryEntry->flags & LARGE_SCENERY_FLAG_IS_TREE) != 0; + auto canBuild = MapCanConstructWithClearAt( + { curTile, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), CREATE_CROSSING_MODE_NONE, + isTree); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::NoClearance, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_CANT_POSITION_THIS_HERE; + return canBuild; } - int32_t tempSceneryGroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + supportsCost += canBuild->Cost; + + int32_t tempSceneryGroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); if (!gCheatsDisableClearanceChecks) { - if ((gMapGroundFlags & ELEMENT_IS_UNDERWATER) || (gMapGroundFlags & ELEMENT_IS_UNDERGROUND)) + if ((canBuild->GroundFlags & ELEMENT_IS_UNDERWATER) || (canBuild->GroundFlags & ELEMENT_IS_UNDERGROUND)) { return std::make_unique( GameActions::Status::Disallowed, STR_CANT_BUILD_THIS_UNDERWATER); @@ -258,15 +262,18 @@ GameActions::Result::Ptr LargeSceneryPlaceAction::Execute() const int32_t zHigh = tile->z_clearance + zLow; QuarterTile quarterTile = QuarterTile{ static_cast(tile->flags >> 12), 0 }.Rotate(_loc.direction); - if (!map_can_construct_with_clear_at( - { curTile, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), &supportsCost, - CREATE_CROSSING_MODE_NONE, (sceneryEntry->flags & LARGE_SCENERY_FLAG_IS_TREE) != 0)) + const auto isTree = (sceneryEntry->flags & LARGE_SCENERY_FLAG_IS_TREE) != 0; + auto canBuild = MapCanConstructWithClearAt( + { curTile, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), CREATE_CROSSING_MODE_NONE, + isTree); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::NoClearance, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_CANT_POSITION_THIS_HERE; + return canBuild; } - res->GroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + supportsCost += canBuild->Cost; + res->GroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); if (!(GetFlags() & GAME_COMMAND_FLAG_GHOST)) { diff --git a/src/openrct2/actions/MazePlaceTrackAction.cpp b/src/openrct2/actions/MazePlaceTrackAction.cpp index 0b5f7d356e..dc19183047 100644 --- a/src/openrct2/actions/MazePlaceTrackAction.cpp +++ b/src/openrct2/actions/MazePlaceTrackAction.cpp @@ -83,24 +83,22 @@ GameActions::Result::Ptr MazePlaceTrackAction::Query() const } } - money32 clearCost = 0; - - if (!map_can_construct_with_clear_at( - { _loc.ToTileStart(), baseHeight, clearanceHeight }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags(), - &clearCost, CREATE_CROSSING_MODE_NONE)) + auto canBuild = MapCanConstructWithClearAt( + { _loc.ToTileStart(), baseHeight, clearanceHeight }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags()); + if (canBuild->Error != GameActions::Status::Ok) { - return MakeResult( - GameActions::Status::NoClearance, res->ErrorTitle.GetStringId(), gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } - if (gMapGroundFlags & ELEMENT_IS_UNDERWATER) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER) { res->Error = GameActions::Status::NoClearance; res->ErrorMessage = STR_RIDE_CANT_BUILD_THIS_UNDERWATER; return res; } - if (gMapGroundFlags & ELEMENT_IS_UNDERGROUND) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERGROUND) { res->Error = GameActions::Status::NoClearance; res->ErrorMessage = STR_CAN_ONLY_BUILD_THIS_ABOVE_GROUND; @@ -116,7 +114,7 @@ GameActions::Result::Ptr MazePlaceTrackAction::Query() const } money32 price = (((ride->GetRideTypeDescriptor().BuildCosts.TrackPrice * TrackPricing[TrackElemType::Maze]) >> 16)); - res->Cost = clearCost + price / 2 * 10; + res->Cost = canBuild->Cost + price / 2 * 10; return res; } @@ -154,17 +152,17 @@ GameActions::Result::Ptr MazePlaceTrackAction::Execute() const auto baseHeight = _loc.z; auto clearanceHeight = _loc.z + MAZE_CLEARANCE_HEIGHT; - money32 clearCost = 0; - if (!map_can_construct_with_clear_at( - { _loc.ToTileStart(), baseHeight, clearanceHeight }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, - GetFlags() | GAME_COMMAND_FLAG_APPLY, &clearCost, CREATE_CROSSING_MODE_NONE)) + auto canBuild = MapCanConstructWithClearAt( + { _loc.ToTileStart(), baseHeight, clearanceHeight }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, + GetFlags() | GAME_COMMAND_FLAG_APPLY); + if (canBuild->Error != GameActions::Status::Ok) { - return MakeResult( - GameActions::Status::NoClearance, res->ErrorTitle.GetStringId(), gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } money32 price = (((ride->GetRideTypeDescriptor().BuildCosts.TrackPrice * TrackPricing[TrackElemType::Maze]) >> 16)); - res->Cost = clearCost + price / 2 * 10; + res->Cost = canBuild->Cost + price / 2 * 10; auto startLoc = _loc.ToTileStart(); diff --git a/src/openrct2/actions/RideEntranceExitPlaceAction.cpp b/src/openrct2/actions/RideEntranceExitPlaceAction.cpp index 5627295f31..f60574d0c5 100644 --- a/src/openrct2/actions/RideEntranceExitPlaceAction.cpp +++ b/src/openrct2/actions/RideEntranceExitPlaceAction.cpp @@ -99,15 +99,15 @@ GameActions::Result::Ptr RideEntranceExitPlaceAction::Query() const } auto clear_z = z + (_isExit ? RideExitHeight : RideEntranceHeight); - auto cost = MONEY32_UNDEFINED; - if (!map_can_construct_with_clear_at( - { _loc, z, clear_z }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags(), &cost, - CREATE_CROSSING_MODE_NONE)) + auto canBuild = MapCanConstructWithClearAt( + { _loc, z, clear_z }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags()); + if (canBuild->Error != GameActions::Status::Ok) { - return MakeResult(GameActions::Status::NoClearance, errorTitle, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = errorTitle; + return canBuild; } - if (gMapGroundFlags & ELEMENT_IS_UNDERWATER) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER) { return MakeResult(GameActions::Status::Disallowed, errorTitle, STR_RIDE_CANT_BUILD_THIS_UNDERWATER); } @@ -163,12 +163,12 @@ GameActions::Result::Ptr RideEntranceExitPlaceAction::Execute() const } auto clear_z = z + (_isExit ? RideExitHeight : RideEntranceHeight); - auto cost = MONEY32_UNDEFINED; - if (!map_can_construct_with_clear_at( - { _loc, z, clear_z }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags() | GAME_COMMAND_FLAG_APPLY, &cost, - CREATE_CROSSING_MODE_NONE)) + auto canBuild = MapCanConstructWithClearAt( + { _loc, z, clear_z }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, GetFlags() | GAME_COMMAND_FLAG_APPLY); + if (canBuild->Error != GameActions::Status::Ok) { - return MakeResult(GameActions::Status::NoClearance, errorTitle, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = errorTitle; + return canBuild; } auto res = MakeResult(); @@ -229,14 +229,14 @@ GameActions::Result::Ptr RideEntranceExitPlaceAction::TrackPlaceQuery(const Coor int16_t baseZ = loc.z; int16_t clearZ = baseZ + (isExit ? RideExitHeight : RideEntranceHeight); - auto cost = MONEY32_UNDEFINED; - if (!map_can_construct_with_clear_at( - { loc, baseZ, clearZ }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, 0, &cost, CREATE_CROSSING_MODE_NONE)) + auto canBuild = MapCanConstructWithClearAt({ loc, baseZ, clearZ }, &map_place_non_scenery_clear_func, { 0b1111, 0 }, 0); + if (canBuild->Error != GameActions::Status::Ok) { - return MakeResult(GameActions::Status::NoClearance, errorTitle, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = errorTitle; + return canBuild; } - if (gMapGroundFlags & ELEMENT_IS_UNDERWATER) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER) { return MakeResult(GameActions::Status::Disallowed, errorTitle, STR_RIDE_CANT_BUILD_THIS_UNDERWATER); } diff --git a/src/openrct2/actions/SmallSceneryPlaceAction.cpp b/src/openrct2/actions/SmallSceneryPlaceAction.cpp index b96da2620f..adb2c8743c 100644 --- a/src/openrct2/actions/SmallSceneryPlaceAction.cpp +++ b/src/openrct2/actions/SmallSceneryPlaceAction.cpp @@ -276,20 +276,19 @@ GameActions::Result::Ptr SmallSceneryPlaceAction::Query() const } QuarterTile quarterTile = QuarterTile{ collisionQuadrants, supports }.Rotate(quadRotation); - money32 clearCost = 0; - - if (!map_can_construct_with_clear_at( - { _loc, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), &clearCost, - CREATE_CROSSING_MODE_NONE, scenery_small_entry_has_flag(sceneryEntry, SMALL_SCENERY_FLAG_IS_TREE))) + const auto isTree = scenery_small_entry_has_flag(sceneryEntry, SMALL_SCENERY_FLAG_IS_TREE); + auto canBuild = MapCanConstructWithClearAt( + { _loc, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags(), CREATE_CROSSING_MODE_NONE, isTree); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::Disallowed, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_CANT_POSITION_THIS_HERE; + return canBuild; } - res->GroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + res->GroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); res->Expenditure = ExpenditureType::Landscaping; - res->Cost = (sceneryEntry->price * 10) + clearCost; + res->Cost = (sceneryEntry->price * 10) + canBuild->Cost; return res; } @@ -414,20 +413,20 @@ GameActions::Result::Ptr SmallSceneryPlaceAction::Execute() const } QuarterTile quarterTile = QuarterTile{ collisionQuadrants, supports }.Rotate(quadRotation); - money32 clearCost = 0; - - if (!map_can_construct_with_clear_at( - { _loc, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags() | GAME_COMMAND_FLAG_APPLY, &clearCost, - CREATE_CROSSING_MODE_NONE, scenery_small_entry_has_flag(sceneryEntry, SMALL_SCENERY_FLAG_IS_TREE))) + const auto isTree = scenery_small_entry_has_flag(sceneryEntry, SMALL_SCENERY_FLAG_IS_TREE); + auto canBuild = MapCanConstructWithClearAt( + { _loc, zLow, zHigh }, &map_place_scenery_clear_func, quarterTile, GetFlags() | GAME_COMMAND_FLAG_APPLY, + CREATE_CROSSING_MODE_NONE, isTree); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::Disallowed, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_CANT_POSITION_THIS_HERE; + return canBuild; } - res->GroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + res->GroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); res->Expenditure = ExpenditureType::Landscaping; - res->Cost = (sceneryEntry->price * 10) + clearCost; + res->Cost = (sceneryEntry->price * 10) + canBuild->Cost; auto* sceneryElement = TileElementInsert( CoordsXYZ{ _loc, zLow }, quarterTile.GetBaseQuarterOccupied()); diff --git a/src/openrct2/actions/TrackPlaceAction.cpp b/src/openrct2/actions/TrackPlaceAction.cpp index 7aa0bac0f6..7f5f8b3d8c 100644 --- a/src/openrct2/actions/TrackPlaceAction.cpp +++ b/src/openrct2/actions/TrackPlaceAction.cpp @@ -232,12 +232,14 @@ GameActions::Result::Ptr TrackPlaceAction::Query() const && _trackType == TrackElemType::Flat) ? CREATE_CROSSING_MODE_TRACK_OVER_PATH : CREATE_CROSSING_MODE_NONE; - if (!map_can_construct_with_clear_at( - { mapLoc, baseZ, clearanceZ }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), &cost, crossingMode)) + auto canBuild = MapCanConstructWithClearAt( + { mapLoc, baseZ, clearanceZ }, &map_place_non_scenery_clear_func, quarterTile, GetFlags(), crossingMode); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::NoClearance, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } + cost += canBuild->Cost; // When building a level crossing, remove any pre-existing path furniture. if (crossingMode == CREATE_CROSSING_MODE_TRACK_OVER_PATH) @@ -249,7 +251,7 @@ GameActions::Result::Ptr TrackPlaceAction::Query() const } } - uint8_t mapGroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + uint8_t mapGroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); if (res->GroundFlags != 0 && (res->GroundFlags & mapGroundFlags) == 0) { return std::make_unique( @@ -269,14 +271,14 @@ GameActions::Result::Ptr TrackPlaceAction::Query() const if (TrackFlags[_trackType] & TRACK_ELEM_FLAG_ONLY_UNDERWATER) { // No element has this flag - if (gMapGroundFlags & ELEMENT_IS_UNDERWATER) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER) { return std::make_unique( GameActions::Status::Disallowed, STR_CAN_ONLY_BUILD_THIS_UNDERWATER); } } - if (gMapGroundFlags & ELEMENT_IS_UNDERWATER && !gCheatsDisableClearanceChecks) + if (canBuild->GroundFlags & ELEMENT_IS_UNDERWATER && !gCheatsDisableClearanceChecks) { return std::make_unique( GameActions::Status::Disallowed, STR_RIDE_CANT_BUILD_THIS_UNDERWATER); @@ -428,13 +430,15 @@ GameActions::Result::Ptr TrackPlaceAction::Execute() const && _trackType == TrackElemType::Flat) ? CREATE_CROSSING_MODE_TRACK_OVER_PATH : CREATE_CROSSING_MODE_NONE; - if (!map_can_construct_with_clear_at( - mapLocWithClearance, &map_place_non_scenery_clear_func, quarterTile, GetFlags() | GAME_COMMAND_FLAG_APPLY, - &cost, crossingMode)) + auto canBuild = MapCanConstructWithClearAt( + mapLocWithClearance, &map_place_non_scenery_clear_func, quarterTile, GetFlags() | GAME_COMMAND_FLAG_APPLY, + crossingMode); + if (canBuild->Error != GameActions::Status::Ok) { - return std::make_unique( - GameActions::Status::NoClearance, gGameCommandErrorText, gCommonFormatArgs); + canBuild->ErrorTitle = STR_RIDE_CONSTRUCTION_CANT_CONSTRUCT_THIS_HERE; + return canBuild; } + cost += canBuild->Cost; if (!(GetFlags() & GAME_COMMAND_FLAG_GHOST) && !gCheatsDisableClearanceChecks) { @@ -459,7 +463,7 @@ GameActions::Result::Ptr TrackPlaceAction::Execute() const } } - uint8_t mapGroundFlags = gMapGroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); + uint8_t mapGroundFlags = canBuild->GroundFlags & (ELEMENT_IS_ABOVE_GROUND | ELEMENT_IS_UNDERGROUND); if (res->GroundFlags != 0 && (res->GroundFlags & mapGroundFlags) == 0) { return std::make_unique( diff --git a/src/openrct2/actions/WallPlaceAction.cpp b/src/openrct2/actions/WallPlaceAction.cpp index c014e3bd87..86331606b2 100644 --- a/src/openrct2/actions/WallPlaceAction.cpp +++ b/src/openrct2/actions/WallPlaceAction.cpp @@ -534,7 +534,6 @@ GameActions::Result::Ptr WallPlaceAction::WallCheckObstruction( rct_large_scenery_tile* tile; *wallAcrossTrack = false; - gMapGroundFlags = ELEMENT_IS_ABOVE_GROUND; if (map_is_location_at_edge(_loc)) { return MakeResult(GameActions::Status::InvalidParameters, STR_OFF_EDGE_OF_MAP); diff --git a/src/openrct2/world/Map.cpp b/src/openrct2/world/Map.cpp index b14f903e98..1f4e5ad951 100644 --- a/src/openrct2/world/Map.cpp +++ b/src/openrct2/world/Map.cpp @@ -90,8 +90,6 @@ CoordsXY gMapSelectPositionB; CoordsXYZ gMapSelectArrowPosition; uint8_t gMapSelectArrowDirection; -uint8_t gMapGroundFlags; - TileCoordsXY gWidePathTileLoopPosition; uint16_t gGrassSceneryTileLoopPosition; @@ -1492,37 +1490,9 @@ std::unique_ptr MapCanConstructWithClearAt( return res; } -bool map_can_construct_with_clear_at( - const CoordsXYRangedZ& pos, CLEAR_FUNC clearFunc, QuarterTile quarterTile, uint8_t flags, money32* price, - uint8_t crossingMode, bool isTree) -{ - auto res = MapCanConstructWithClearAt(pos, clearFunc, quarterTile, flags, crossingMode, isTree); - if (auto message = res->ErrorMessage.AsStringId()) - gGameCommandErrorText = *message; - else - gGameCommandErrorText = STR_NONE; - std::copy(res->ErrorMessageArgs.begin(), res->ErrorMessageArgs.end(), gCommonFormatArgs); - if (price != nullptr) - { - *price += res->Cost; - } - - gMapGroundFlags = res->GroundFlags; - return res->Error == GameActions::Status::Ok; -} - -/** - * - * rct2: 0x0068B93A - */ -int32_t map_can_construct_at(const CoordsXYRangedZ& pos, QuarterTile bl) -{ - return map_can_construct_with_clear_at(pos, nullptr, bl, 0, nullptr, CREATE_CROSSING_MODE_NONE); -} - std::unique_ptr MapCanConstructAt(const CoordsXYRangedZ& pos, QuarterTile bl) { - return MapCanConstructWithClearAt(pos, nullptr, bl, 0, CREATE_CROSSING_MODE_NONE); + return MapCanConstructWithClearAt(pos, nullptr, bl, 0); } /** * Updates grass length, scenery age and jumping fountains. diff --git a/src/openrct2/world/Map.h b/src/openrct2/world/Map.h index 384ce7076b..ec2ff4f335 100644 --- a/src/openrct2/world/Map.h +++ b/src/openrct2/world/Map.h @@ -85,7 +85,7 @@ enum MAP_SELECT_TYPE_EDGE_3, }; -// Used when calling map_can_construct_with_clear_at(); +// Used when calling MapCanConstructWithClearAt(); // This assumes that the caller has already done the check on the element it wants to place, // as this function can only check the element the player wants to build through. enum @@ -114,8 +114,6 @@ extern CoordsXY gMapSelectPositionB; extern CoordsXYZ gMapSelectArrowPosition; extern uint8_t gMapSelectArrowDirection; -extern uint8_t gMapGroundFlags; - extern std::vector gMapSelectionTiles; extern std::vector gPeepSpawns; @@ -235,14 +233,10 @@ using CLEAR_FUNC = int32_t (*)(TileElement** tile_element, const CoordsXY& coord int32_t map_place_non_scenery_clear_func(TileElement** tile_element, const CoordsXY& coords, uint8_t flags, money32* price); int32_t map_place_scenery_clear_func(TileElement** tile_element, const CoordsXY& coords, uint8_t flags, money32* price); -bool map_can_construct_with_clear_at( - const CoordsXYRangedZ& pos, CLEAR_FUNC clearFunc, QuarterTile quarterTile, uint8_t flags, money32* price, - uint8_t crossingMode, bool isTree = false); std::unique_ptr MapCanConstructWithClearAt( - const CoordsXYRangedZ& pos, CLEAR_FUNC clearFunc, QuarterTile quarterTile, uint8_t flags, uint8_t crossingMode, - bool isTree = false); + const CoordsXYRangedZ& pos, CLEAR_FUNC clearFunc, QuarterTile quarterTile, uint8_t flags, + uint8_t crossingMode = CREATE_CROSSING_MODE_NONE, bool isTree = false); std::unique_ptr MapCanConstructAt(const CoordsXYRangedZ& pos, QuarterTile bl); -int32_t map_can_construct_at(const CoordsXYRangedZ& pos, QuarterTile bl); struct tile_element_iterator {