mirror of
https://github.com/JGRennison/OpenTTD-patches.git
synced 2024-11-09 19:10:38 +00:00
Add: Command to build an individual house on a specific tile.
This commit is contained in:
parent
f901722066
commit
d99c1337a2
@ -283,6 +283,7 @@ enum Commands : uint16_t {
|
||||
CMD_TOWN_SET_TEXT, ///< set the custom text of a town
|
||||
CMD_EXPAND_TOWN, ///< expand a town
|
||||
CMD_DELETE_TOWN, ///< delete a town
|
||||
CMD_PLACE_HOUSE, ///< place a house
|
||||
|
||||
CMD_ORDER_REFIT, ///< change the refit information of an order (for "goto depot" )
|
||||
CMD_CLONE_ORDER, ///< clone (and share) an order
|
||||
|
106
src/town_cmd.cpp
106
src/town_cmd.cpp
@ -2665,6 +2665,39 @@ static bool CheckTownBuild2x2House(TileIndex *tile, Town *t, int maxz, bool nosl
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Build a house at this tile.
|
||||
* @param t The town the house will belong to.
|
||||
* @param tile The tile to try building on.
|
||||
* @param hs The @a HouseSpec of the house.
|
||||
* @param house The @a HouseID of the house.
|
||||
* @param random_bits The random data to be associated with the house.
|
||||
*/
|
||||
static void BuildTownHouse(Town *t, TileIndex tile, const HouseSpec *hs, HouseID house, uint8_t random_bits)
|
||||
{
|
||||
/* build the house */
|
||||
t->cache.num_houses++;
|
||||
|
||||
uint8_t construction_counter = 0;
|
||||
uint8_t construction_stage = 0;
|
||||
|
||||
if (_generating_world || _game_mode == GM_EDITOR) {
|
||||
uint32_t construction_random = Random();
|
||||
|
||||
construction_stage = TOWN_HOUSE_COMPLETED;
|
||||
if (Chance16(1, 7)) construction_stage = GB(construction_random, 0, 2);
|
||||
|
||||
if (construction_stage == TOWN_HOUSE_COMPLETED) {
|
||||
ChangePopulation(t, hs->population);
|
||||
} else {
|
||||
construction_counter = GB(construction_random, 2, 2);
|
||||
}
|
||||
}
|
||||
|
||||
MakeTownHouse(tile, t, construction_counter, construction_stage, house, random_bits);
|
||||
UpdateTownRadius(t);
|
||||
UpdateTownGrowthRate(t);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tries to build a house at this tile.
|
||||
@ -2784,31 +2817,10 @@ static bool TryBuildTownHouse(Town *t, TileIndex tile)
|
||||
if (callback_res != CALLBACK_FAILED && !Convert8bitBooleanCallback(hs->grf_prop.grffile, CBID_HOUSE_ALLOW_CONSTRUCTION, callback_res)) continue;
|
||||
}
|
||||
|
||||
/* build the house */
|
||||
t->cache.num_houses++;
|
||||
|
||||
/* Special houses that there can be only one of. */
|
||||
t->flags |= oneof;
|
||||
|
||||
uint8_t construction_counter = 0;
|
||||
uint8_t construction_stage = 0;
|
||||
|
||||
if (_generating_world || _game_mode == GM_EDITOR) {
|
||||
uint32_t construction_random = Random();
|
||||
|
||||
construction_stage = TOWN_HOUSE_COMPLETED;
|
||||
if (Chance16(1, 7)) construction_stage = GB(construction_random, 0, 2);
|
||||
|
||||
if (construction_stage == TOWN_HOUSE_COMPLETED) {
|
||||
ChangePopulation(t, hs->population);
|
||||
} else {
|
||||
construction_counter = GB(construction_random, 2, 2);
|
||||
}
|
||||
}
|
||||
|
||||
MakeTownHouse(tile, t, construction_counter, construction_stage, house, random_bits);
|
||||
UpdateTownRadius(t);
|
||||
UpdateTownGrowthRate(t);
|
||||
BuildTownHouse(t, tile, hs, house, random_bits);
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -2816,6 +2828,56 @@ static bool TryBuildTownHouse(Town *t, TileIndex tile)
|
||||
return false;
|
||||
}
|
||||
|
||||
CommandCost CmdPlaceHouse(DoCommandFlag flags, TileIndex tile, HouseID house)
|
||||
{
|
||||
if (_game_mode != GM_EDITOR) return CMD_ERROR;
|
||||
if (Town::GetNumItems() == 0) return_cmd_error(STR_ERROR_MUST_FOUND_TOWN_FIRST);
|
||||
|
||||
if (static_cast<size_t>(house) >= HouseSpec::Specs().size()) return CMD_ERROR;
|
||||
const HouseSpec *hs = HouseSpec::Get(house);
|
||||
if (!hs->enabled) return CMD_ERROR;
|
||||
|
||||
if (TimerGameCalendar::year < hs->min_year || TimerGameCalendar::year > hs->max_year) return CMD_ERROR;
|
||||
|
||||
Town *t = ClosestTownFromTile(tile, UINT_MAX);
|
||||
|
||||
/* cannot build on these slopes... */
|
||||
Slope slope = GetTileSlope(tile);
|
||||
if (IsSteepSlope(slope)) return_cmd_error(STR_ERROR_LAND_SLOPED_IN_WRONG_DIRECTION);
|
||||
|
||||
/* building under a bridge? */
|
||||
if (IsBridgeAbove(tile)) return_cmd_error(STR_ERROR_MUST_DEMOLISH_BRIDGE_FIRST);
|
||||
|
||||
/* can we clear the land? */
|
||||
CommandCost cost = Command<CMD_LANDSCAPE_CLEAR>::Do(DC_AUTO | DC_NO_WATER, tile);
|
||||
if (!cost.Succeeded()) return cost;
|
||||
|
||||
int maxz = GetTileMaxZ(tile);
|
||||
|
||||
/* Make sure there is no slope? */
|
||||
bool noslope = (hs->building_flags & TILE_NOT_SLOPED) != 0;
|
||||
if (noslope && slope != SLOPE_FLAT) return_cmd_error(STR_ERROR_FLAT_LAND_REQUIRED);
|
||||
|
||||
TileArea ta = tile;
|
||||
if (hs->building_flags & TILE_SIZE_2x2) ta.Add(TileAddXY(tile, 1, 1));
|
||||
if (hs->building_flags & TILE_SIZE_2x1) ta.Add(TileAddByDiagDir(tile, DIAGDIR_SW));
|
||||
if (hs->building_flags & TILE_SIZE_1x2) ta.Add(TileAddByDiagDir(tile, DIAGDIR_SE));
|
||||
|
||||
/* Check additonal tiles covered by this house. */
|
||||
for (const TileIndex &subtile : ta) {
|
||||
cost = Command<CMD_LANDSCAPE_CLEAR>::Do(DC_AUTO | DC_NO_WATER, subtile);
|
||||
if (!cost.Succeeded()) return cost;
|
||||
|
||||
if (!CheckBuildHouseSameZ(subtile, maxz, noslope)) return_cmd_error(STR_ERROR_LAND_SLOPED_IN_WRONG_DIRECTION);
|
||||
}
|
||||
|
||||
if (flags & DC_EXEC) {
|
||||
BuildTownHouse(t, tile, hs, house, Random());
|
||||
}
|
||||
|
||||
return CommandCost();
|
||||
}
|
||||
|
||||
/**
|
||||
* Update data structures when a house is removed
|
||||
* @param tile Tile of the house
|
||||
|
@ -15,6 +15,7 @@
|
||||
#include "town_type.h"
|
||||
|
||||
enum TownAcceptanceEffect : uint8_t;
|
||||
using HouseID = uint16_t;
|
||||
|
||||
std::tuple<CommandCost, Money, TownID> CmdFoundTown(DoCommandFlag flags, TileIndex tile, TownSize size, bool city, TownLayout layout, bool random_location, uint32_t townnameparts, const std::string &text);
|
||||
CommandCost CmdRenameTown(DoCommandFlag flags, TownID town_id, const std::string &text);
|
||||
@ -25,6 +26,7 @@ CommandCost CmdTownCargoGoal(DoCommandFlag flags, TownID town_id, TownAcceptance
|
||||
CommandCost CmdTownSetText(DoCommandFlag flags, TownID town_id, const std::string &text);
|
||||
CommandCost CmdExpandTown(DoCommandFlag flags, TownID town_id, uint32_t grow_amount);
|
||||
CommandCost CmdDeleteTown(DoCommandFlag flags, TownID town_id);
|
||||
CommandCost CmdPlaceHouse(DoCommandFlag flags, TileIndex tile, HouseID house);
|
||||
|
||||
DEF_CMD_TRAIT(CMD_FOUND_TOWN, CmdFoundTown, CMD_DEITY | CMD_NO_TEST, CMDT_LANDSCAPE_CONSTRUCTION) // founding random town can fail only in exec run
|
||||
DEF_CMD_TRAIT(CMD_RENAME_TOWN, CmdRenameTown, CMD_DEITY | CMD_SERVER, CMDT_OTHER_MANAGEMENT)
|
||||
@ -35,6 +37,7 @@ DEF_CMD_TRAIT(CMD_TOWN_RATING, CmdTownRating, CMD_DEITY,
|
||||
DEF_CMD_TRAIT(CMD_TOWN_SET_TEXT, CmdTownSetText, CMD_DEITY | CMD_STR_CTRL, CMDT_OTHER_MANAGEMENT)
|
||||
DEF_CMD_TRAIT(CMD_EXPAND_TOWN, CmdExpandTown, CMD_DEITY, CMDT_LANDSCAPE_CONSTRUCTION)
|
||||
DEF_CMD_TRAIT(CMD_DELETE_TOWN, CmdDeleteTown, CMD_OFFLINE, CMDT_LANDSCAPE_CONSTRUCTION)
|
||||
DEF_CMD_TRAIT(CMD_PLACE_HOUSE, CmdPlaceHouse, CMD_DEITY, CMDT_OTHER_MANAGEMENT)
|
||||
|
||||
CommandCallback CcFoundTown;
|
||||
void CcFoundRandomTown(Commands cmd, const CommandCost &result, Money, TownID town_id);
|
||||
|
Loading…
Reference in New Issue
Block a user