50#include "table/strings.h"
67std::span<const GRFFile> GetAllGRFFiles()
92void GrfMsgI(
int severity,
const std::string &msg)
94 if (_cur_gps.grfconfig ==
nullptr) {
95 Debug(grf, severity,
"{}", msg);
97 Debug(grf, severity,
"[{}:{}] {}", _cur_gps.grfconfig->filename, _cur_gps.nfo_line, msg);
108 auto it = std::ranges::find(
_grf_files, grfid, &GRFFile::grfid);
120 auto it = std::ranges::find(
_grf_files, filename, &GRFFile::filename);
143 if (config !=
nullptr) {
146 config = _cur_gps.grfconfig;
147 file = _cur_gps.grffile;
152 if (config == _cur_gps.grfconfig) _cur_gps.skip_sprites = -1;
154 if (message == STR_NULL)
return nullptr;
157 if (it == std::end(config->
errors)) {
158 it = config->
errors.emplace(it, STR_NEWGRF_ERROR_MSG_FATAL, _cur_gps.nfo_line, message);
160 if (config == _cur_gps.grfconfig) it->param_value[0] = _cur_gps.nfo_line;
176 error->
data = _cur_gps.grfconfig->GetName();
179static std::map<GrfID, GrfID> _grf_id_overrides;
188 if (target_grfid.
Empty()) {
189 _grf_id_overrides.erase(source_grfid);
190 GrfMsg(5,
"SetNewGRFOverride: Removed override of {}",
FormatArrayAsHex(source_grfid));
192 _grf_id_overrides[source_grfid] = target_grfid;
203 auto found = _grf_id_overrides.find(_cur_gps.grffile->grfid);
204 if (found != std::end(_grf_id_overrides)) {
206 if (grffile !=
nullptr)
return grffile;
226 scope_grfid = file->grfid;
227 if (
auto it = _grf_id_overrides.find(file->grfid); it != std::end(_grf_id_overrides)) {
228 scope_grfid = it->second;
230 if (grf_match ==
nullptr) {
238 EngineID engine = _engine_mngr.GetID(type, internal_id, scope_grfid);
239 if (engine != EngineID::Invalid()) {
249 EngineID engine = _engine_mngr.UseUnreservedID(type, internal_id, scope_grfid, static_access);
250 if (engine != EngineID::Invalid()) {
255 GrfMsg(5,
"Replaced engine at index {} for GRFID {}, type {}, index {}", e->index,
FormatArrayAsHex(file->grfid), type, internal_id);
261 if (static_access)
return nullptr;
264 GrfMsg(0,
"Can't allocate any more engines");
275 _engine_mngr.SetID(type, internal_id, scope_grfid, std::min<uint8_t>(internal_id,
GetOriginalEngineCount(type)), e->index);
282 _gted[e->index].railtypelabels.clear();
286 GrfMsg(5,
"Created new engine at index {} for GRFID {}, type {}, index {}", e->index,
FormatArrayAsHex(file->grfid), type, internal_id);
305 scope_grfid = file->grfid;
306 if (
auto it = _grf_id_overrides.find(file->grfid); it != std::end(_grf_id_overrides)) {
307 scope_grfid = it->second;
311 return _engine_mngr.GetID(type, internal_id, scope_grfid);
342 if (base_pointer == 0) {
347 static const uint32_t start = 0x4B34;
348 static const uint32_t size = 6;
350 if (base_pointer < start || (base_pointer - start) % size != 0 || (base_pointer - start) / size >=
to_underlying(
Price::End)) {
351 GrfMsg(1,
"{}: Unsupported running cost base 0x{:04X}, ignoring", error_location, base_pointer);
355 *index = (
Price)((base_pointer - start) / size);
367 if (grffile ==
nullptr)
return nullptr;
370 if (it == std::end(grffile->
language_map))
return nullptr;
384 _cur_gps.skip_sprites = -1;
390 _cur_gps.grfconfig =
nullptr;
391 _cur_gps.grffile =
nullptr;
408extern void ResetCallbacks(
bool final);
409extern void ResetGRM();
417 CleanUpGRFTownNames();
438 _gted[e->index].railtypelabels.clear();
501 _grf_id_overrides.clear();
503 InitializeSoundPool();
504 _spritegroup_pool.CleanPool();
505 ResetCallbacks(
false);
514 _engine_mngr.ResetToDefaultMapping();
515 _house_mngr.ResetMapping();
516 _industry_mngr.ResetMapping();
517 _industile_mngr.ResetMapping();
518 _airport_mngr.ResetMapping();
519 _airporttile_mngr.ResetMapping();
545 _cur_gps.grffile->cargo_map.fill(UINT8_MAX);
552 if (idx >= 0) _cur_gps.grffile->cargo_map[cs->Index()] = idx;
563 if (newfile !=
nullptr) {
565 _cur_gps.grffile = newfile;
570 _cur_gps.grffile = &
_grf_files.emplace_back(config);
605 this->param = config.
param;
611GRFFile::~GRFFile() =
default;
621 CargoType cargo_type = GetCargoTypeByLabel(label);
622 if (cargo_type != INVALID_CARGO)
return label;
642 default: NOT_REACHED();
647 return std::visit(visitor{}, label);
663 bool only_defaultcargo;
671 if (
_gted[engine].defaultcargo_grf ==
nullptr) {
678 static const struct DefaultRefitMasks {
683 } _default_refit_masks[] = {
708 _gted[engine].cargo_disallowed = {};
709 }
else if (label == CT_OIL) {
712 _gted[engine].cargo_disallowed = {};
727 _gted[engine].cargo_disallowed = {};
731 for (
const auto &drm : _default_refit_masks) {
732 if (!drm.climate.Test(
_settings_game.game_creation.landscape))
continue;
733 if (drm.cargo_label != label)
continue;
735 _gted[engine].cargo_allowed = drm.cargo_allowed;
736 _gted[engine].cargo_disallowed = drm.cargo_disallowed;
741 _gted[engine].ctt_exclude_mask = original_known_cargoes;
744 _gted[engine].UpdateRefittability(
_gted[engine].cargo_allowed.Any());
759 if (
_gted[engine].cargo_allowed.Any()) {
762 if (cs->classes.Any(
_gted[engine].cargo_allowed) && cs->classes.All(
_gted[engine].cargo_allowed_required)) mask.
Set(cs->Index());
763 if (cs->classes.Any(
_gted[engine].cargo_disallowed)) not_mask.
Set(cs->Index());
768 ei->refit_mask = mask.
Reset(not_mask).Flip(xor_mask).Reset(invalid_mask);
771 ei->refit_mask.
Set(
_gted[engine].ctt_include_mask);
772 ei->refit_mask.
Reset(
_gted[engine].ctt_exclude_mask);
776 if (file ==
nullptr) file = e->GetGRF();
779 uint8_t local_slot = file->
cargo_map[cs->Index()];
785 case 1: ei->refit_mask.
Set(cs->Index());
break;
786 case 2: ei->refit_mask.
Reset(cs->Index());
break;
800 ei->cargo_type = INVALID_CARGO;
808 if (file ==
nullptr) file = e->GetGRF();
809 if (file !=
nullptr && file->grf_version >= 8 && !file->
cargo_list.empty()) {
811 uint8_t best_local_slot = UINT8_MAX;
812 for (
CargoType cargo_type : ei->refit_mask) {
813 uint8_t local_slot = file->
cargo_map[cargo_type];
814 if (local_slot < best_local_slot) {
815 best_local_slot = local_slot;
816 ei->cargo_type = cargo_type;
823 ei->cargo_type = *ei->refit_mask.
begin();
838 ei->refit_mask.
Reset();
858 if (e->GetGRF() ==
nullptr) {
859 auto found = std::ranges::find(_engine_mngr.mappings[e->type], e->index, &EngineIDMapping::engine);
860 if (found == std::end(_engine_mngr.mappings[e->type]) || found->grfid !=
INVALID_GRFID || found->internal_id != found->substitute_id) {
861 e->info.string_id = STR_NEWGRF_INVALID_ENGINE;
866 if (e->info.variant_id != EngineID::Invalid()) {
867 e->info.variant_id =
GetNewEngineID(e->grf_prop.grffile, e->type, e->info.variant_id.base());
870 if (!e->info.climates.Test(
_settings_game.game_creation.landscape))
continue;
904 default: NOT_REACHED();
915 EngineID parent = e->info.variant_id;
917 bool update_slow =
false;
918 while (parent != EngineID::Invalid()) {
920 if (update_slow) parent_slow =
Engine::Get(parent_slow)->info.variant_id;
921 update_slow = !update_slow;
922 if (parent != e->index && parent != parent_slow)
continue;
925 e->info.variant_id = EngineID::Invalid();
927 GrfMsg(1,
"FinaliseEngineArray: Variant of engine {:x} in '{}' loops back on itself", e->grf_prop.local_id, e->GetGRF()->filename);
931 if (e->info.variant_id != EngineID::Invalid()) {
945 }
else if (cs.label == CT_MAIL) {
952 cs.name = cs.name_single = cs.units_volume = STR_NEWGRF_INVALID_CARGO;
953 cs.quantifier = STR_NEWGRF_INVALID_CARGO_QUANTITY;
954 cs.abbrev = STR_NEWGRF_INVALID_CARGO_ABBREV;
978 if (!filename.empty())
Debug(grf, 1,
"FinaliseHouseArray: {} defines house {} as multitile, but no suitable tiles follow. Disabling house.", filename, hs.
grf_prop.
local_id);
988 if (!filename.empty())
Debug(grf, 1,
"FinaliseHouseArray: {} defines multitile house {} with non-zero population on additional tiles. Disabling house.", filename, hs.
grf_prop.
local_id);
996 Debug(grf, 1,
"FinaliseHouseArray: {} defines house {} with different house size then it's substitute type. Disabling house.", filename, hs.
grf_prop.
local_id);
1003 if (!filename.empty())
Debug(grf, 1,
"FinaliseHouseArray: {} defines house {} without a size but marked it as available. Disabling house.", filename, hs.
grf_prop.
local_id);
1021 if (!hs.enabled)
continue;
1022 if (!hs.building_availability.All(bitmask))
continue;
1023 if (hs.min_year < min_year) min_year = hs.min_year;
1026 if (min_year == 0)
return;
1029 if (!hs.enabled)
continue;
1030 if (!hs.building_availability.All(bitmask))
continue;
1053 if (file.housespec.empty())
continue;
1055 size_t num_houses = file.housespec.size();
1056 for (
size_t i = 0; i < num_houses; i++) {
1057 auto &hs = file.housespec[i];
1059 if (hs ==
nullptr)
continue;
1061 const HouseSpec *next1 = (i + 1 < num_houses ? file.housespec[i + 1].get() :
nullptr);
1062 const HouseSpec *next2 = (i + 2 < num_houses ? file.housespec[i + 2].get() :
nullptr);
1063 const HouseSpec *next3 = (i + 3 < num_houses ? file.housespec[i + 3].get() :
nullptr);
1067 _house_mngr.SetEntitySpec(std::move(*hs));
1071 file.housespec.clear();
1072 file.housespec.shrink_to_fit();
1103 for (
HouseZone climate : climate_mask) {
1118 for (
auto &indsp : file.industryspec) {
1119 if (indsp ==
nullptr || !indsp->enabled)
continue;
1121 _industry_mngr.SetEntitySpec(std::move(*indsp));
1124 for (
auto &indtsp : file.indtspec) {
1125 if (indtsp !=
nullptr) {
1126 _industile_mngr.SetEntitySpec(std::move(*indtsp));
1131 file.industryspec.clear();
1132 file.industryspec.shrink_to_fit();
1133 file.indtspec.clear();
1134 file.indtspec.shrink_to_fit();
1137 for (
auto &indsp : _industry_specs) {
1138 if (indsp.enabled && indsp.grf_prop.HasGrfFile()) {
1139 for (
auto &conflicting : indsp.conflicting) {
1143 if (!indsp.enabled) {
1144 indsp.name = STR_NEWGRF_INVALID_INDUSTRYTYPE;
1148 for (
size_t i = 0; i < std::size(indsp.produced_cargo_label); ++i) {
1151 for (
size_t i = 0; i < std::size(indsp.accepts_cargo_label); ++i) {
1156 for (
auto &indtsp : _industry_tile_specs) {
1158 for (
size_t i = 0; i < std::size(indtsp.accepts_cargo_label); ++i) {
1172 for (
auto &objectspec : file.objectspec) {
1173 if (objectspec !=
nullptr && objectspec->grf_prop.HasGrfFile() && objectspec->IsEnabled()) {
1174 _object_mngr.SetEntitySpec(std::move(*objectspec));
1179 file.objectspec.clear();
1180 file.objectspec.shrink_to_fit();
1194 for (
auto &as : file.airportspec) {
1195 if (as !=
nullptr && as->enabled) {
1196 _airport_mngr.SetEntitySpec(std::move(*as));
1200 for (
auto &ats : file.airtspec) {
1201 if (ats !=
nullptr && ats->enabled) {
1202 _airporttile_mngr.SetEntitySpec(std::move(*ats));
1207 file.airportspec.clear();
1208 file.airportspec.shrink_to_fit();
1209 file.airtspec.clear();
1210 file.airtspec.shrink_to_fit();
1216 template <u
int8_t TAction>
1226 default: NOT_REACHED();
1231 static constexpr Invoker funcs[] = {
1232 Invoke<0x00>, Invoke<0x01>, Invoke<0x02>, Invoke<0x03>, Invoke<0x04>, Invoke<0x05>, Invoke<0x06>, Invoke<0x07>,
1233 Invoke<0x08>, Invoke<0x09>, Invoke<0x0A>, Invoke<0x0B>, Invoke<0x0C>, Invoke<0x0D>, Invoke<0x0E>, Invoke<0x0F>,
1234 Invoke<0x10>, Invoke<0x11>, Invoke<0x12>, Invoke<0x13>, Invoke<0x14>,
1239 Invoker func = action < std::size(funcs) ? funcs[action] :
nullptr;
1240 if (func ==
nullptr) {
1241 GrfMsg(7,
"DecodeSpecialSprite: Skipping unknown action 0x{:02X}", action);
1243 GrfMsg(7,
"DecodeSpecialSprite: Handling action 0x{:02X} in stage {}", action, stage);
1258 auto it = _grf_line_to_action6_sprite_override.find({_cur_gps.grfconfig->ident.grfid, _cur_gps.nfo_line});
1259 if (it == _grf_line_to_action6_sprite_override.end()) {
1263 _cur_gps.file->ReadBlock(buf, num);
1266 buf = it->second.data();
1267 assert(it->second.size() == num);
1268 GrfMsg(7,
"DecodeSpecialSprite: Using preloaded pseudo sprite data");
1271 _cur_gps.file->SeekTo(num, SEEK_CUR);
1277 uint8_t action = br.ReadByte();
1279 if (action == 0xFF) {
1280 GrfMsg(2,
"DecodeSpecialSprite: Unexpected data block, skipping");
1281 }
else if (action == 0xFE) {
1282 GrfMsg(2,
"DecodeSpecialSprite: Unexpected import block, skipping");
1284 InvokeGrfActionHandler::Invoke(action, stage, br);
1287 GrfMsg(1,
"DecodeSpecialSprite: Tried to read past end of pseudo-sprite data");
1303 Debug(grf, 2,
"LoadNewGRFFile: Reading NewGRF-file '{}'", config.
filename);
1306 if (grf_container_version == 0) {
1307 Debug(grf, 7,
"LoadNewGRFFile: Custom .grf has invalid format");
1317 if (grf_container_version >= 2) file.
ReadDword();
1320 if (grf_container_version >= 2) {
1322 uint8_t compression = file.
ReadByte();
1323 if (compression != 0) {
1324 Debug(grf, 7,
"LoadNewGRFFile: Unsupported compression format");
1333 if (num == 4 && file.
ReadByte() == 0xFF) {
1336 Debug(grf, 7,
"LoadNewGRFFile: Custom .grf has invalid format");
1340 _cur_gps.ClearDataForNextFile();
1344 while ((num = (grf_container_version >= 2 ? file.
ReadDword() : file.
ReadWord())) != 0) {
1346 _cur_gps.nfo_line++;
1349 if (_cur_gps.skip_sprites == 0) {
1351 if (num > 1024 * 1024) {
1352 GrfMsg(0,
"LoadNewGRFFile: Unexpectedly large sprite, disabling");
1353 DisableGrf(STR_NEWGRF_ERROR_UNEXPECTED_SPRITE);
1357 DecodeSpecialSprite(allocator, num, stage);
1360 if (_cur_gps.skip_sprites == -1)
break;
1367 if (_cur_gps.skip_sprites == 0) {
1368 GrfMsg(0,
"LoadNewGRFFile: Unexpected sprite, disabling");
1369 DisableGrf(STR_NEWGRF_ERROR_UNEXPECTED_SPRITE);
1373 if (grf_container_version >= 2 && type == 0xFD) {
1382 if (_cur_gps.skip_sprites > 0) _cur_gps.skip_sprites--;
1396 const std::string &filename = config.
filename;
1409 if (_cur_gps.grffile ==
nullptr) UserError(
"File '{}' lost in cache.\n", filename);
1416 SpriteFile temporarySpriteFile(filename, subdir, needs_palette_remap);
1489 std::vector<int> grf_overrides(num_grfs, -1);
1490 for (
int i = 0; i < num_grfs; i++) {
1492 auto it = _grf_id_overrides.find(source.grfid);
1493 if (it == std::end(_grf_id_overrides))
continue;
1494 GrfID override_grfid = it->second;
1496 auto dest = std::ranges::find(
_grf_files, override_grfid, &GRFFile::grfid);
1499 grf_overrides[i] =
static_cast<int>(std::ranges::distance(std::begin(
_grf_files), dest));
1500 assert(grf_overrides[i] >= 0);
1504 for (
int i = 0; i < num_grfs; i++) {
1505 if (grf_overrides[i] < 0 || grf_overrides[i] >= i)
continue;
1515 if (!features.
Test(_price_base_specs[p].grf_feature) || source.
price_base_multipliers[p] == INVALID_PRICE_MODIFIER)
continue;
1516 Debug(grf, 3,
"'{}' overrides price base multiplier {} of '{}'", source.filename, p, dest.filename);
1522 for (
int i = num_grfs - 1; i >= 0; i--) {
1523 if (grf_overrides[i] < 0 || grf_overrides[i] <= i)
continue;
1534 Debug(grf, 3,
"Price base multiplier {} from '{}' propagated to '{}'", p, source.filename, dest.filename);
1540 for (
int i = 0; i < num_grfs; i++) {
1541 if (grf_overrides[i] < 0)
continue;
1550 if (!features.
Test(_price_base_specs[p].grf_feature))
continue;
1552 Debug(grf, 3,
"Price base multiplier {} from '{}' propagated to '{}'", p, dest.filename, source.filename);
1560 if (file.grf_version >= 8)
continue;
1561 PriceMultipliers &price_base_multipliers = file.price_base_multipliers;
1563 Price fallback_price = _price_base_specs[p].fallback_price;
1564 if (fallback_price !=
Price::Invalid && price_base_multipliers[p] == INVALID_PRICE_MODIFIER) {
1567 price_base_multipliers[p] = price_base_multipliers[fallback_price];
1574 PriceMultipliers &price_base_multipliers = file.price_base_multipliers;
1576 if (price_base_multipliers[p] == INVALID_PRICE_MODIFIER) {
1578 price_base_multipliers[p] = 0;
1580 if (!file.grf_features.Test(_price_base_specs[p].grf_feature)) {
1583 Debug(grf, 3,
"'{}' sets global price base multiplier {}", file.filename, p);
1585 price_base_multipliers[p] = 0;
1587 Debug(grf, 3,
"'{}' sets local price base multiplier {}", file.filename, p);
1594template <
typename T>
1597 for (
auto &spec : specs) {
1598 if (spec ==
nullptr)
continue;
1599 spec->badges.push_back(badge.
index);
1609 if (badge ==
nullptr)
continue;
1612 if (e->grf_prop.grffile != &file)
continue;
1613 e->badges.push_back(badge->
index);
1637 ResetCallbacks(
true);
1642 _grf_line_to_action6_sprite_override.clear();
1699 if (
_gted[e->index].rv_max_speed != 0) {
1706 const GRFFile *file = e->GetGRF();
1707 if (file ==
nullptr ||
_gted[e->index].roadtramtype == 0) {
1713 _gted[e->index].roadtramtype--;
1716 if (
_gted[e->index].roadtramtype < list->size())
1718 RoadTypeLabel rtl = (*list)[
_gted[e->index].roadtramtype];
1727 e->info.climates = {};
1732 for (RailTypeLabel label :
_gted[e->index].railtypelabels) {
1737 if (railtypes.
Any()) {
1742 e->info.climates = {};
1752 _grm_sprites.clear();
1805 _cur_gps.spriteid = load_index;
1818 static const std::pair<GrfID, GrfID> default_grf_overrides[] = {
1819 {
GrfID{
"\x44\x44\x22\x02"},
GrfID{
"\x44\x44\x01\x11"} },
1820 {
GrfID{
"\x6D\x62\x04\x02"},
GrfID{
"\x6D\x62\x04\x01"} },
1821 {
GrfID{
"\x4D\x65\x6f\x20"},
GrfID{
"\x4D\x65\x6F\x17"} },
1823 for (
const auto &grf_override : default_grf_overrides) {
1829 uint num_non_static = 0;
1831 _cur_gps.stage = stage;
1838 Debug(grf, 0,
"NewGRF file is missing '{}'; disabling", c->filename);
1847 Debug(grf, 0,
"'{}' is not loaded as the maximum number of non-static GRFs has been reached", c->filename);
1849 c->errors.emplace_back(STR_NEWGRF_ERROR_MSG_FATAL, 0, STR_NEWGRF_ERROR_TOO_MANY_NEWGRFS_LOADED);
1865 Debug(sprite, 2,
"LoadNewGRF: Currently {} sprites are loaded", _cur_gps.spriteid);
1874 _cur_gps.grfconfig =
nullptr;
1875 _cur_gps.grffile =
nullptr;
1878 _cur_gps.ClearDataForNextFile();
Class for backupping variables and making sure they are restored later.
void ResetBridges()
Reset the data been eventually changed by the grf loaded.
static constexpr CargoLabel CT_INVALID
Invalid cargo type.
Label< struct CargoLabelTag > CargoLabel
Globally unique label of a cargo type.
bool IsValidCargoType(CargoType cargo)
Test whether cargo type is not INVALID_CARGO.
EnumBitSet< CargoType, uint64_t > CargoTypes
Bitset of CargoType elements.
static constexpr CargoType NUM_CARGO
Maximum number of cargo types in a game.
MixedCargoType
Mixed cargo types for definitions with cargo that can vary depending on climate.
@ MCT_GRAIN_WHEAT_MAIZE
Cargo can be grain, wheat or maize.
@ MCT_LIVESTOCK_FRUIT
Cargo can be livestock or fruit.
@ MCT_VALUABLES_GOLD_DIAMONDS
Cargo can be valuables, gold or diamonds.
static constexpr CargoLabel CT_PASSENGERS
Available types of cargo Labels may be re-used between different climates.
CargoType
Cargo slots to indicate a cargo type within a game.
std::span< const CargoLabel > GetClimateDependentCargoTranslationTable()
Get default climate-dependent cargo translation table for a NewGRF, used if the NewGRF does not provi...
bool IsDefaultCargo(CargoType cargo_type)
Test if a cargo is a default cargo type.
CargoTypes _standard_cargo_mask
Bitmask of real cargo types available.
std::span< const CargoLabel > GetClimateIndependentCargoTranslationTable()
Get default climate-independent cargo translation table for a NewGRF, used if the NewGRF does not pro...
void SetupCargoForClimate(LandscapeType l)
Set up the default cargo types for the given landscape type.
void InitializeSortedCargoSpecs()
Initialize the list of sorted cargo specifications.
CargoTypes _cargo_mask
Bitmask of cargo types available.
@ Bulk
Bulk cargo (Coal, Grain etc., Ores, Fruit).
@ Liquid
Liquids (Oil, Water, Rubber).
@ Armoured
Armoured cargo (Valuables, Gold, Diamonds).
@ Refrigerated
Refrigerated cargo (Food, Fruit).
@ Express
Express cargo (Goods, Food, Candy, but also possible for passengers).
@ PieceGoods
Piece goods (Livestock, Wood, Steel, Paper).
@ Invalid
Invalid town production effect.
@ Mail
Cargo behaves mail-like for production.
@ Passengers
Cargo behaves passenger-like for production.
@ None
Town will not produce this cargo type.
EnumBitSet< CargoClass, uint16_t > CargoClasses
Bitset of CargoClass elements.
BadgeID index
Index assigned to badge.
GrfSpecFeatures features
Bitmask of which features use this badge.
constexpr bool Test(Tvalue_type value) const
Test if the value-th bit is set.
constexpr Timpl & Reset()
Reset all bits.
constexpr Timpl & Set()
Set all bits.
auto begin() const
Returns an iterator to begin of the set bits.
constexpr bool Any(const Timpl &other) const
Test if any of the given values are set.
Class to read from a NewGRF file.
static Pool::IterateWrapperFiltered< Engine, EngineTypeFilter > IterateType(VehicleType vt, size_t from=0)
Returns an iterable ensemble of all valid engines of the given type.
CargoGRFFileProps grf_prop
Link to NewGRF.
Iterate a range of enum values.
uint8_t ReadByte()
Read a byte from the file.
uint32_t ReadDword()
Read a double word (32 bits) from the file (in low endian format).
void SkipBytes(size_t n)
Skip n bytes ahead in the file.
uint16_t ReadWord()
Read a word (16 bits) from the file (in low endian format).
A reusable buffer that can be used for places that temporary allocate a bit of memory and do that ver...
T * Allocate(size_t count)
Get buffer of at least count times T.
RandomAccessFile with some extra information specific for sprite files.
uint8_t GetContainerVersion() const
Get the version number of container type used by the file.
static Date ConvertYMDToDate(Year year, Month month, Day day)
Converts a tuple of Year, Month and Day to a Date.
static Date date
Current date in days (day counter).
static Year year
Current year, starting at 0.
static DateFract date_fract
Fractional part of the day.
static constexpr TimerGame< struct Calendar >::Year MIN_YEAR
static constexpr TimerGame< struct Calendar >::Year MAX_YEAR
static Date date
Current date in days (day counter).
static Year year
Current year, starting at 0.
static DateFract date_fract
Fractional part of the day.
static Date ConvertYMDToDate(Year year, Month month, Day day)
Converts a tuple of Year, Month and Day to a Date.
static TickCounter counter
Monotonic counter, in ticks, since start of game.
StrongType::Typedef< int32_t, struct YearTag< struct Calendar >, StrongType::Compare, StrongType::Integer > Year
A sort-of mixin that implements 'at(pos)' and 'operator[](pos)' only for a specific type.
void ResetFaces()
Reset company manager face styles to default.
Functionality related to the company manager's face.
Configuration options of the network stuff.
static const uint NETWORK_MAX_GRF_COUNT
Maximum number of GRFs that can be sent.
Some simple functions to help with accessing containers.
int find_index(Container const &container, typename Container::const_reference item)
Helper function to get the index of an item Consider using std::set, std::unordered_set or std::flat_...
void ResetCurrencies(bool preserve_custom)
Will fill _currency_specs array with default values from _origin_currency_specs Called only from newg...
Functions to handle different currencies.
Functions related to debugging.
#define Debug(category, level, format_string,...)
Output a line of debugging information.
void SetPriceBaseMultiplier(Price price, int factor)
Change a price base by the given factor.
void ResetPriceBaseMultipliers()
Reset changes to the price base multipliers.
Price
Enumeration of all base prices for use with Prices.
@ Invalid
Invalid base price.
@ End
Price base end marker.
void SetYearEngineAgingStops()
Compute the value for _year_engine_aging_stops.
void SetupEngines()
Initialise the engine pool with the data from the original vehicles.
uint8_t GetOriginalEngineCount(VehicleType type)
Get the number of original engines for a VehicleType.
@ HasVariants
Set if engine has variants.
@ IsFolded
Set if display of variants should be folded (hidden).
Functions related to engines.
@ RoadIsTram
Road vehicle is a tram/light rail vehicle.
PoolID< uint16_t, struct EngineIDTag, 64000, 0xFFFF > EngineID
Unique identification number of an engine.
@ Wagon
simple wagon, not motorized
#define T
Climate temperate.
#define Y
Climate toyland.
#define A
Climate sub-arctic.
#define S
Climate sub-tropic.
constexpr std::underlying_type_t< enum_type > to_underlying(enum_type e)
Implementation of std::to_underlying (from C++23).
Error reporting related functions.
bool FioCheckFileExists(std::string_view filename, Subdirectory subdir)
Check whether the given file exists.
Functions for standard in/out file operations.
Subdirectory
The different kinds of subdirectories OpenTTD uses.
@ NewGrf
Subdirectory for all NewGRFs.
@ Baseset
Subdirectory for all base data (base sets, intro game).
Functions related to world/map generation.
uint32_t SpriteID
The number of a sprite, without mapping bits and colourtables.
void ClearSnowLine()
Clear the variable snow line table and free the memory.
HouseZones GetClimateMaskForLandscape()
Get the HouseZones climate mask for the current landscape type.
static const HouseID NUM_HOUSES
Total number of houses.
EnumBitSet< HouseZone, uint16_t > HouseZones
Bitset of HouseZone elements.
HouseZone
Concentric rings of zoning around the centre of a town.
void ResetIndustries()
This function initialize the spec arrays of both industry and industry tiles.
void SortIndustryTypes()
Initialize the list of sorted industry types.
Functions related to OTTD's landscape.
EnumBitSet< LandscapeType, uint8_t > LandscapeTypes
Bitset of LandscapeType elements.
LandscapeType
Landscape types.
@ Arctic
Landscape with snow levels.
@ Toyland
Landscape with funky industries and vehicles.
@ Tropic
Landscape with distinct rainforests and deserts,.
@ Temperate
Base landscape.
LiveryScheme
List of different livery schemes.
@ EMU
EMUs and their passenger wagons.
@ PassengerWagonDiesel
Passenger wagons attached to diesel engines.
@ Electric
Electric engines.
@ Monorail
Monorail engines.
@ PassengerWagonSteam
Passenger wagons attached to steam engines.
@ FreightWagon
Freight wagons.
@ DMU
DMUs and their passenger wagons.
bool _networking
are we in networking mode?
static void FinaliseObjectsArray()
Add all new objects to the object array.
static void FinalisePriceBaseMultipliers()
Decide whether price base multipliers of grfs shall apply globally or only to the grf specifying them...
static CargoLabel GetActiveCargoLabel(const std::initializer_list< CargoLabel > &labels)
Find first cargo label that exists and is active from a list of cargo labels.
static void FinaliseIndustriesArray()
Add all new industries to the industry array.
std::span< const CargoLabel > GetCargoTranslationTable(const GRFFile &grffile)
Get the cargo translation table to use for the given GRF file.
static std::vector< GRFFile > _grf_files
List of all loaded GRF files.
void ResetPersistentNewGRFData()
Reset NewGRF data which is stored persistently in savegames.
static void FinaliseAirportsArray()
Add all new airports to the airport array.
static GRFFile * GetFileByFilename(const std::string &filename)
Obtain a NewGRF file by its filename.
GRFFile * GetCurrentGRFOverride()
Get overridden GRF for current GRF if present.
void ConvertTTDBasePrice(uint32_t base_pointer, std::string_view error_location, Price *index)
Converts TTD(P) Base Price pointers into the enum used by OTTD See http://wiki.ttdpatch....
void GRFUnsafe(ByteReader &)
Set the current NewGRF as unsafe for static use.
Engine * GetNewEngine(const GRFFile *file, VehicleType type, uint16_t internal_id, bool static_access)
Returns the engine associated to a certain internal_id, resp.
static void ActivateOldShore()
Relocates the old shore sprites at new positions.
static void EnsureEarlyHouse(HouseZones bitmask)
Make sure there is at least one house available in the year 0 for the given climate / housezone combi...
TypedIndexContainer< std::vector< GRFTempEngineData >, EngineID > _gted
Temporary engine data used during NewGRF loading.
static void FinaliseEngineArray()
Check for invalid engines.
static void ResetNewGRFErrors()
Clear all NewGRF errors.
static void LoadNewGRFFileFromFile(GRFConfig &config, GrfLoadingStage stage, SpriteFile &file)
Load a particular NewGRF from a SpriteFile.
GRFLoadedFeatures _loaded_newgrf_features
Indicates which are the newgrf features currently loaded ingame.
void LoadNewGRF(SpriteID load_index, uint num_baseset)
Load all the NewGRFs.
static void ClearTemporaryNewGRFData(GRFFile *gf)
Reset all NewGRFData that was used only while processing data.
void DisableStaticNewGRFInfluencingNonStaticNewGRFs(GRFConfig &c)
Disable a static NewGRF when it is influencing another (non-static) NewGRF as this could cause desync...
static void FinaliseCanals()
Set to use the correct action0 properties for each canal feature.
void ResetNewGRFData()
Reset all NewGRF loaded data.
static void CalculateRefitMasks()
Precalculate refit masks from cargo classes for all vehicles.
void FinaliseCargoArray()
Check for invalid cargoes.
GrfSpecFeature GetGrfSpecFeature(VehicleType type)
Get the GrfSpecFeature associated with a VehicleType.
static void BuildCargoTranslationMap()
Construct the Cargo Mapping.
GRFFile * GetFileByGRFID(GrfID grfid)
Obtain a NewGRF file by its grfID.
void SetNewGRFOverride(GrfID source_grfid, GrfID target_grfid)
Set the override for a NewGRF.
void GrfMsgI(int severity, const std::string &msg)
Debug() function dedicated to newGRF debugging messages Function is essentially the same as Debug(grf...
EngineID GetNewEngineID(const GRFFile *file, VehicleType type, uint16_t internal_id)
Return the ID of a new engine.
GrfMiscBits _misc_grf_features
Miscellaneous GRF features, set by Action 0x0D, parameter 0x9E.
static void FinaliseHouseArray()
Add all new houses to the house array.
static void InitNewGRFFile(const GRFConfig &config)
Prepare loading a NewGRF file with its config.
static void ActivateOldTramDepot()
Relocate the old tram depot sprites to the new position, if no new ones were loaded.
void LoadNewGRFFile(GRFConfig &config, GrfLoadingStage stage, Subdirectory subdir, bool temporary)
Load a particular NewGRF.
static bool IsHouseSpecValid(HouseSpec &hs, const HouseSpec *next1, const HouseSpec *next2, const HouseSpec *next3, const std::string &filename)
Check if a given housespec is valid and disable it if it's not.
static void AfterLoadGRFs()
Finish loading NewGRFs and execute needed post-processing.
GRFError * DisableGrf(StringID message, GRFConfig *config)
Disable a GRF.
static void ResetNewGRF()
Reset and clear all NewGRFs.
void InitGRFTownGeneratorNames()
Allocate memory for the NewGRF town names.
VehicleType GetVehicleType(GrfSpecFeature feature)
Get the VehicleType associated with a GrfSpecFeature.
CargoTypes TranslateRefitMask(uint32_t refit_mask)
Translate the refit mask.
static void FinaliseBadges()
Finish up applying badges to things.
GrfLoadingStage
Stages of loading all NewGRFs.
@ SafetyScan
Checks whether the NewGRF can be used in a static context.
@ Reserve
Third step of NewGRF loading; reserve features and GRMs.
@ Init
Second step of NewGRF loading; load all actions into memory.
@ LabelScan
First step of NewGRF loading; find the 'goto' labels in the NewGRF.
@ Activation
Forth step of NewGRF loading; activate the features.
@ FileScan
Load the Action 8 metadata (GRF ID, name).
@ None
No shore sprites were replaced.
@ Action5
Shore sprites were replaced by Action5.
@ ActionA
Shore sprites were replaced by ActionA (using grass tiles for the corner-shores).
CanalFeature
List of different canal 'features'.
@ WithTrack
Electrified depot graphics with tram track were loaded.
@ None
No tram depot graphics were loaded.
EnumBitSet< GrfMiscBit, uint8_t > GrfMiscBits
Bitset of GrfMiscBit elements.
@ RoadStops
Road stops feature.
@ RoadVehicles
Road vehicles feature.
@ Invalid
An invalid spec feature.
@ Stations
Stations feature.
@ Airports
Airports feature.
@ Aircraft
Aircraft feature.
@ IndustryTiles
Industry tiles feature.
@ Objects
Objects feature.
@ AirportTiles
Airport tiles feature.
@ Industries
Industries feature.
EnumBitSet< GrfSpecFeature, uint32_t, GrfSpecFeature::End > GrfSpecFeatures
Bitset of GrfSpecFeature elements.
void InitializePatchFlags()
Initialize the TTDPatch flags.
void BindAirportSpecs()
Tie all airportspecs to their class.
NewGRF handling of airports.
NewGRF handling of airport tiles.
void ApplyBadgeFeaturesToClassBadges()
Apply features from all badges to their badge classes.
void AppendCopyableBadgeList(std::vector< BadgeID > &dst, std::span< const BadgeID > src, GrfSpecFeature feature)
Append copyable badges from a list onto another.
Badge * GetBadgeByLabel(std::string_view label)
Get a badge by label if it exists.
void ResetBadges()
Reset badges to the default state.
Functions related to NewGRF badges.
void AddBadgeClassesToConfiguration()
Add current badge classes to user configuration.
Functions related to NewGRF badge configuration.
NewGRF buffer reader definition.
@ CustomRefit
Custom refit mask.
@ CBID_VEHICLE_CUSTOM_REFIT
Called to get custom engine refit mask.
static const uint CALLBACK_FAILED
Different values for Callback result evaluations.
EnumIndexArray< WaterFeature, CanalFeature, CanalFeature::End > _water_feature
Table of canal 'feature' sprite groups.
Handling of NewGRF canals.
CargoType GetCargoTranslation(uint8_t cargo, const GRFFile *grffile, bool usebit)
Translate a GRF-local cargo slot/bitnum into a CargoType.
Cargo support for NewGRFs.
void ErrorUnknownCallbackResult(GrfID grfid, uint16_t cbid, uint16_t cb_res)
Record that a NewGRF returned an unknown/invalid callback result.
GRFConfigList _grfconfig
First item in list of current GRF set up.
@ NotFound
GRF file was not found in the local cache.
@ Initialised
GRF file has been initialised.
@ Unknown
The status of this grf file is unknown.
@ Disabled
GRF file is disabled.
@ Activated
GRF file has been activated.
@ Static
GRF file is used statically (can be used in any MP game).
@ Reserved
GRF file passed GrfLoadingStage::Reserve stage.
@ System
GRF file is an openttd-internal system grf.
@ Unsafe
GRF file is unsafe for static usage.
@ InitOnly
GRF file is processed up to GrfLoadingStage::Init.
@ GRFP_USE_MASK
Bitmask to get only the use palette use states.
uint16_t GetVehicleCallback(CallbackID callback, uint32_t param1, uint32_t param2, EngineID engine, const Vehicle *v, std::span< int32_t > regs100)
Evaluate a newgrf callback for vehicles.
void CommitVehicleListOrderChanges()
Determine default engine sorting and execute recorded ListOrderChanges from AlterVehicleListOrder.
Functions for NewGRF engines.
void ResetGenericCallbacks()
Reset all generic feature callback sprite groups.
void ResetHouses()
Reset and initialise house specs.
IndustryType MapNewGRFIndustryType(IndustryType grf_type, GrfID grf_id)
Map the GRF local type to an industry type.
Functions for NewGRF industries.
NewGRF internal processing state.
NewGRF internal processing state for vehicles.
void ResetObjects()
This function initialize the spec arrays of objects.
Functions related to NewGRF objects.
NewGRF definitions and structures for road stops.
Functions related to NewGRF provided sounds.
Header file for NewGRF stations.
void FinaliseStringMapping()
Finalise all string mappings.
NewGRF string mapping definition.
void CleanUpStrings()
House cleaning.
Header of Action 04 "universal holder" structure and functions.
GRFLanguage
Incomplete enumeration of the (New)GRF languages.
Header of Action 0F "universal holder" structure and functions.
static const GrfID INVALID_GRFID
An invalid NewGRF.
Label< struct GrfIDTag > GrfID
The unique identifier of a NewGRF.
Table of all default price bases.
RailType GetRailTypeByLabel(RailTypeLabel label, bool allow_alternate_labels)
Get the rail type for a given label.
void InitRailTypes()
Resolve sprites of custom rail types.
void ResetRailTypes()
Reset all rail type information to its default values.
const RailTypeInfo * GetRailTypeInfo(RailType railtype)
Returns a pointer to the Railtype information for a given railtype.
EnumBitSet< RailType, uint64_t > RailTypes
Bitset of RailType elements.
RailType
Enumeration for all possible railtypes.
@ INVALID_RAILTYPE
Flag for invalid railtype.
@ RAILTYPE_ELECTRIC
Electric rails.
@ RAILTYPE_RAIL
Standard non-electric rails.
RoadType GetRoadTypeByLabel(RoadTypeLabel label, bool allow_alternate_labels)
Get the road type for a given label.
void ResetRoadTypes()
Reset all road type information to its default values.
void InitRoadTypes()
Resolve sprites of custom road types.
const RoadTypeInfo * GetRoadTypeInfo(RoadType roadtype)
Returns a pointer to the Roadtype information for a given roadtype.
RoadType
The different roadtypes we support.
@ INVALID_ROADTYPE
flag for invalid roadtype
@ ROADTYPE_ROAD
Basic road type.
RoadTramType
The different types of road type.
A number of safeguards to prevent using unsafe methods.
GameSettings _settings_game
Game settings of a running game or the scenario editor.
void BuildLinkStatsLegend()
Populate legend table for the link stat view.
void BuildIndustriesLegend()
Fills an array for the industries legends.
SpriteFile & OpenCachedSpriteFile(const std::string &filename, Subdirectory subdir, bool palette_remap)
Open/get the SpriteFile that is cached for use in the sprite cache.
bool SkipSpriteData(SpriteFile &file, uint8_t type, uint16_t num)
Skip the given amount of sprite graphics data.
void ReadGRFSpriteOffsets(SpriteFile &file)
Parse the sprite section of GRFs.
Functions to cache sprites in memory.
static const SpriteID SPR_TRAMWAY_DEPOT_WITH_TRACK
static const SpriteID SPR_TRAMWAY_DEPOT_NO_TRACK
static const SpriteID SPR_ROAD_DEPOT
static const SpriteID SPR_FLAT_GRASS_TILE
static const SpriteID SPR_ORIGINALSHORE_START
static const SpriteID SPR_SHORE_BASE
Definition of base types and functions in a cross-platform compatible way.
#define lengthof(array)
Return the length of an fixed size array.
std::string FormatArrayAsHex(std::span< const uint8_t > data)
Format a byte array into a continuous hex string.
Functions related to low-level strings.
uint32_t StringID
Numeric value that represents a string, independent of the selected language.
static void ResetAirports()
This function initializes the airportspec array.
static void ResetAirportTiles()
This function initializes the tile array of AirportTileSpec.
Class to backup a specific variable and restore it upon destruction of this object to prevent stack v...
constexpr bool Empty() const
Check whether the label is empty.
Specification of a cargo type.
static IterateWrapper Iterate(size_t from=0)
Returns an iterable ensemble of all valid CargoSpec.
static CargoSpec array[NUM_CARGO]
Array holding all CargoSpecs.
Information about a vehicle.
LandscapeTypes climates
Climates supported by the engine.
Information about GRF, used in the game and (part of it) in savegames.
uint8_t palette
GRFPalette, bitset.
std::vector< GRFError > errors
NOSAVE: Error/Warning during GRF loading (Action 0x0B).
std::vector< uint32_t > param
GRF parameters.
GRFStatus status
NOSAVE: GRFStatus, enum.
GRFConfigFlags flags
NOSAVE: GCF_Flags, bitset.
std::string filename
Filename - either with or without full path.
GRFIdentifier ident
grfid and md5sum to uniquely identify newgrfs
Information about why GRF had problems during initialisation.
uint32_t nfo_line
Line within NewGRF of error.
std::string data
Additional data for message and custom_message.
uint16_t local_id
id defined by the grf file for this entity
void SetGRFFile(const struct GRFFile *grffile)
Set the NewGRF file, and its grfid, associated with grf props.
bool HasGrfFile() const
Test if this entity was introduced by NewGRF.
Dynamic data of a loaded NewGRF.
std::array< uint8_t, NUM_CARGO > cargo_map
Inverse cargo translation table (CargoType -> local ID).
std::vector< RoadTypeLabel > roadtype_list
Roadtype translation table (road).
std::vector< RoadTypeLabel > tramtype_list
Roadtype translation table (tram).
GRFFile(const GRFConfig &config)
Constructor for GRFFile.
std::vector< CargoLabel > cargo_list
Cargo translation table (local ID -> label).
std::unordered_map< GRFLanguage, LanguageMap > language_map
Mappings related to the languages.
uint traininfo_vehicle_width
Width (in pixels) of a 8/8 train vehicle in depot GUI and vehicle details.
GrfSpecFeatures grf_features
Bitset of GrfSpecFeature the grf uses.
int traininfo_vehicle_pitch
Vertical offset for drawing train images in depot GUI and vehicle details.
std::vector< GRFLabel > labels
List of labels.
PriceMultipliers price_base_multipliers
Price base multipliers as set by the grf.
GrfID grfid
GRF ID (defined by Action 0x08).
State of features loaded by NewGRFs.
@ NonEmpty
GRF defined the vehicle as refittable. If the refitmask is empty after translation (cargotypes not av...
static void FileScan(ByteReader &buf)
Implementation of the GrfLoadingStage::FileScan stage of this action.
static void SafetyScan(ByteReader &buf)
Implementation of the GrfLoadingStage::SafetyScan stage of this action.
static void Reserve(ByteReader &buf)
Implementation of the GrfLoadingStage::Reserve stage of this action.
static void Activation(ByteReader &buf)
Implementation of the GrfLoadingStage::Activation stage of this action.
static void Init(ByteReader &buf)
Implementation of the GrfLoadingStage::Init stage of this action.
static void LabelScan(ByteReader &buf)
Implementation of the GrfLoadingStage::LabelScan stage of this action.
Temporary data during loading of GRFs.
CargoType accepts_cargo[HOUSE_NUM_ACCEPTS]
input cargo slots
SubstituteGRFFileProps grf_prop
Properties related the the grf file.
bool enabled
the house is available to build (true by default, but can be disabled by newgrf)
CargoLabel accepts_cargo_label[HOUSE_ORIGINAL_NUM_ACCEPTS]
input landscape cargo slots
static HouseSpec * Get(size_t house_id)
Get the spec for a house ID.
BuildingFlags building_flags
some flags that describe the house (size, stadium etc...)
uint8_t population
population (Zero on other tiles in multi tile house.)
uint8_t cargo_acceptance[HOUSE_NUM_ACCEPTS]
acceptance level for the cargo slots
HouseZones building_availability
where can it be built (climates, zones)
static std::vector< HouseSpec > & Specs()
Get a reference to all HouseSpecs.
Helper class to invoke a GrfActionHandler.
Mapping of language data between a NewGRF and OpenTTD.
static const LanguageMap * GetLanguageMap(GrfID grfid, GRFLanguage language_id)
Get the language map associated with a given NewGRF and language.
static void BindToClasses()
Tie all ObjectSpecs to their class.
static Pool::IterateWrapper< Engine > Iterate(size_t from=0)
static size_t GetPoolSize()
static T * Create(Targs &&... args)
static Engine * Get(auto index)
static bool CanAllocateItem(size_t n=1)
Information about a rail vehicle.
RailTypes railtypes
Railtypes, mangled if elrail is disabled.
RailVehicleType railveh_type
Type of rail vehicle.
uint8_t capacity
Cargo capacity of vehicle; For multiheaded engines the capacity of each single engine.
Information about a road vehicle.
RoadType roadtype
Road type.
Iterable ensemble of each set bit in a value.
Information about a ship vehicle.
bool old_refittable
Is ship refittable; only used during initialisation. Later use EngineInfo::refit_mask.
uint16_t subst_id
The id of the entity to replace.
DisplayOptions _display_opt
What do we want to draw/do?
LiveryScheme GetEngineLiveryScheme(EngineID engine_type, EngineID parent_engine_type, const Vehicle *v)
Determines the LiveryScheme for a vehicle.
Base class for all vehicles.
VehicleType
Available vehicle types.
@ Invalid
Non-existing type of vehicle.
@ Aircraft
Aircraft vehicle type.
@ Train
Train vehicle type.