Merge branch 'master' into jgrpp

# Conflicts:
#	src/base_station_base.h
#	src/newgrf.cpp
#	src/newgrf_class.h
#	src/newgrf_class_func.h
#	src/newgrf_commons.cpp
#	src/newgrf_commons.h
#	src/newgrf_roadstop.cpp
#	src/newgrf_roadstop.h
#	src/newgrf_station.cpp
#	src/saveload/newgrf_sl.cpp
#	src/saveload/saveload.h
#	src/saveload/station_sl.cpp
pull/532/head
Jonathan G Rennison 1 year ago
commit 36fadb5424

@ -24,7 +24,7 @@ extern StationPool _station_pool;
struct StationSpecList {
const StationSpec *spec;
uint32 grfid; ///< GRF ID of this custom station
uint8 localidx; ///< Station ID within GRF of station
uint16 localidx; ///< Station ID within GRF of station
};
struct RoadStopSpecList {

@ -215,7 +215,8 @@ public:
typedef void (*SpecialSpriteHandler)(ByteReader *buf);
static const uint NUM_STATIONS_PER_GRF = 255; ///< Number of StationSpecs per NewGRF; limited to 255 to allow extending Action3 with an extended byte later on.
/** The maximum amount of stations a single GRF is allowed to add */
static const uint NUM_STATIONS_PER_GRF = UINT16_MAX - 1;
/** Temporary engine data used when loading only */
struct GRFTempEngineData {
@ -1940,7 +1941,7 @@ static ChangeInfoResult StationChangeInfo(uint stid, int numinfo, int prop, cons
}
case 0x0A: { // Copy sprite layout
byte srcid = buf->ReadByte();
uint16 srcid = buf->ReadExtendedByte();
const StationSpec *srcstatspec = srcid >= _cur.grffile->stations.size() ? nullptr : _cur.grffile->stations[srcid].get();
if (srcstatspec == nullptr) {
@ -1994,7 +1995,7 @@ static ChangeInfoResult StationChangeInfo(uint stid, int numinfo, int prop, cons
break;
case 0x0F: { // Copy custom layout
byte srcid = buf->ReadByte();
uint16 srcid = buf->ReadExtendedByte();
const StationSpec *srcstatspec = srcid >= _cur.grffile->stations.size() ? nullptr : _cur.grffile->stations[srcid].get();
if (srcstatspec == nullptr) {
@ -2047,6 +2048,8 @@ static ChangeInfoResult StationChangeInfo(uint stid, int numinfo, int prop, cons
statspec->animation.triggers = buf->ReadWord();
break;
/* 0x19 road routing (not implemented) */
case 0x1A: { // Advanced sprite layout
uint16 tiles = buf->ReadExtendedByte();
statspec->renderdata.clear(); // delete earlier loaded stuff
@ -2085,6 +2088,14 @@ static ChangeInfoResult StationChangeInfo(uint stid, int numinfo, int prop, cons
}
break;
case 0x1C: // Station Name
AddStringForMapping(buf->ReadWord(), &statspec->name);
break;
case 0x1D: // Station Class name
AddStringForMapping(buf->ReadWord(), &StationClass::Get(statspec->cls_id)->name);
break;
default:
ret = HandleAction0PropertyDefault(buf, prop);
break;
@ -6439,9 +6450,9 @@ static void VehicleMapSpriteGroup(ByteReader *buf, byte feature, uint8 idcount)
static void CanalMapSpriteGroup(ByteReader *buf, uint8 idcount)
{
CanalFeature *cfs = AllocaM(CanalFeature, idcount);
uint16 *cfs = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
cfs[i] = (CanalFeature)buf->ReadByte();
cfs[i] = buf->ReadExtendedByte();
}
uint8 cidcount = buf->ReadByte();
@ -6451,7 +6462,7 @@ static void CanalMapSpriteGroup(ByteReader *buf, uint8 idcount)
if (!IsValidGroupID(groupid, "CanalMapSpriteGroup")) return;
for (uint i = 0; i < idcount; i++) {
CanalFeature cf = cfs[i];
uint16 cf = cfs[i];
if (cf >= CF_END) {
grfmsg(1, "CanalMapSpriteGroup: Canal subset %d out of range, skipping", cf);
@ -6471,9 +6482,9 @@ static void StationMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *stations = AllocaM(uint8, idcount);
uint16 *stations = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
stations[i] = buf->ReadByte();
stations[i] = buf->ReadExtendedByte();
}
uint8 cidcount = buf->ReadByte();
@ -6489,7 +6500,7 @@ static void StationMapSpriteGroup(ByteReader *buf, uint8 idcount)
StationSpec *statspec = stations[i] >= _cur.grffile->stations.size() ? nullptr : _cur.grffile->stations[stations[i]].get();
if (statspec == nullptr) {
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%02X does not exist, skipping", stations[i]);
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%X undefined, skipping", stations[i]);
continue;
}
@ -6504,12 +6515,12 @@ static void StationMapSpriteGroup(ByteReader *buf, uint8 idcount)
StationSpec *statspec = stations[i] >= _cur.grffile->stations.size() ? nullptr : _cur.grffile->stations[stations[i]].get();
if (statspec == nullptr) {
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%02X does not exist, skipping", stations[i]);
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%X undefined, skipping", stations[i]);
continue;
}
if (statspec->grf_prop.grffile != nullptr) {
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%02X mapped multiple times, skipping", stations[i]);
grfmsg(1, "StationMapSpriteGroup: Station with ID 0x%X mapped multiple times, skipping", stations[i]);
continue;
}
@ -6528,9 +6539,9 @@ static void TownHouseMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *houses = AllocaM(uint8, idcount);
uint16 *houses = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
houses[i] = buf->ReadByte();
houses[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6559,9 +6570,9 @@ static void IndustryMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *industries = AllocaM(uint8, idcount);
uint16 *industries = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
industries[i] = buf->ReadByte();
industries[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6590,9 +6601,9 @@ static void IndustrytileMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *indtiles = AllocaM(uint8, idcount);
uint16 *indtiles = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
indtiles[i] = buf->ReadByte();
indtiles[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6616,9 +6627,9 @@ static void IndustrytileMapSpriteGroup(ByteReader *buf, uint8 idcount)
static void CargoMapSpriteGroup(ByteReader *buf, uint8 idcount)
{
CargoID *cargoes = AllocaM(CargoID, idcount);
uint16 *cargoes = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
cargoes[i] = buf->ReadByte();
cargoes[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6629,7 +6640,7 @@ static void CargoMapSpriteGroup(ByteReader *buf, uint8 idcount)
if (!IsValidGroupID(groupid, "CargoMapSpriteGroup")) return;
for (uint i = 0; i < idcount; i++) {
CargoID cid = cargoes[i];
uint16 cid = cargoes[i];
if (cid >= NUM_CARGO) {
grfmsg(1, "CargoMapSpriteGroup: Cargo ID %d out of range, skipping", cid);
@ -6644,9 +6655,9 @@ static void CargoMapSpriteGroup(ByteReader *buf, uint8 idcount)
static void SignalsMapSpriteGroup(ByteReader *buf, uint8 idcount)
{
uint8 *ids = AllocaM(uint8, idcount);
uint16 *ids = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
ids[i] = buf->ReadByte();
ids[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6657,7 +6668,7 @@ static void SignalsMapSpriteGroup(ByteReader *buf, uint8 idcount)
if (!IsValidGroupID(groupid, "SignalsMapSpriteGroup")) return;
for (uint i = 0; i < idcount; i++) {
uint8 id = ids[i];
uint16 id = ids[i];
switch (id) {
case NSA3ID_CUSTOM_SIGNALS:
@ -6684,7 +6695,7 @@ static void ObjectMapSpriteGroup(ByteReader *buf, uint8 idcount)
uint16 *objects = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
objects[i] = HasBit(_cur.grffile->observed_feature_tests, GFTOF_MORE_OBJECTS_PER_GRF) ? buf->ReadExtendedByte() : buf->ReadByte();
objects[i] = buf->ReadExtendedByte();
}
uint8 cidcount = buf->ReadByte();
@ -6700,7 +6711,7 @@ static void ObjectMapSpriteGroup(ByteReader *buf, uint8 idcount)
ObjectSpec *spec = (objects[i] >= _cur.grffile->objectspec.size()) ? nullptr : _cur.grffile->objectspec[objects[i]].get();
if (spec == nullptr) {
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%02X undefined, skipping", objects[i]);
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%X undefined, skipping", objects[i]);
continue;
}
@ -6715,12 +6726,12 @@ static void ObjectMapSpriteGroup(ByteReader *buf, uint8 idcount)
ObjectSpec *spec = (objects[i] >= _cur.grffile->objectspec.size()) ? nullptr : _cur.grffile->objectspec[objects[i]].get();
if (spec == nullptr) {
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%02X undefined, skipping", objects[i]);
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%X undefined, skipping", objects[i]);
continue;
}
if (spec->grf_prop.grffile != nullptr) {
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%02X mapped multiple times, skipping", objects[i]);
grfmsg(1, "ObjectMapSpriteGroup: Object with ID 0x%X mapped multiple times, skipping", objects[i]);
continue;
}
@ -6734,7 +6745,7 @@ static void RailTypeMapSpriteGroup(ByteReader *buf, uint8 idcount)
{
uint8 *railtypes = AllocaM(uint8, idcount);
for (uint i = 0; i < idcount; i++) {
uint8 id = buf->ReadByte();
uint16 id = buf->ReadExtendedByte();
railtypes[i] = id < RAILTYPE_END ? _cur.grffile->railtype_map[id] : INVALID_RAILTYPE;
}
@ -6767,7 +6778,7 @@ static void RoadTypeMapSpriteGroup(ByteReader *buf, uint8 idcount, RoadTramType
uint8 *roadtypes = AllocaM(uint8, idcount);
for (uint i = 0; i < idcount; i++) {
uint8 id = buf->ReadByte();
uint16 id = buf->ReadExtendedByte();
roadtypes[i] = id < ROADTYPE_END ? type_map[id] : INVALID_ROADTYPE;
}
@ -6801,9 +6812,9 @@ static void AirportMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *airports = AllocaM(uint8, idcount);
uint16 *airports = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
airports[i] = buf->ReadByte();
airports[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6832,9 +6843,9 @@ static void AirportTileMapSpriteGroup(ByteReader *buf, uint8 idcount)
return;
}
uint8 *airptiles = AllocaM(uint8, idcount);
uint16 *airptiles = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
airptiles[i] = buf->ReadByte();
airptiles[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6876,7 +6887,7 @@ static void RoadStopMapSpriteGroup(ByteReader *buf, uint8 idcount)
RoadStopSpec *roadstopspec = (roadstops[i] >= _cur.grffile->roadstops.size()) ? nullptr : _cur.grffile->roadstops[roadstops[i]].get();
if (roadstopspec == nullptr) {
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%02X does not exist, skipping", roadstops[i]);
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%X does not exist, skipping", roadstops[i]);
continue;
}
@ -6896,12 +6907,12 @@ static void RoadStopMapSpriteGroup(ByteReader *buf, uint8 idcount)
RoadStopSpec *roadstopspec = (roadstops[i] >= _cur.grffile->roadstops.size()) ? nullptr : _cur.grffile->roadstops[roadstops[i]].get();
if (roadstopspec == nullptr) {
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%02X does not exist, skipping.", roadstops[i]);
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%X does not exist, skipping.", roadstops[i]);
continue;
}
if (roadstopspec->grf_prop.grffile != nullptr) {
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%02X mapped multiple times, skipping", roadstops[i]);
grfmsg(1, "RoadStopMapSpriteGroup: Road stop with ID 0x%X mapped multiple times, skipping", roadstops[i]);
continue;
}
@ -6914,9 +6925,9 @@ static void RoadStopMapSpriteGroup(ByteReader *buf, uint8 idcount)
static void NewLandscapeMapSpriteGroup(ByteReader *buf, uint8 idcount)
{
uint8 *ids = AllocaM(uint8, idcount);
uint16 *ids = AllocaM(uint16, idcount);
for (uint i = 0; i < idcount; i++) {
ids[i] = buf->ReadByte();
ids[i] = buf->ReadExtendedByte();
}
/* Skip the cargo type section, we only care about the default group */
@ -6927,7 +6938,7 @@ static void NewLandscapeMapSpriteGroup(ByteReader *buf, uint8 idcount)
if (!IsValidGroupID(groupid, "NewLandscapeMapSpriteGroup")) return;
for (uint i = 0; i < idcount; i++) {
uint8 id = ids[i];
uint16 id = ids[i];
switch (id) {
case NLA3ID_CUSTOM_ROCKS:
@ -6955,7 +6966,7 @@ static void FeatureMapSpriteGroup(ByteReader *buf)
* B feature see action 0
* B n-id bits 0-6: how many IDs this definition applies to
* bit 7: if set, this is a wagon override definition (see below)
* B ids the IDs for which this definition applies
* E ids the IDs for which this definition applies
* B num-cid number of cargo IDs (sprite group IDs) in this definition
* can be zero, in that case the def-cid is used always
* B cargo-type type of this cargo type (e.g. mail=2, wood=7, see below)

@ -1376,7 +1376,7 @@ int GetEngineProperty(EngineID engine, PropertyID property, int orig_value, cons
}
static void DoTriggerVehicle(Vehicle *v, VehicleTrigger trigger, uint16_t base_random_bits, bool first)
static void DoTriggerVehicle(Vehicle *v, VehicleTrigger trigger, uint16 base_random_bits, bool first)
{
/* We can't trigger a non-existent vehicle... */
assert(v != nullptr);

@ -64,7 +64,7 @@ extern const GRFFeatureInfo _grf_feature_list[] = {
GRFFeatureInfo("action0_object_viewport_map_tile_type", 1),
GRFFeatureInfo("road_stops", 9, GFTOF_ROAD_STOPS),
GRFFeatureInfo("new_landscape", 2),
GRFFeatureInfo("more_objects_per_grf", 1, GFTOF_MORE_OBJECTS_PER_GRF),
GRFFeatureInfo("more_objects_per_grf", 1),
GRFFeatureInfo("more_action2_ids", 1, GFTOF_MORE_ACTION2_IDS),
GRFFeatureInfo("town_feature", 1),
GRFFeatureInfo("town_uncapped_variables", 1),

@ -103,8 +103,7 @@ enum Action2VariableRemapIds {
};
enum GRFFeatureTestObservationFlag : uint8 {
GFTOF_MORE_OBJECTS_PER_GRF = 0,
GFTOF_MORE_ACTION2_IDS,
GFTOF_MORE_ACTION2_IDS = 0,
GFTOF_TOWN_ZONE_CALLBACK,
GFTOF_MORE_VARACTION2_TYPES,
GFTOF_MULTI_PART_SHIPS,

@ -21,6 +21,7 @@ static const ObjectType OBJECT_HQ = 4; ///< HeadQuarter of a play
static const ObjectType NEW_OBJECT_OFFSET = 5; ///< Offset for new objects
static const ObjectType NUM_OBJECTS = 64000; ///< Number of supported objects overall
static const ObjectType NUM_OBJECTS_PER_GRF = NUM_OBJECTS; ///< Number of supported objects per NewGRF
static const ObjectType INVALID_OBJECT_TYPE = 0xFFFF; ///< An invalid object
/** Unique identifier for an object. */

@ -183,7 +183,7 @@ const SlxiSubChunkInfo _sl_xv_sub_chunk_infos[] = {
{ XSLFI_TOWN_SETTING_OVERRIDE, XSCF_NULL, 1, 1, "town_setting_override", nullptr, nullptr, nullptr },
{ XSLFI_LINKGRAPH_SPARSE_EDGES, XSCF_NULL, 1, 1, "linkgraph_sparse_edges", nullptr, nullptr, nullptr },
{ XSLFI_AUX_TILE_LOOP, XSCF_NULL, 1, 1, "aux_tile_loop", nullptr, nullptr, nullptr },
{ XSLFI_NEWGRF_ENTITY_EXTRA, XSCF_NULL, 1, 1, "newgrf_entity_extra", nullptr, nullptr, nullptr },
{ XSLFI_NEWGRF_ENTITY_EXTRA, XSCF_NULL, 2, 2, "newgrf_entity_extra", nullptr, nullptr, nullptr },
{ XSLFI_TNNC_CHUNK, XSCF_IGNORABLE_ALL, 0, 1, "tnnc_chunk", nullptr, nullptr, "TNNC" },
{ XSLFI_MULTI_CARGO_SHIPS, XSCF_NULL, 1, 1, "multi_cargo_ships", nullptr, nullptr, nullptr },
{ XSLFI_REMAIN_NEXT_ORDER_STATION, XSCF_IGNORABLE_UNKNOWN, 1, 1, "remain_next_order_station", nullptr, nullptr, nullptr },

@ -363,6 +363,7 @@ enum SaveLoadVersion : uint16 {
SLV_AI_START_DATE, ///< 309 PR#10653 Removal of individual AI start dates and added a generic one.
SLV_EXTEND_VEHICLE_RANDOM, ///< 310 PR#10701 Extend vehicle random bits.
SLV_EXTEND_ENTITY_MAPPING, ///< 311 PR#10672 Extend entity mapping range.
SL_MAX_VERSION, ///< Highest possible saveload version

@ -240,7 +240,8 @@ static Money _cargo_feeder_share;
static const SaveLoad _station_speclist_desc[] = {
SLE_CONDVAR(StationSpecList, grfid, SLE_UINT32, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR(StationSpecList, localidx, SLE_UINT8, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR_X(StationSpecList, localidx, SLE_FILE_U8 | SLE_VAR_U16, SL_MIN_VERSION, SL_MAX_VERSION, SlXvFeatureTest(XSLFTO_AND, XSLFI_NEWGRF_ENTITY_EXTRA, 0, 1)),
SLE_CONDVAR_X(StationSpecList, localidx, SLE_UINT16, SL_MIN_VERSION, SL_MAX_VERSION, SlXvFeatureTest(XSLFTO_AND, XSLFI_NEWGRF_ENTITY_EXTRA, 2)),
};
static const SaveLoad _roadstop_speclist_desc[] = {

@ -79,8 +79,9 @@ static void SwapPackets(GoodsEntry *ge)
class SlStationSpecList : public DefaultSaveLoadHandler<SlStationSpecList, BaseStation> {
public:
inline static const SaveLoad description[] = {
SLE_CONDVAR(StationSpecList, grfid, SLE_UINT32, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR(StationSpecList, localidx, SLE_UINT8, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR(StationSpecList, grfid, SLE_UINT32, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR(StationSpecList, localidx, SLE_FILE_U8 | SLE_VAR_U16, SLV_27, SLV_EXTEND_ENTITY_MAPPING),
SLE_CONDVAR(StationSpecList, localidx, SLE_UINT16, SLV_EXTEND_ENTITY_MAPPING, SL_MAX_VERSION),
};
inline const static SaveLoadCompatTable compat_description = _station_spec_list_sl_compat;
@ -106,8 +107,9 @@ public:
class SlRoadStopSpecList : public DefaultSaveLoadHandler<SlRoadStopSpecList, BaseStation> {
public:
inline static const SaveLoad description[] = {
SLE_VAR(RoadStopSpecList, grfid, SLE_UINT32),
SLE_VAR(RoadStopSpecList, localidx, SLE_FILE_U8 | SLE_VAR_U16),
SLE_CONDVAR(StationSpecList, grfid, SLE_UINT32, SLV_27, SL_MAX_VERSION),
SLE_CONDVAR(StationSpecList, localidx, SLE_FILE_U8 | SLE_VAR_U16, SLV_27, SLV_EXTEND_ENTITY_MAPPING),
SLE_CONDVAR(StationSpecList, localidx, SLE_UINT16, SLV_EXTEND_ENTITY_MAPPING, SL_MAX_VERSION),
};
inline const static SaveLoadCompatTable compat_description = _station_road_stop_spec_list_sl_compat;

Loading…
Cancel
Save