Add town growth tiles
This commit is contained in:
@@ -20,10 +20,15 @@ namespace event {
|
||||
struct NewMonth {
|
||||
};
|
||||
|
||||
struct TownGrowthTick {
|
||||
struct TownGrowthSucceeded {
|
||||
Town *town;
|
||||
bool growth_result;
|
||||
uint16 prev_houses;
|
||||
TileIndex tile;
|
||||
uint32 prev_houses;
|
||||
};
|
||||
|
||||
struct TownGrowthFailed {
|
||||
Town *town;
|
||||
TileIndex tile;
|
||||
};
|
||||
|
||||
struct HouseRebuilt {
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
namespace citymania {
|
||||
|
||||
Game::Game() {
|
||||
this->events.listen<event::NewMonth>([] (const event::NewMonth &) {
|
||||
this->events.listen<event::NewMonth>([this] (const event::NewMonth &) {
|
||||
for (Town *t : Town::Iterate()) {
|
||||
t->cm.hs_last_month = t->cm.hs_total - t->cm.hs_total_prev;
|
||||
t->cm.hs_total_prev = t->cm.hs_total;
|
||||
@@ -21,26 +21,38 @@ Game::Game() {
|
||||
t->cm.houses_demolished_last_month = t->cm.houses_demolished_this_month;
|
||||
t->cm.houses_demolished_this_month = 0;
|
||||
}
|
||||
|
||||
this->towns_growth_tiles_last_month = this->towns_growth_tiles;
|
||||
this->towns_growth_tiles.clear();
|
||||
});
|
||||
this->events.listen<event::TownGrowthTick>([this] (const event::TownGrowthTick &event) {
|
||||
if (event.growth_result) {
|
||||
if (event.town->cache.num_houses <= event.prev_houses) {
|
||||
event.town->cm.hs_total++;
|
||||
}
|
||||
} else {
|
||||
event.town->cm.cs_total++;
|
||||
|
||||
this->events.listen<event::TownGrowthSucceeded>([this] (const event::TownGrowthSucceeded &event) {
|
||||
if (event.town->cache.num_houses <= event.prev_houses) {
|
||||
event.town->cm.hs_total++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::HS;
|
||||
}
|
||||
});
|
||||
|
||||
this->events.listen<event::TownGrowthFailed>([this] (const event::TownGrowthFailed &event) {
|
||||
event.town->cm.cs_total++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::CS;
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseRebuilt>([this] (const event::HouseRebuilt &event) {
|
||||
if (event.was_successful) {
|
||||
event.town->cm.houses_reconstructed_this_month++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::RH_REBUILT;
|
||||
} else {
|
||||
event.town->cm.houses_demolished_this_month++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::RH_REMOVED;
|
||||
}
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseBuilt>([this] (const event::HouseBuilt &event) {
|
||||
event.town->cm.houses_constructing++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::NEW_HOUSE;
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseCompleted>([this] (const event::HouseCompleted &event) {
|
||||
event.town->cm.houses_constructing--;
|
||||
});
|
||||
|
||||
@@ -7,7 +7,23 @@
|
||||
|
||||
namespace citymania {
|
||||
|
||||
/* BEGIN CMClient growth tiles */
|
||||
enum class TownGrowthTileState : uint8 {
|
||||
NONE = 0,
|
||||
RH_REMOVED,
|
||||
NEW_HOUSE,
|
||||
RH_REBUILT, // rebuilt and removed houses are also
|
||||
CS,
|
||||
HS,
|
||||
HR
|
||||
};
|
||||
|
||||
class Game {
|
||||
protected:
|
||||
typedef std::map<TileIndex, TownGrowthTileState> TownsGrowthTilesIndex;
|
||||
TownsGrowthTilesIndex towns_growth_tiles_last_month;
|
||||
TownsGrowthTilesIndex towns_growth_tiles;
|
||||
|
||||
public:
|
||||
event::Dispatcher events;
|
||||
|
||||
|
||||
@@ -881,10 +881,7 @@ static void TownTickHandler(Town *t)
|
||||
if (HasBit(t->flags, TOWN_IS_GROWING)) {
|
||||
int i = (int)t->grow_counter - 1;
|
||||
if (i < 0) {
|
||||
uint16 prev_houses = t->cache.num_houses;
|
||||
bool growth_res = GrowTown(t);
|
||||
citymania::Emit((citymania::event::TownGrowthTick){t, growth_res, prev_houses});
|
||||
if (growth_res) {
|
||||
if (GrowTown(t)) {
|
||||
i = t->growth_rate;
|
||||
} else {
|
||||
/* If growth failed wait a bit before retrying */
|
||||
@@ -1570,17 +1567,24 @@ static bool GrowTownAtRoad(Town *t, TileIndex tile)
|
||||
break;
|
||||
}
|
||||
|
||||
uint16 prev_houses = t->cache.num_houses;
|
||||
do {
|
||||
RoadBits cur_rb = GetTownRoadBits(tile); // The RoadBits of the current tile
|
||||
|
||||
/* Try to grow the town from this point */
|
||||
GrowTownInTile(&tile, cur_rb, target_dir, t);
|
||||
if (_grow_town_result == GROWTH_SUCCEED) return true;
|
||||
if (_grow_town_result == GROWTH_SUCCEED) {
|
||||
citymania::Emit(citymania::event::TownGrowthSucceeded{t, tile, prev_houses});
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Exclude the source position from the bitmask
|
||||
* and return if no more road blocks available */
|
||||
if (IsValidDiagDirection(target_dir)) cur_rb &= ~DiagDirToRoadBits(ReverseDiagDir(target_dir));
|
||||
if (cur_rb == ROAD_NONE) return false;
|
||||
if (cur_rb == ROAD_NONE) {
|
||||
citymania::Emit(citymania::event::TownGrowthFailed{t, tile});
|
||||
return false;
|
||||
}
|
||||
|
||||
if (IsTileType(tile, MP_TUNNELBRIDGE)) {
|
||||
/* Only build in the direction away from the tunnel or bridge. */
|
||||
@@ -1589,7 +1593,10 @@ static bool GrowTownAtRoad(Town *t, TileIndex tile)
|
||||
/* Select a random bit from the blockmask, walk a step
|
||||
* and continue the search from there. */
|
||||
do {
|
||||
if (cur_rb == ROAD_NONE) return false;
|
||||
if (cur_rb == ROAD_NONE) {
|
||||
citymania::Emit(citymania::event::TownGrowthFailed{t, tile});
|
||||
return false;
|
||||
}
|
||||
RoadBits target_bits;
|
||||
do {
|
||||
target_dir = RandomDiagDir();
|
||||
@@ -1603,6 +1610,7 @@ static bool GrowTownAtRoad(Town *t, TileIndex tile)
|
||||
if (IsTileType(tile, MP_ROAD) && !IsRoadDepot(tile) && HasTileRoadType(tile, RTT_ROAD)) {
|
||||
/* Don't allow building over roads of other cities */
|
||||
if (IsRoadOwner(tile, RTT_ROAD, OWNER_TOWN) && Town::GetByTile(tile) != t) {
|
||||
citymania::Emit(citymania::event::TownGrowthFailed{t, tile});
|
||||
return false;
|
||||
} else if (IsRoadOwner(tile, RTT_ROAD, OWNER_NONE) && _game_mode == GM_EDITOR) {
|
||||
/* If we are in the SE, and this road-piece has no town owner yet, it just found an
|
||||
@@ -1615,6 +1623,7 @@ static bool GrowTownAtRoad(Town *t, TileIndex tile)
|
||||
/* Max number of times is checked. */
|
||||
} while (--_grow_town_result >= 0);
|
||||
|
||||
citymania::Emit(citymania::event::TownGrowthFailed{t, tile});
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -1684,6 +1693,7 @@ static bool GrowTown(Town *t)
|
||||
RoadType rt = GetTownRoadType(t);
|
||||
DoCommand(tile, GenRandomRoadBits() | (rt << 4), t->index, DC_EXEC | DC_AUTO, CMD_BUILD_ROAD);
|
||||
cur_company.Restore();
|
||||
citymania::Emit(citymania::event::TownGrowthSucceeded{t, tile, t->cache.num_houses});
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -1692,6 +1702,7 @@ static bool GrowTown(Town *t)
|
||||
}
|
||||
|
||||
cur_company.Restore();
|
||||
citymania::Emit(citymania::event::TownGrowthFailed{t, tile});
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user