From 32ef582c37e3fda64c61b36acb398c235f8292a2 Mon Sep 17 00:00:00 2001 From: peter1138 Date: Sat, 30 Jan 2010 21:49:22 +0000 Subject: (svn r18969) -Add: [NewGRF] NewGRF-settable rail type properties. --- src/newgrf.cpp | 159 ++++++++++++++++++++++++++++++++++++++++++++++++++++++- src/newgrf.h | 5 ++ src/rail.h | 5 ++ src/rail_cmd.cpp | 20 +++++++ 4 files changed, 188 insertions(+), 1 deletion(-) diff --git a/src/newgrf.cpp b/src/newgrf.cpp index 6eb357fe5..455fdfb57 100644 --- a/src/newgrf.cpp +++ b/src/newgrf.cpp @@ -2488,6 +2488,155 @@ static ChangeInfoResult IndustriesChangeInfo(uint indid, int numinfo, int prop, return ret; } +static ChangeInfoResult RailTypeChangeInfo(uint id, int numinfo, int prop, ByteReader *buf) +{ + ChangeInfoResult ret = CIR_SUCCESS; + + extern RailtypeInfo _railtypes[RAILTYPE_END]; + + for (int i = 0; i < numinfo; i++) { + RailType rt = _cur_grffile->railtype_map[id + i]; + if (rt == INVALID_RAILTYPE) return CIR_INVALID_ID; + + RailtypeInfo *rti = &_railtypes[rt]; + + switch (prop) { + case 0x08: // Label of rail type + /* Skipped here as this is loaded during reservation stage. */ + buf->ReadDWord(); + break; + + case 0x09: // Name of railtype + rti->strings.toolbar_caption = buf->ReadWord(); + _string_to_grf_mapping[&rti->strings.toolbar_caption] = _cur_grffile->grfid; + break; + + case 0x0A: // Menu text of railtype + rti->strings.menu_text = buf->ReadWord(); + _string_to_grf_mapping[&rti->strings.menu_text] = _cur_grffile->grfid; + break; + + case 0x0B: // Build window caption + rti->strings.build_caption = buf->ReadWord(); + _string_to_grf_mapping[&rti->strings.build_caption] = _cur_grffile->grfid; + break; + + case 0x0C: // Autoreplace text + rti->strings.replace_text = buf->ReadWord(); + _string_to_grf_mapping[&rti->strings.replace_text] = _cur_grffile->grfid; + break; + + case 0x0D: // New locomotive text + rti->strings.new_loco = buf->ReadWord(); + _string_to_grf_mapping[&rti->strings.new_loco] = _cur_grffile->grfid; + break; + + case 0x0E: // Compatible railtype list + case 0x0F: // Powered railtype list + { + /* Rail type compatibility bits are added to the existing bits + * to allow multiple GRFs to modify compatibility with the + * default rail types. */ + int n = buf->ReadByte(); + for (int j = 0; j != n; j++) { + RailTypeLabel label = buf->ReadDWord(); + RailType rt = GetRailTypeByLabel(BSWAP32(label)); + if (rt != INVALID_RAILTYPE) { + if (prop == 0x0E) { + SetBit(rti->compatible_railtypes, rt); + } else { + SetBit(rti->powered_railtypes, rt); + } + } + } + break; + } + + case 0x10: // Rail Type flags + rti->flags = (RailTypeFlags)buf->ReadByte(); + break; + + case 0x11: // Curve speed advantage + rti->curve_speed = buf->ReadByte(); + break; + + case 0x12: // Station graphic + rti->total_offset = Clamp(buf->ReadByte(), 0, 2) * 88; + break; + + case 0x13: // Construction cost factor + rti->cost_multiplier = buf->ReadByte(); + break; + + case 0x14: // Speed limit + buf->ReadWord(); + break; + + case 0x15: // Acceleration model + rti->acceleration_type = Clamp(buf->ReadByte(), 0, 2); + break; + + default: + ret = CIR_UNKNOWN; + break; + } + } + + return ret; +} + +static ChangeInfoResult RailTypeReserveInfo(uint id, int numinfo, int prop, ByteReader *buf) +{ + ChangeInfoResult ret = CIR_SUCCESS; + + for (int i = 0; i < numinfo; i++) { + switch (prop) { + case 0x08: // Label of rail type + { + RailTypeLabel rtl = buf->ReadDWord(); + rtl = BSWAP32(rtl); + + RailType rt = GetRailTypeByLabel(rtl); + if (rt == INVALID_RAILTYPE) { + /* Set up new rail type */ + rt = AllocateRailType(rtl); + } + + _cur_grffile->railtype_map[id + i] = rt; + break; + } + + case 0x09: // Name of railtype + case 0x0A: // Menu text + case 0x0B: // Build window caption + case 0x0C: // Autoreplace text + case 0x0D: // New loco + case 0x14: // Speed limit + buf->ReadWord(); + break; + + case 0x0E: // Compatible railtype list + case 0x0F: // Powered railtype list + for (int j = buf->ReadByte(); j != 0; j--) buf->ReadDWord(); + break; + + case 0x10: // Rail Type flags + case 0x11: // Curve speed advantage + case 0x12: // Station graphic + case 0x13: // Construction cost + case 0x15: // Acceleration model + buf->ReadByte(); + break; + + default: + ret = CIR_UNKNOWN; + break; + } + } + + return ret; +} + static bool HandleChangeInfoResult(const char *caller, ChangeInfoResult cir, uint8 feature, uint8 property) { switch (cir) { @@ -2543,6 +2692,10 @@ static void FeatureChangeInfo(ByteReader *buf) /* GSF_INDUSTRIES */ IndustriesChangeInfo, /* GSF_CARGOS */ NULL, // Cargo is handled during reservation /* GSF_SOUNDFX */ SoundEffectChangeInfo, + /* GSF_AIRPORTS */ NULL, + /* GSF_SIGNALS */ NULL, + /* GSF_OBJECTS */ NULL, + /* GSF_RAILTYPES */ RailTypeChangeInfo, }; uint8 feature = buf->ReadByte(); @@ -2611,7 +2764,7 @@ static void ReserveChangeInfo(ByteReader *buf) { uint8 feature = buf->ReadByte(); - if (feature != GSF_CARGOS && feature != GSF_GLOBALVAR) return; + if (feature != GSF_CARGOS && feature != GSF_GLOBALVAR && feature != GSF_RAILTYPES) return; uint8 numprops = buf->ReadByte(); uint8 numinfo = buf->ReadByte(); @@ -2630,6 +2783,10 @@ static void ReserveChangeInfo(ByteReader *buf) case GSF_GLOBALVAR: cir = GlobalVarReserveInfo(index, numinfo, prop, buf); break; + + case GSF_RAILTYPES: + cir = RailTypeReserveInfo(index, numinfo, prop, buf); + break; } if (HandleChangeInfoResult("ReserveChangeInfo", cir, feature, prop)) return; diff --git a/src/newgrf.h b/src/newgrf.h index b38cf4803..6f4dd758e 100644 --- a/src/newgrf.h +++ b/src/newgrf.h @@ -54,6 +54,10 @@ enum GrfSpecFeature { GSF_INDUSTRIES, GSF_CARGOS, GSF_SOUNDFX, + GSF_AIRPORTS, + GSF_SIGNALS, + GSF_OBJECTS, + GSF_RAILTYPES, GSF_END, }; @@ -111,6 +115,7 @@ struct GRFFile { uint8 railtype_max; RailTypeLabel *railtype_list; + RailType railtype_map[RAILTYPE_END]; int traininfo_vehicle_pitch; ///< Vertical offset for draing train images in depot GUI and vehicle details int traininfo_vehicle_width; ///< Width (in pixels) of a 8/8 train vehicle in depot GUI and vehicle details diff --git a/src/rail.h b/src/rail.h index 6c6feee40..0507dad2b 100644 --- a/src/rail.h +++ b/src/rail.h @@ -281,4 +281,9 @@ RailType GetRailTypeByLabel(RailTypeLabel label); */ void ResetRailTypes(); +/** + * Allocate a new rail type label + */ +RailType AllocateRailType(RailTypeLabel label); + #endif /* RAIL_H */ diff --git a/src/rail_cmd.cpp b/src/rail_cmd.cpp index fa751e505..22e45c7b8 100644 --- a/src/rail_cmd.cpp +++ b/src/rail_cmd.cpp @@ -52,6 +52,26 @@ void ResetRailTypes() memcpy(_railtypes, _original_railtypes, sizeof(_original_railtypes)); } +RailType AllocateRailType(RailTypeLabel label) +{ + for (RailType rt = RAILTYPE_BEGIN; rt != RAILTYPE_END; rt++) { + RailtypeInfo *rti = &_railtypes[rt]; + + if (rti->label == 0) { + /* Set up new rail type */ + memcpy(rti, &_railtypes[RAILTYPE_RAIL], sizeof(*rti)); + rti->label = label; + + /* Make us compatible with ourself. */ + rti->powered_railtypes = (RailTypes)(1 << rt); + rti->compatible_railtypes = (RailTypes)(1 << rt); + return rt; + } + } + + return INVALID_RAILTYPE; +} + static const byte _track_sloped_sprites[14] = { 14, 15, 22, 13, 0, 21, 17, 12, -- cgit v1.2.3-70-g09d2