Merge remote-tracking branch 'upstream/master'
This commit is contained in:
35
source.list
35
source.list
@@ -613,23 +613,6 @@ water_cmd.cpp
|
||||
waypoint_cmd.cpp
|
||||
zoning_cmd.cpp
|
||||
|
||||
# CityMania files
|
||||
citymania/base64.h
|
||||
citymania/base64.cpp
|
||||
citymania/cm_bitstream.hpp
|
||||
citymania/cm_bitstream.cpp
|
||||
citymania/highlight.hpp
|
||||
citymania/highlight.cpp
|
||||
citymania/locations.hpp
|
||||
citymania/locations.cpp
|
||||
citymania/minimap.hpp
|
||||
citymania/minimap.cpp
|
||||
citymania/cm_saveload.hpp
|
||||
citymania/cm_saveload.cpp
|
||||
citymania/station_ui.hpp
|
||||
citymania/station_ui.cpp
|
||||
newgrf_revisions.hpp
|
||||
|
||||
# Save/Load handlers
|
||||
saveload/afterload.cpp
|
||||
saveload/ai_sl.cpp
|
||||
@@ -1220,6 +1203,8 @@ sound/null_s.cpp
|
||||
thread.h
|
||||
|
||||
# CityMania
|
||||
citymania/cm_bitstream.hpp
|
||||
citymania/cm_bitstream.cpp
|
||||
citymania/cm_console_cmds.hpp
|
||||
citymania/cm_console_cmds.cpp
|
||||
citymania/cm_event.hpp
|
||||
@@ -1232,5 +1217,21 @@ citymania/cm_main.cpp
|
||||
citymania/cm_tooltips.hpp
|
||||
citymania/cm_tooltips.cpp
|
||||
citymania/cm_type.hpp
|
||||
citymania/cm_saveload.hpp
|
||||
citymania/cm_saveload.cpp
|
||||
citymania/cm_settings.hpp
|
||||
citymania/extensions/cmext_town.hpp
|
||||
citymania/extensions/cmext_company.hpp
|
||||
|
||||
# CityMania client
|
||||
citymania/base64.h
|
||||
citymania/base64.cpp
|
||||
citymania/highlight.hpp
|
||||
citymania/highlight.cpp
|
||||
citymania/locations.hpp
|
||||
citymania/locations.cpp
|
||||
citymania/minimap.hpp
|
||||
citymania/minimap.cpp
|
||||
citymania/station_ui.hpp
|
||||
citymania/station_ui.cpp
|
||||
newgrf_revisions.hpp
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
#define CM_EVENT_HPP
|
||||
|
||||
#include "cm_type.hpp"
|
||||
|
||||
#include "../console_func.h"
|
||||
#include "../cargo_type.h"
|
||||
#include "../company_type.h"
|
||||
#include "../economy_type.h"
|
||||
@@ -42,12 +44,15 @@ struct HouseRebuilt {
|
||||
struct HouseBuilt {
|
||||
Town *town;
|
||||
TileIndex tile;
|
||||
HouseID house_id;
|
||||
const HouseSpec *house_spec;
|
||||
bool is_rebuilding;
|
||||
};
|
||||
|
||||
struct HouseCleared {
|
||||
Town *town;
|
||||
TileIndex tile;
|
||||
HouseID house_id;
|
||||
const HouseSpec *house_spec;
|
||||
bool was_completed; ///< whether house was completed before destruction
|
||||
};
|
||||
@@ -55,6 +60,7 @@ struct HouseCleared {
|
||||
struct HouseCompleted {
|
||||
Town *town;
|
||||
TileIndex tile;
|
||||
HouseID house_id;
|
||||
const HouseSpec *house_spec;
|
||||
};
|
||||
|
||||
@@ -100,6 +106,13 @@ struct CompanyBalanceChanged {
|
||||
Money delta;
|
||||
};
|
||||
|
||||
enum class Slot : uint8 {
|
||||
GOAL = 10,
|
||||
CONTROLLER = 20,
|
||||
GAME = 30,
|
||||
CONTROLLER_POST = 40,
|
||||
RECORDER = 50,
|
||||
};
|
||||
|
||||
class TypeDispatcherBase {
|
||||
public:
|
||||
@@ -115,14 +128,16 @@ public:
|
||||
TypeDispatcher() { }
|
||||
virtual ~TypeDispatcher() {}
|
||||
|
||||
void listen(Handler &handler) {
|
||||
this->new_handlers.push_back(handler);
|
||||
void listen(Slot slot, Handler &handler) {
|
||||
this->handler_map.insert(std::make_pair(slot, handler));
|
||||
}
|
||||
|
||||
void emit(const T &event) {
|
||||
if (!this->new_handlers.empty()) {
|
||||
this->handlers.insert(this->handlers.end(), this->new_handlers.begin(), this->new_handlers.end());
|
||||
this->new_handlers.clear();
|
||||
if (this->new_handlers) { // only rebuild handlers while not iterating
|
||||
this->handlers.clear();
|
||||
for (auto &p : this->handler_map) {
|
||||
this->handlers.push_back(p.second);
|
||||
}
|
||||
}
|
||||
for (auto &h : this->handlers) {
|
||||
h(event);
|
||||
@@ -131,7 +146,8 @@ public:
|
||||
|
||||
protected:
|
||||
std::vector<Handler> handlers;
|
||||
std::vector<Handler> new_handlers;
|
||||
std::multimap<Slot, Handler> handler_map;
|
||||
bool new_handlers = false;
|
||||
};
|
||||
|
||||
|
||||
@@ -151,8 +167,8 @@ protected:
|
||||
|
||||
public:
|
||||
template<typename T>
|
||||
void listen(std::function<void(const T &)> handler) {
|
||||
this->get_dispatcher<T>().listen(handler);
|
||||
void listen(Slot slot, std::function<void(const T &)> handler) {
|
||||
this->get_dispatcher<T>().listen(slot, handler);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
namespace citymania {
|
||||
|
||||
Game::Game() {
|
||||
this->events.listen<event::NewMonth>([this] (const event::NewMonth &) {
|
||||
this->events.listen<event::NewMonth>(event::Slot::GAME, [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;
|
||||
@@ -28,45 +28,45 @@ Game::Game() {
|
||||
this->towns_growth_tiles.clear();
|
||||
});
|
||||
|
||||
this->events.listen<event::TownGrowthSucceeded>([this] (const event::TownGrowthSucceeded &event) {
|
||||
this->events.listen<event::TownGrowthSucceeded>(event::Slot::GAME, [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->set_town_growth_tile(event.tile, TownGrowthTileState::HS);
|
||||
}
|
||||
});
|
||||
|
||||
this->events.listen<event::TownGrowthFailed>([this] (const event::TownGrowthFailed &event) {
|
||||
this->events.listen<event::TownGrowthFailed>(event::Slot::GAME, [this] (const event::TownGrowthFailed &event) {
|
||||
event.town->cm.cs_total++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::CS;
|
||||
this->set_town_growth_tile(event.tile, TownGrowthTileState::CS);
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseRebuilt>([this] (const event::HouseRebuilt &event) {
|
||||
this->events.listen<event::HouseRebuilt>(event::Slot::GAME, [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;
|
||||
this->set_town_growth_tile(event.tile, TownGrowthTileState::RH_REBUILT);
|
||||
} else {
|
||||
event.town->cm.houses_demolished_this_month++;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::RH_REMOVED;
|
||||
this->set_town_growth_tile(event.tile, TownGrowthTileState::RH_REMOVED);
|
||||
}
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseBuilt>([this] (const event::HouseBuilt &event) {
|
||||
this->events.listen<event::HouseBuilt>(event::Slot::GAME, [this] (const event::HouseBuilt &event) {
|
||||
event.town->cm.houses_constructing++;
|
||||
event.town->cm.real_population += event.house_spec->population;
|
||||
this->towns_growth_tiles[event.tile] = TownGrowthTileState::NEW_HOUSE;
|
||||
this->set_town_growth_tile(event.tile, TownGrowthTileState::NEW_HOUSE);
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseCleared>([this] (const event::HouseCleared &event) {
|
||||
this->events.listen<event::HouseCleared>(event::Slot::GAME, [this] (const event::HouseCleared &event) {
|
||||
if (!event.was_completed)
|
||||
event.town->cm.houses_constructing--;
|
||||
event.town->cm.real_population -= event.house_spec->population;
|
||||
});
|
||||
|
||||
this->events.listen<event::HouseCompleted>([this] (const event::HouseCompleted &event) {
|
||||
this->events.listen<event::HouseCompleted>(event::Slot::GAME, [this] (const event::HouseCompleted &event) {
|
||||
event.town->cm.houses_constructing--;
|
||||
});
|
||||
|
||||
this->events.listen<event::TownCachesRebuilt>([this] (const event::TownCachesRebuilt &event) {
|
||||
this->events.listen<event::TownCachesRebuilt>(event::Slot::GAME, [this] (const event::TownCachesRebuilt &event) {
|
||||
for (Town *town : Town::Iterate()) {
|
||||
town->cm.real_population = 0;
|
||||
town->cm.houses_constructing = 0;
|
||||
@@ -81,9 +81,13 @@ Game::Game() {
|
||||
}
|
||||
});
|
||||
|
||||
this->events.listen<event::CargoAccepted>([this] (const event::CargoAccepted &event) {
|
||||
this->events.listen<event::CargoAccepted>(event::Slot::GAME, [this] (const event::CargoAccepted &event) {
|
||||
event.company->cur_economy.cm.cargo_income[event.cargo_type] += event.profit;
|
||||
});
|
||||
}
|
||||
|
||||
void Game::set_town_growth_tile(TileIndex tile, TownGrowthTileState state) {
|
||||
if (this->towns_growth_tiles[tile] < state) this->towns_growth_tiles[tile] = state;
|
||||
}
|
||||
|
||||
} // namespace citymania
|
||||
@@ -1,5 +1,5 @@
|
||||
#ifndef CMEXT_GAME_HPP
|
||||
#define CMEXT_GAME_HPP
|
||||
#ifndef CM_GAME_HPP
|
||||
#define CM_GAME_HPP
|
||||
|
||||
#include "../town.h"
|
||||
|
||||
@@ -20,13 +20,14 @@ enum class TownGrowthTileState : uint8 {
|
||||
|
||||
class Game {
|
||||
public:
|
||||
event::Dispatcher events;
|
||||
|
||||
typedef std::map<TileIndex, TownGrowthTileState> TownsGrowthTilesIndex;
|
||||
TownsGrowthTilesIndex towns_growth_tiles_last_month;
|
||||
TownsGrowthTilesIndex towns_growth_tiles;
|
||||
|
||||
event::Dispatcher events;
|
||||
|
||||
Game();
|
||||
void set_town_growth_tile(TileIndex tile, TownGrowthTileState state);
|
||||
|
||||
TownGrowthTileState get_town_growth_tile(TileIndex tile) {
|
||||
auto a = this->towns_growth_tiles.find(tile);
|
||||
|
||||
@@ -16,7 +16,7 @@ void ResetGame() {
|
||||
}
|
||||
|
||||
void SwitchToMode(SwitchMode new_mode) {
|
||||
ResetGame();
|
||||
if (new_mode != SM_SAVE_GAME) ResetGame();
|
||||
}
|
||||
|
||||
void ToggleSmallMap() {
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
|
||||
#include "cm_bitstream.hpp"
|
||||
#include "cm_saveload.hpp"
|
||||
#include "cm_settings.hpp"
|
||||
#include "cm_game.hpp"
|
||||
#include "cm_main.hpp"
|
||||
|
||||
@@ -116,7 +117,8 @@ void CBController_saveload_encode(BitOStream &bs) {
|
||||
bs.WriteBytes(0 /* version */, 2);
|
||||
// Controller::saveload_encode(bs);
|
||||
bs.WriteBytes(0, 1);
|
||||
bs.WriteBytes(_settings_client.gui.cb_distance_check, 1);
|
||||
bs.WriteBytes(0, 1);
|
||||
// bs.WriteBytes(_settings_client.gui.cb_distance_check, 1);
|
||||
bs.WriteBytes(0, 1);
|
||||
bs.WriteBytes(0, 1);
|
||||
bs.WriteBytes(0, 1);
|
||||
@@ -124,43 +126,43 @@ void CBController_saveload_encode(BitOStream &bs) {
|
||||
bs.WriteBytes(0, 1);
|
||||
bs.WriteBytes(0, 1);
|
||||
std::vector<CargoID> cb_cargos;
|
||||
for(CargoID cargo = 0; cargo < NUM_CARGO; cargo++) {
|
||||
if (CB_GetReq(cargo) > 0)
|
||||
cb_cargos.push_back(cargo);
|
||||
}
|
||||
// for(CargoID cargo = 0; cargo < NUM_CARGO; cargo++) {
|
||||
// if (CB_GetReq(cargo) > 0)
|
||||
// cb_cargos.push_back(cargo);
|
||||
// }
|
||||
|
||||
for (auto cargo_id : cb_cargos) {
|
||||
// bs.WriteBytes(req.cargo_id, 1);
|
||||
// bs.WriteBytes(req.amount, 4);
|
||||
// bs.WriteBytes(req.from, 4);
|
||||
// bs.WriteBytes(req.decay, 1);
|
||||
bs.WriteBytes(cargo_id, 1);
|
||||
bs.WriteBytes(CB_GetReq(cargo_id), 4);
|
||||
bs.WriteBytes(CB_GetFrom(cargo_id), 4);
|
||||
bs.WriteBytes(CB_GetDecay(cargo_id), 1);
|
||||
}
|
||||
// uint16 cb_towns = 0;
|
||||
// ForEachCBTown([this, &cb_towns](Town *, Company *) { cb_towns++; });
|
||||
bs.WriteBytes(Town::GetNumItems(), 2);
|
||||
for (Town *t : Town::Iterate()) {
|
||||
auto &tcb = t->cb;
|
||||
bs.WriteBytes(t->index, 2);
|
||||
bs.WriteBytes(tcb.pax_delivered, 4);
|
||||
bs.WriteBytes(tcb.mail_delivered, 4);
|
||||
bs.WriteBytes(tcb.pax_delivered_last_month, 4);
|
||||
bs.WriteBytes(tcb.mail_delivered_last_month, 4);
|
||||
bs.WriteBytes((uint8)tcb.growth_state, 1);
|
||||
bs.WriteBytes(tcb.shrink_effeciency, 1);
|
||||
bs.WriteBytes(tcb.shrink_rate, 2);
|
||||
bs.WriteBytes(tcb.shrink_counter, 2);
|
||||
for (auto cargo_id : cb_cargos) {
|
||||
bs.WriteBytes(tcb.stored[cargo_id], 4);
|
||||
bs.WriteBytes(tcb.delivered[cargo_id], 4);
|
||||
bs.WriteBytes(tcb.required[cargo_id], 4);
|
||||
bs.WriteBytes(tcb.delivered_last_month[cargo_id], 4);
|
||||
bs.WriteBytes(tcb.required_last_month[cargo_id], 4);
|
||||
}
|
||||
}
|
||||
// for (auto cargo_id : cb_cargos) {
|
||||
// // bs.WriteBytes(req.cargo_id, 1);
|
||||
// // bs.WriteBytes(req.amount, 4);
|
||||
// // bs.WriteBytes(req.from, 4);
|
||||
// // bs.WriteBytes(req.decay, 1);
|
||||
// bs.WriteBytes(cargo_id, 1);
|
||||
// bs.WriteBytes(CB_GetReq(cargo_id), 4);
|
||||
// bs.WriteBytes(CB_GetFrom(cargo_id), 4);
|
||||
// bs.WriteBytes(CB_GetDecay(cargo_id), 1);
|
||||
// }
|
||||
// // uint16 cb_towns = 0;
|
||||
// // ForEachCBTown([this, &cb_towns](Town *, Company *) { cb_towns++; });
|
||||
// bs.WriteBytes(Town::GetNumItems(), 2);
|
||||
// for (Town *t : Town::Iterate()) {
|
||||
// auto &tcb = t->cb;
|
||||
// bs.WriteBytes(t->index, 2);
|
||||
// bs.WriteBytes(tcb.pax_delivered, 4);
|
||||
// bs.WriteBytes(tcb.mail_delivered, 4);
|
||||
// bs.WriteBytes(tcb.pax_delivered_last_month, 4);
|
||||
// bs.WriteBytes(tcb.mail_delivered_last_month, 4);
|
||||
// bs.WriteBytes((uint8)tcb.growth_state, 1);
|
||||
// bs.WriteBytes(tcb.shrink_effeciency, 1);
|
||||
// bs.WriteBytes(tcb.shrink_rate, 2);
|
||||
// bs.WriteBytes(tcb.shrink_counter, 2);
|
||||
// for (auto cargo_id : cb_cargos) {
|
||||
// bs.WriteBytes(tcb.stored[cargo_id], 4);
|
||||
// bs.WriteBytes(tcb.delivered[cargo_id], 4);
|
||||
// bs.WriteBytes(tcb.required[cargo_id], 4);
|
||||
// bs.WriteBytes(tcb.delivered_last_month[cargo_id], 4);
|
||||
// bs.WriteBytes(tcb.required_last_month[cargo_id], 4);
|
||||
// }
|
||||
// }
|
||||
}
|
||||
|
||||
bool CBController_saveload_decode(BitIStream &bs) {
|
||||
@@ -171,7 +173,8 @@ bool CBController_saveload_decode(BitIStream &bs) {
|
||||
// if (!Controller::saveload_decode(bs))
|
||||
// return false;
|
||||
bs.ReadBytes(1); /* _settings_game.citymania.cb.requirements_type */
|
||||
_settings_client.gui.cb_distance_check = bs.ReadBytes(1); /* _settings_game.citymania.cb.acceptance_range */
|
||||
bs.ReadBytes(1); /* _settings_game.citymania.cb.acceptance_range */
|
||||
// _settings_client.gui.cb_distance_check = bs.ReadBytes(1); /* _settings_game.citymania.cb.acceptance_range */
|
||||
bs.ReadBytes(1); /* _settings_game.citymania.cb.storage_size */
|
||||
bs.ReadBytes(1); /* _settings_game.citymania.cb.town_protection_range */
|
||||
bs.ReadBytes(2); /* _settings_game.citymania.cb.claim_max_houses */
|
||||
@@ -191,7 +194,7 @@ bool CBController_saveload_decode(BitIStream &bs) {
|
||||
auto required = bs.ReadBytes(4);
|
||||
auto from = bs.ReadBytes(4);
|
||||
auto decay = bs.ReadBytes(1);
|
||||
CB_SetRequirements(cargo_id, required, from, decay);
|
||||
// CB_SetRequirements(cargo_id, required, from, decay);
|
||||
// _settings_game.citymania.cb.requirements.push_back(CBRequirement(cargo_id, from, required, decay, i, ""));
|
||||
}
|
||||
|
||||
@@ -205,28 +208,54 @@ bool CBController_saveload_decode(BitIStream &bs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto &tcb = t->cb;
|
||||
tcb.pax_delivered = bs.ReadBytes(4);
|
||||
tcb.mail_delivered = bs.ReadBytes(4);
|
||||
tcb.pax_delivered_last_month = bs.ReadBytes(4);
|
||||
tcb.mail_delivered_last_month = bs.ReadBytes(4);
|
||||
tcb.growth_state = (TownGrowthState)bs.ReadBytes(1);
|
||||
tcb.shrink_effeciency = bs.ReadBytes(1);
|
||||
tcb.shrink_rate = bs.ReadBytes(2);
|
||||
tcb.shrink_counter = bs.ReadBytes(2);
|
||||
for (auto cargo_id : cb_cargos) {
|
||||
tcb.stored[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.delivered[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.required[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.delivered_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.required_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
}
|
||||
// auto &tcb = t->cb;
|
||||
// tcb.pax_delivered = bs.ReadBytes(4);
|
||||
// tcb.mail_delivered = bs.ReadBytes(4);
|
||||
// tcb.pax_delivered_last_month = bs.ReadBytes(4);
|
||||
// tcb.mail_delivered_last_month = bs.ReadBytes(4);
|
||||
// tcb.growth_state = (TownGrowthState)bs.ReadBytes(1);
|
||||
// tcb.shrink_effeciency = bs.ReadBytes(1);
|
||||
// tcb.shrink_rate = bs.ReadBytes(2);
|
||||
// tcb.shrink_counter = bs.ReadBytes(2);
|
||||
// for (auto cargo_id : cb_cargos) {
|
||||
// tcb.stored[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.delivered[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.required[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.delivered_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.required_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
// }
|
||||
};
|
||||
return true;
|
||||
}
|
||||
|
||||
uint8 _controller_type = 0;
|
||||
uint8 _game_type = 0;
|
||||
void EncodeSettings(BitOStream &bs, Settings &settings) {
|
||||
bs.WriteBytes(settings.max_players_in_company, 1);
|
||||
bs.WriteBytes(settings.destroyed_houses_per_month, 2);
|
||||
bs.WriteBytes(settings.game_length_years, 2);
|
||||
bs.WriteBytes(settings.protect_funded_industries, 1);
|
||||
bs.WriteBytes(settings.same_depot_sell_years, 2);
|
||||
bs.WriteBytes(settings.economy.cashback_for_extra_land_clear, 1);
|
||||
bs.WriteBytes(settings.economy.cashback_for_bridges_and_tunnels, 1);
|
||||
bs.WriteBytes(settings.economy.cashback_for_foundations, 1);
|
||||
bs.WriteBytes(settings.limits.max_airports, 2);
|
||||
bs.WriteBytes(settings.limits.disable_canals, 1);
|
||||
bs.WriteBytes(settings.limits.min_distance_between_docks, 2);
|
||||
}
|
||||
|
||||
void DecodeSettings(BitIStream &bs, Settings &settings) {
|
||||
settings.max_players_in_company = bs.ReadBytes(1);
|
||||
settings.destroyed_houses_per_month = bs.ReadBytes(2);
|
||||
settings.game_length_years = bs.ReadBytes(2);
|
||||
settings.protect_funded_industries = bs.ReadBytes(1);
|
||||
settings.same_depot_sell_years = bs.ReadBytes(2);
|
||||
settings.economy.cashback_for_extra_land_clear = bs.ReadBytes(1);
|
||||
settings.economy.cashback_for_bridges_and_tunnels = bs.ReadBytes(1);
|
||||
settings.economy.cashback_for_foundations = bs.ReadBytes(1);
|
||||
settings.limits.max_airports = bs.ReadBytes(2);
|
||||
settings.limits.disable_canals = bs.ReadBytes(1);
|
||||
settings.limits.min_distance_between_docks = bs.ReadBytes(2);
|
||||
}
|
||||
|
||||
uint16 _last_client_version = 1512;
|
||||
|
||||
static u8vector EncodeData() {
|
||||
@@ -234,37 +263,39 @@ static u8vector EncodeData() {
|
||||
bs.Reserve(1000);
|
||||
bs.WriteBytes(SAVEGAME_DATA_FORMAT_VERSION, 2);
|
||||
bs.WriteBytes(_last_client_version, 2);
|
||||
bs.WriteBytes(_controller_type, 1);
|
||||
bs.WriteBytes(_settings_game.citymania.controller_type, 1);
|
||||
bs.WriteBytes(_date, 4); // Just in case we'll need to detect that game
|
||||
bs.WriteBytes(_date_fract, 1); // was saved by unmodified client
|
||||
bs.WriteBytes(_game_type, 1);
|
||||
bs.WriteBytes(_settings_game.citymania.game_type, 1);
|
||||
bs.WriteBytes(0, 3); // Reserved
|
||||
bs.WriteBytes(0, 4); // Reserved
|
||||
|
||||
EncodeSettings(bs, _settings_game.citymania);
|
||||
EncodeCompanies(bs);
|
||||
EncodeTowns(bs);
|
||||
EncodeTownsGrowthTiles(bs, _game->towns_growth_tiles);
|
||||
EncodeTownsGrowthTiles(bs, _game->towns_growth_tiles_last_month);
|
||||
if (_controller_type == 4)
|
||||
if (_settings_game.citymania.controller_type == 4)
|
||||
CBController_saveload_encode(bs);
|
||||
|
||||
return bs.GetVector();
|
||||
}
|
||||
|
||||
static void DecodeDataV2(BitIStream &bs) {
|
||||
DecodeSettings(bs, _settings_game.citymania);
|
||||
DecodeCompanies(bs);
|
||||
DecodeTowns(bs);
|
||||
DecodeTownsGrowthTiles(bs, _game->towns_growth_tiles);
|
||||
DecodeTownsGrowthTiles(bs, _game->towns_growth_tiles_last_month);
|
||||
if (_controller_type == 4) CBController_saveload_decode(bs);
|
||||
if (_settings_game.citymania.controller_type == 4) CBController_saveload_decode(bs);
|
||||
}
|
||||
|
||||
static void DecodeTownsCargoV1(BitIStream &bs)
|
||||
{
|
||||
CB_SetStorage(bs.ReadBytes(1));
|
||||
_settings_client.gui.cb_distance_check = bs.ReadBytes(1);
|
||||
bs.ReadBytes(1);bs.ReadBytes(1);
|
||||
// CB_SetStorage(bs.ReadBytes(1));
|
||||
// _settings_client.gui.cb_distance_check = bs.ReadBytes(1);
|
||||
uint n_cb_cargos = bs.ReadBytes(1);
|
||||
CB_ResetRequirements();
|
||||
// CB_ResetRequirements();
|
||||
std::vector<CargoID> cb_cargos;
|
||||
for (uint i = 0; i < n_cb_cargos; i++) {
|
||||
uint cargo = bs.ReadBytes(1);
|
||||
@@ -276,7 +307,7 @@ static void DecodeTownsCargoV1(BitIStream &bs)
|
||||
uint req = bs.ReadBytes(4);
|
||||
uint from = bs.ReadBytes(4);
|
||||
uint decay = bs.ReadBytes(1);
|
||||
CB_SetRequirements(cargo, req, from, decay);
|
||||
// CB_SetRequirements(cargo, req, from, decay);
|
||||
}
|
||||
Town *t;
|
||||
uint n_affected_towns = bs.ReadBytes(2);
|
||||
@@ -287,21 +318,21 @@ static void DecodeTownsCargoV1(BitIStream &bs)
|
||||
DEBUG(sl, 0, "Invalid TownID in CB towns cargo data (%u)", town_id);
|
||||
return;
|
||||
}
|
||||
auto &tcb = t->cb;
|
||||
for (auto cargo_id : cb_cargos) {
|
||||
tcb.stored[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.delivered_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
tcb.delivered[cargo_id] = bs.ReadBytes(4);
|
||||
bs.ReadBytes(1); /* delivered enough */
|
||||
// auto &tcb = t->cb;
|
||||
// for (auto cargo_id : cb_cargos) {
|
||||
// tcb.stored[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.delivered_last_month[cargo_id] = bs.ReadBytes(4);
|
||||
// tcb.delivered[cargo_id] = bs.ReadBytes(4);
|
||||
// bs.ReadBytes(1); /* delivered enough */
|
||||
|
||||
tcb.required[cargo_id] = 0;
|
||||
tcb.required_last_month[cargo_id] = 0;
|
||||
}
|
||||
// tcb.required[cargo_id] = 0;
|
||||
// tcb.required_last_month[cargo_id] = 0;
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
static void DecodeDataV1(BitIStream &bs) {
|
||||
if (_controller_type != 0) DecodeTownsCargoV1(bs);
|
||||
if (_settings_game.citymania.controller_type != 0) DecodeTownsCargoV1(bs);
|
||||
for (Town *t : Town::Iterate()) {
|
||||
t->cm.growing_by_chance = bs.ReadBytes(1);
|
||||
t->cm.houses_reconstructed_this_month = bs.ReadBytes(2);
|
||||
@@ -348,15 +379,15 @@ static void DecodeData(u8vector &data) {
|
||||
}
|
||||
DEBUG(sl, 2, "CityMania savegame data version %u", version);
|
||||
_last_client_version = bs.ReadBytes(2);
|
||||
_controller_type = bs.ReadBytes(1);
|
||||
if (version <= 1) _controller_type = (_controller_type ? 4 : 0);
|
||||
_settings_game.citymania.controller_type = bs.ReadBytes(1);
|
||||
if (version <= 1) _settings_game.citymania.controller_type = (_settings_game.citymania.controller_type ? 4 : 0);
|
||||
int32 date = bs.ReadBytes(4);
|
||||
uint32 date_fract = bs.ReadBytes(1);
|
||||
if (date != _date || date_fract != _date_fract) {
|
||||
DEBUG(sl, 0, "Savegame was run in unmodified client, extra save data "
|
||||
"preserved, but may not be accurate");
|
||||
}
|
||||
_game_type = bs.ReadBytes(1);
|
||||
_settings_game.citymania.game_type = bs.ReadBytes(1);
|
||||
bs.ReadBytes(3); // reserved
|
||||
bs.ReadBytes(4); // reserved
|
||||
if (version == 1) DecodeDataV1(bs);
|
||||
|
||||
69
src/citymania/cm_settings.hpp
Normal file
69
src/citymania/cm_settings.hpp
Normal file
@@ -0,0 +1,69 @@
|
||||
#ifndef CM_SETTINGS_HPP
|
||||
#define CM_SETTINGS_HPP
|
||||
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
// #include "types.hpp"
|
||||
|
||||
namespace citymania {
|
||||
|
||||
class CBRequirement {
|
||||
public:
|
||||
CargoID cargo_id;
|
||||
uint32 from;
|
||||
uint32 amount;
|
||||
uint8 decay;
|
||||
uint8 index;
|
||||
std::string name;
|
||||
bool has_storage;
|
||||
|
||||
static CBRequirement Parse(const char *name, const char *value, uint8 index);
|
||||
|
||||
CBRequirement(CargoID cargo_id, uint32 from, uint32 amount, uint8 decay,
|
||||
uint8 index, std::string name)
|
||||
:cargo_id{cargo_id}, from{from}, amount{amount}, decay{decay},
|
||||
index{index}, name{name}, has_storage{decay < 100} {}
|
||||
};
|
||||
|
||||
struct EconomySettings {
|
||||
bool cashback_for_extra_land_clear;
|
||||
bool cashback_for_bridges_and_tunnels;
|
||||
bool cashback_for_foundations;
|
||||
};
|
||||
|
||||
struct LimitsSettings {
|
||||
uint16 max_airports; ///< maximum number of airports per company, 0=unlimited
|
||||
bool disable_canals;
|
||||
uint16 min_distance_between_docks; ///< docks can be build only x tiles apart another, 0=disable check
|
||||
};
|
||||
|
||||
|
||||
struct CBSettings {
|
||||
uint8 requirements_type; // 0 - regular 1 - income-based requirements (new cb only)
|
||||
std::vector<CBRequirement> requirements;
|
||||
uint8 acceptance_range; // How far can station be to count towards requiremnts
|
||||
uint8 storage_size; // cargo storage multiplier (x * monthly requirements)
|
||||
uint8 town_protection_range; // Claimed town protection range (square from centre), overlaped with tz0
|
||||
uint16 claim_max_houses; // Max amount of houses claimable town can have
|
||||
bool smooth_growth_rate; // Calculate growth rate precisely instead of rounding to 50 houses and allow going below 70 ticks (default max)
|
||||
bool allow_negative_growth; // Make town shrink (with the same speed as growth) if requirements aren't satisfied
|
||||
};
|
||||
|
||||
struct Settings {
|
||||
CBSettings cb;
|
||||
EconomySettings economy;
|
||||
LimitsSettings limits;
|
||||
|
||||
uint8 game_type; // GameType
|
||||
uint8 controller_type; // ControllerType
|
||||
uint8 max_players_in_company;
|
||||
uint16 destroyed_houses_per_month; // max amount of houses a company can destroy per month
|
||||
uint16 game_length_years; // game length in years(0 = disabled)
|
||||
bool protect_funded_industries;
|
||||
uint16 same_depot_sell_years; // can only sell vehicles in the same place (20 tiles radius) for first x yearss of its lifetime (0 = disabled)
|
||||
};
|
||||
|
||||
}; // namespace citymania
|
||||
|
||||
#endif
|
||||
@@ -18,7 +18,7 @@ public:
|
||||
bool is_scored; ///< whether company is eligible for scoring
|
||||
};
|
||||
|
||||
} // namespace ext
|
||||
} // namespace citymania
|
||||
|
||||
} // namespace citymania
|
||||
|
||||
|
||||
@@ -20,6 +20,8 @@
|
||||
#include "zoom_type.h"
|
||||
#include "openttd.h"
|
||||
|
||||
#include "citymania/cm_settings.hpp"
|
||||
|
||||
|
||||
/** Settings profiles and highscore tables. */
|
||||
enum SettingsProfile {
|
||||
@@ -585,6 +587,8 @@ struct GameSettings {
|
||||
LinkGraphSettings linkgraph; ///< settings for link graph calculations
|
||||
StationSettings station; ///< settings related to station management
|
||||
LocaleSettings locale; ///< settings related to used currency/unit system in the current game
|
||||
|
||||
citymania::Settings citymania;
|
||||
};
|
||||
|
||||
/** All settings that are only important for the local client. */
|
||||
|
||||
@@ -258,7 +258,7 @@ enum TownGrowthResult {
|
||||
// GROWTH_SEARCH_RUNNING >= 1
|
||||
};
|
||||
|
||||
static bool BuildTownHouse(Town *t, TileIndex tile);
|
||||
static bool BuildTownHouse(Town *t, TileIndex tile, bool is_rebuilding = false);
|
||||
static Town *CreateRandomTown(uint attempts, uint32 townnameparts, TownSize size, bool city, TownLayout layout);
|
||||
|
||||
static void TownDrawHouseLift(const TileInfo *ti)
|
||||
@@ -537,7 +537,7 @@ static void MakeSingleHouseBigger(TileIndex tile)
|
||||
ResetHouseAge(tile);
|
||||
|
||||
if (hs->building_flags & BUILDING_HAS_1_TILE)
|
||||
citymania::Emit(citymania::event::HouseCompleted{town, tile, hs});
|
||||
citymania::Emit(citymania::event::HouseCompleted{town, tile, house_id, hs});
|
||||
}
|
||||
MarkTileDirtyByTile(tile);
|
||||
}
|
||||
@@ -673,7 +673,7 @@ static void TileLoop_Town(TileIndex tile)
|
||||
|
||||
/* Rebuild with another house? */
|
||||
bool rebuild_res = false;
|
||||
if (GB(r, 24, 8) >= 12) rebuild_res = BuildTownHouse(t, tile);
|
||||
if (GB(r, 24, 8) >= 12) rebuild_res = BuildTownHouse(t, tile, true);
|
||||
citymania::Emit(citymania::event::HouseRebuilt{t, tile, rebuild_res});
|
||||
}
|
||||
|
||||
@@ -2745,7 +2745,7 @@ static bool CheckTownBuild2x2House(TileIndex *tile, Town *t, int maxz, bool nosl
|
||||
* @param tile where the house will be built
|
||||
* @return false iff no house can be built at this tile
|
||||
*/
|
||||
static bool BuildTownHouse(Town *t, TileIndex tile)
|
||||
static bool BuildTownHouse(Town *t, TileIndex tile, bool is_rebuilding)
|
||||
{
|
||||
/* forbidden building here by town layout */
|
||||
if (!TownLayoutAllowsHouseHere(t, tile)) return false;
|
||||
@@ -2894,8 +2894,10 @@ static bool BuildTownHouse(Town *t, TileIndex tile)
|
||||
UpdateTownGrowthRate(t);
|
||||
UpdateTownCargoes(t, tile);
|
||||
|
||||
citymania::Emit(citymania::event::HouseBuilt{t, tile, hs});
|
||||
if (completed) citymania::Emit(citymania::event::HouseCompleted{t, tile, hs});
|
||||
if (!_generating_world) {
|
||||
citymania::Emit(citymania::event::HouseBuilt{t, tile, house, hs, is_rebuilding});
|
||||
if (completed) citymania::Emit(citymania::event::HouseCompleted{t, tile, house, hs});
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -2986,7 +2988,7 @@ void ClearTownHouse(Town *t, TileIndex tile)
|
||||
/* Update cargo acceptance. */
|
||||
UpdateTownCargoes(t, tile);
|
||||
|
||||
citymania::Emit(citymania::event::HouseCleared{t, tile, hs, is_completed});
|
||||
citymania::Emit(citymania::event::HouseCleared{t, tile, house, hs, is_completed});
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
Reference in New Issue
Block a user