00001
00002
00003
00004
00005
00006
00007
00008
00009
00012 #include "../stdafx.h"
00013 #include "../town.h"
00014 #include "../industry.h"
00015 #include "../company_func.h"
00016 #include "../aircraft.h"
00017 #include "../roadveh.h"
00018 #include "../ship.h"
00019 #include "../train.h"
00020 #include "../signs_base.h"
00021 #include "../station_base.h"
00022 #include "../subsidy_base.h"
00023 #include "../debug.h"
00024 #include "../depot_base.h"
00025 #include "../date_func.h"
00026 #include "../vehicle_func.h"
00027 #include "../variables.h"
00028 #include "../effectvehicle_base.h"
00029 #include "../core/mem_func.hpp"
00030 #include "../core/alloc_type.hpp"
00031 #include "../engine_base.h"
00032 #include "../engine_func.h"
00033 #include "../company_base.h"
00034 #include "saveload_internal.h"
00035 #include "oldloader.h"
00036
00037 #include "table/strings.h"
00038 #include "../table/engines.h"
00039 #include "../table/townname.h"
00040
00041 static bool _read_ttdpatch_flags;
00042
00043 static uint8 *_old_map3;
00044
00045 void FixOldMapArray()
00046 {
00047
00048
00049 MemSetT(&_m[0], 0);
00050 SetTileType(0, MP_WATER);
00051 SetTileOwner(0, OWNER_WATER);
00052 }
00053
00054 static void FixTTDMapArray()
00055 {
00056
00057 for (TileIndex t = 0; t < OLD_MAP_SIZE; t++) {
00058 _m[t].m3 = _old_map3[t * 2];
00059 _m[t].m4 = _old_map3[t * 2 + 1];
00060 }
00061
00062 for (TileIndex t = 0; t < OLD_MAP_SIZE; t++) {
00063 switch (GetTileType(t)) {
00064 case MP_STATION:
00065 _m[t].m4 = 0;
00066 switch (_m[t].m5) {
00067
00068 case 0x53: case 0x54: _m[t].m5 += 170 - 0x53; break;
00069 case 0x57: case 0x58: _m[t].m5 += 168 - 0x57; break;
00070 case 0x55: case 0x56: _m[t].m5 += 170 - 0x55; break;
00071 case 0x59: case 0x5A: _m[t].m5 += 168 - 0x59; break;
00072 default: break;
00073 }
00074 break;
00075
00076 case MP_RAILWAY:
00077
00078 if (GB(_m[t].m5, 6, 2) == 1) {
00079
00080 if (_m[t].m4) {
00081 _m[t].m4 = (_m[t].m4 >> 1) & 7;
00082 }
00083 }
00084
00085
00086 _m[t].m4 &= 0xF;
00087 break;
00088
00089 case MP_WATER:
00090
00091 if (GB(_m[t].m3, 0, 2) == 3) {
00092 SetTileType(t, MP_WATER);
00093 SetTileOwner(t, OWNER_WATER);
00094 _m[t].m2 = 0;
00095 _m[t].m3 = 2;
00096 _m[t].m4 = Random();
00097 _m[t].m5 = 0;
00098 }
00099 break;
00100
00101 default:
00102 break;
00103 }
00104 }
00105
00106 FixOldMapArray();
00107 }
00108
00109 static void FixTTDDepots()
00110 {
00111 const Depot *d;
00112 FOR_ALL_DEPOTS_FROM(d, 252) {
00113 if (!IsRoadDepotTile(d->xy) && !IsRailDepotTile(d->xy) && !IsShipDepotTile(d->xy) && !IsHangarTile(d->xy)) {
00115 delete d;
00116 }
00117 }
00118 }
00119
00120 #define FIXNUM(x, y, z) (((((x) << 16) / (y)) + 1) << z)
00121
00122 static uint32 RemapOldTownName(uint32 townnameparts, byte old_town_name_type)
00123 {
00124 switch (old_town_name_type) {
00125 case 0: case 3:
00126
00127 return townnameparts;
00128
00129 case 1:
00130
00131
00132 return FIXNUM(townnameparts - 86, lengthof(_name_french_real), 0);
00133
00134 case 2:
00135 DEBUG(misc, 0, "German Townnames are buggy (%d)", townnameparts);
00136 return townnameparts;
00137
00138 case 4:
00139
00140 return FIXNUM(townnameparts, lengthof(_name_spanish_real), 0);
00141
00142 case 5:
00143
00144
00145
00146 return FIXNUM(townnameparts, lengthof(_name_silly_1), 0) | FIXNUM(GB(townnameparts, 16, 8), lengthof(_name_silly_2), 16);
00147 }
00148 return 0;
00149 }
00150
00151 #undef FIXNUM
00152
00153 static void FixOldTowns()
00154 {
00155 Town *town;
00156
00157
00158 FOR_ALL_TOWNS(town) {
00159 if (IsInsideMM(town->townnametype, 0x20C1, 0x20C3)) {
00160 town->townnametype = SPECSTR_TOWNNAME_ENGLISH + _settings_game.game_creation.town_name;
00161 town->townnameparts = RemapOldTownName(town->townnameparts, _settings_game.game_creation.town_name);
00162 }
00163 }
00164 }
00165
00166 static StringID *_old_vehicle_names;
00167
00168 void FixOldVehicles()
00169 {
00170 Vehicle *v;
00171
00172 FOR_ALL_VEHICLES(v) {
00173 if ((size_t)v->next == 0xFFFF) {
00174 v->next = NULL;
00175 } else {
00176 v->next = Vehicle::GetIfValid((size_t)v->next);
00177 }
00178
00179
00180 switch (v->spritenum) {
00181 case 0xfd: break;
00182 case 0xff: v->spritenum = 0xfe; break;
00183 default: v->spritenum >>= 1; break;
00184 }
00185
00186
00187 if (v->type == VEH_EFFECT) v->subtype = v->subtype >> 1;
00188
00189 v->name = CopyFromOldName(_old_vehicle_names[v->index]);
00190
00191
00192 if (v->type == VEH_ROAD) {
00193 RoadVehicle *rv = RoadVehicle::From(v);
00194 if (rv->state != RVSB_IN_DEPOT && rv->state != RVSB_WORMHOLE) {
00195 ClrBit(rv->state, 2);
00196 }
00197 }
00198
00199
00200 if (v->type == VEH_ROAD || v->type == VEH_SHIP) v->subtype = 0;
00201
00202
00203
00204
00205
00206 if (!IsCompanyBuildableVehicleType(v) ||
00207 (v->IsPrimaryVehicle() && v->current_order.IsType(OT_NOTHING))) {
00208 v->current_order.MakeDummy();
00209 }
00210
00211
00212 }
00213 }
00214
00215 static bool FixTTOMapArray()
00216 {
00217 for (TileIndex t = 0; t < OLD_MAP_SIZE; t++) {
00218 TileType tt = GetTileType(t);
00219 if (tt == 11) {
00220
00221
00222 _m[t].m3 = 1;
00223 SetTileType(t, MP_RAILWAY);
00224 _m[t].m2 = 1;
00225 tt = MP_RAILWAY;
00226 }
00227
00228 switch (tt) {
00229 case MP_CLEAR:
00230 break;
00231
00232 case MP_RAILWAY:
00233 switch (GB(_m[t].m5, 6, 2)) {
00234 case 0:
00235 break;
00236 case 1:
00237 _m[t].m4 = (~_m[t].m5 & 1) << 2;
00238 SB(_m[t].m2, 6, 2, GB(_m[t].m5, 3, 2));
00239 _m[t].m3 |= 0xC0;
00240 _m[t].m5 = HasBit(_m[t].m5, 5) ? 2 : 1;
00241 _m[t].m5 |= 0x40;
00242 break;
00243 case 3:
00244 _m[t].m2 = 0;
00245 break;
00246 default:
00247 return false;
00248 }
00249 break;
00250
00251 case MP_ROAD:
00252 switch (GB(_m[t].m5, 4, 4)) {
00253 case 0:
00254 if (_m[t].m2 == 4) _m[t].m2 = 5;
00255 break;
00256 case 1:
00257 _m[t].m3 = _m[t].m1;
00258 break;
00259 case 2:
00260 break;
00261 default:
00262 return false;
00263 }
00264 break;
00265
00266 case MP_HOUSE:
00267 _m[t].m3 = _m[t].m2 & 0xC0;
00268 _m[t].m2 &= 0x3F;
00269 if (_m[t].m2 >= 5) _m[t].m2++;
00270 break;
00271
00272 case MP_TREES:
00273 _m[t].m3 = GB(_m[t].m5, 3, 3);
00274 _m[t].m5 &= 0xC7;
00275 break;
00276
00277 case MP_STATION:
00278 _m[t].m3 = (_m[t].m5 >= 0x08 && _m[t].m5 <= 0x0F) ? 1 : 0;
00279 if (_m[t].m5 >= 8) _m[t].m5 -= 8;
00280 if (_m[t].m5 >= 0x42) _m[t].m5++;
00281 break;
00282
00283 case MP_WATER:
00284 _m[t].m3 = _m[t].m2 = 0;
00285 break;
00286
00287 case MP_VOID:
00288 _m[t].m2 = _m[t].m3 = _m[t].m5 = 0;
00289 break;
00290
00291 case MP_INDUSTRY:
00292 _m[t].m3 = 0;
00293 switch (_m[t].m5) {
00294 case 0x24:
00295 _m[t].m5 = 0x25;
00296 break;
00297 case 0x25: case 0x27:
00298 case 0x28: case 0x29: case 0x2A: case 0x2B:
00299 _m[t].m5--;
00300 break;
00301 default:
00302 if (_m[t].m5 >= 0x2C) _m[t].m5 += 3;
00303 break;
00304 }
00305 break;
00306
00307 case MP_TUNNELBRIDGE:
00308 if (HasBit(_m[t].m5, 7)) {
00309 byte m5 = _m[t].m5;
00310 _m[t].m5 = m5 & 0xE1;
00311 if (GB(m5, 1, 2) == 1) _m[t].m5 |= 0x02;
00312 if (GB(m5, 1, 2) == 3) _m[t].m2 |= 0xA0;
00313 if (!HasBit(m5, 6)) {
00314 _m[t].m3 = (GB(m5, 1, 2) == 3) ? 1 : 0;
00315 } else {
00316 _m[t].m3 = HasBit(m5, 2) ? 0x10 : 0;
00317 if (GB(m5, 3, 2) == 3) _m[t].m3 |= 1;
00318 if (GB(m5, 3, 2) == 1) _m[t].m5 |= 0x08;
00319 }
00320 } else {
00321 _m[t].m2 = 0;
00322 _m[t].m3 = HasBit(_m[t].m5, 3);
00323 _m[t].m5 &= HasBit(_m[t].m5, 3) ? 0x03 : 0x07 ;
00324 }
00325 break;
00326
00327 case MP_UNMOVABLE:
00328 _m[t].m2 = 0;
00329 _m[t].m3 = 0;
00330 break;
00331
00332 default:
00333 return false;
00334
00335 }
00336 }
00337
00338 FixOldMapArray();
00339
00340 return true;
00341 }
00342
00343 static Engine *_old_engines;
00344
00345 static bool FixTTOEngines()
00346 {
00348 static const EngineID ttd_to_tto[] = {
00349 0, 255, 255, 255, 255, 255, 255, 255, 5, 7, 8, 9, 10, 11, 12, 13,
00350 255, 255, 255, 255, 255, 255, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
00351 25, 26, 27, 28, 29, 30, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00352 255, 255, 255, 255, 255, 255, 255, 31, 255, 32, 33, 34, 35, 36, 37, 38,
00353 39, 40, 41, 42, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00354 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00355 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00356 255, 255, 255, 255, 44, 45, 46, 255, 255, 255, 255, 47, 48, 255, 49, 50,
00357 255, 255, 255, 255, 51, 52, 255, 53, 54, 255, 55, 56, 255, 57, 58, 255,
00358 59, 60, 255, 61, 62, 255, 63, 64, 255, 65, 66, 255, 255, 255, 255, 255,
00359 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00360 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255,
00361 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 67, 68, 69, 70,
00362 71, 255, 255, 76, 77, 255, 255, 78, 79, 80, 81, 82, 83, 84, 85, 86,
00363 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 255,
00364 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 102, 255, 255
00365 };
00366
00368 static const EngineID tto_to_ttd[] = {
00369 0, 0, 8, 8, 8, 8, 8, 9, 10, 11, 12, 13, 14, 15, 15, 22,
00370 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 55,
00371 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 116, 116, 117, 118, 123,
00372 124, 126, 127, 132, 133, 135, 136, 138, 139, 141, 142, 144, 145, 147, 148, 150,
00373 151, 153, 154, 204, 205, 206, 207, 208, 211, 212, 211, 212, 211, 212, 215, 216,
00374 217, 218, 219, 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232,
00375 233, 234, 235, 236, 237, 238, 253
00376 };
00377
00378 Vehicle *v;
00379 FOR_ALL_VEHICLES(v) {
00380 if (v->engine_type >= lengthof(tto_to_ttd)) return false;
00381 v->engine_type = tto_to_ttd[v->engine_type];
00382 }
00383
00384
00385 uint j = 0;
00386 for (uint i = 0; i < lengthof(_orig_rail_vehicle_info); i++, j++) new (GetTempDataEngine(j)) Engine(VEH_TRAIN, i);
00387 for (uint i = 0; i < lengthof(_orig_road_vehicle_info); i++, j++) new (GetTempDataEngine(j)) Engine(VEH_ROAD, i);
00388 for (uint i = 0; i < lengthof(_orig_ship_vehicle_info); i++, j++) new (GetTempDataEngine(j)) Engine(VEH_SHIP, i);
00389 for (uint i = 0; i < lengthof(_orig_aircraft_vehicle_info); i++, j++) new (GetTempDataEngine(j)) Engine(VEH_AIRCRAFT, i);
00390
00391 Date aging_date = min(_date + DAYS_TILL_ORIGINAL_BASE_YEAR, ConvertYMDToDate(2050, 0, 1));
00392
00393 for (EngineID i = 0; i < 256; i++) {
00394 int oi = ttd_to_tto[i];
00395 Engine *e = GetTempDataEngine(i);
00396
00397 if (oi == 255) {
00398
00399 _date += DAYS_TILL_ORIGINAL_BASE_YEAR;
00400 StartupOneEngine(e, aging_date);
00401 e->intro_date -= DAYS_TILL_ORIGINAL_BASE_YEAR;
00402 _date -= DAYS_TILL_ORIGINAL_BASE_YEAR;
00403
00404
00405 if (_date >= e->intro_date && HasBit(e->info.climates, 0)) {
00406 e->flags |= ENGINE_AVAILABLE;
00407 e->company_avail = (CompanyMask)0xFF;
00408 e->age = _date > e->intro_date ? (_date - e->intro_date) / 30 : 0;
00409 }
00410 } else {
00411
00412 Engine *oe = &_old_engines[oi];
00413
00414 e->intro_date = oe->intro_date;
00415 e->age = oe->age;
00416 e->reliability = oe->reliability;
00417 e->reliability_spd_dec = oe->reliability_spd_dec;
00418 e->reliability_start = oe->reliability_start;
00419 e->reliability_max = oe->reliability_max;
00420 e->reliability_final = oe->reliability_final;
00421 e->duration_phase_1 = oe->duration_phase_1;
00422 e->duration_phase_2 = oe->duration_phase_2;
00423 e->duration_phase_3 = oe->duration_phase_3;
00424 e->flags = oe->flags;
00425
00426 e->company_avail = 0;
00427
00428
00429
00430 for (uint j = 0; j < lengthof(tto_to_ttd); j++) {
00431 if (tto_to_ttd[j] == i && _old_engines[j].company_avail != 0) {
00432 e->company_avail = (CompanyMask)0xFF;
00433 e->flags |= ENGINE_AVAILABLE;
00434 break;
00435 }
00436 }
00437
00438 e->info.climates = 1;
00439 }
00440
00441 e->preview_company_rank = 0;
00442 e->preview_wait = 0;
00443 e->name = NULL;
00444 }
00445
00446 return true;
00447 }
00448
00449 static void FixTTOCompanies()
00450 {
00451 Company *c;
00452 FOR_ALL_COMPANIES(c) {
00453 c->cur_economy.company_value = CalculateCompanyValue(c);
00454 }
00455 }
00456
00457 static inline byte RemapTTOColour(byte tto)
00458 {
00460 static const byte tto_colour_remap[] = {
00461 COLOUR_DARK_BLUE, COLOUR_GREY, COLOUR_YELLOW, COLOUR_RED,
00462 COLOUR_PURPLE, COLOUR_DARK_GREEN, COLOUR_ORANGE, COLOUR_PALE_GREEN,
00463 COLOUR_BLUE, COLOUR_GREEN, COLOUR_CREAM, COLOUR_BROWN,
00464 COLOUR_WHITE, COLOUR_LIGHT_BLUE, COLOUR_MAUVE, COLOUR_PINK
00465 };
00466
00467 if ((size_t)tto >= lengthof(tto_colour_remap)) return COLOUR_GREY;
00468
00469 return tto_colour_remap[tto];
00470 }
00471
00472 static inline uint RemapTownIndex(uint x)
00473 {
00474 return _savegame_type == SGT_TTO ? (x - 0x264) / 78 : (x - 0x264) / 94;
00475 }
00476
00477 static inline uint RemapOrderIndex(uint x)
00478 {
00479 return _savegame_type == SGT_TTO ? (x - 0x1AC4) / 2 : (x - 0x1C18) / 2;
00480 }
00481
00482 extern TileIndex *_animated_tile_list;
00483 extern uint _animated_tile_count;
00484 extern char *_old_name_array;
00485
00486 static byte _old_vehicle_multiplier;
00487 static uint32 _old_town_index;
00488 static uint16 _old_string_id;
00489 static uint16 _old_string_id_2;
00490 static uint16 _old_extra_chunk_nums;
00491
00492 static void ReadTTDPatchFlags()
00493 {
00494 if (_read_ttdpatch_flags) return;
00495
00496 _read_ttdpatch_flags = true;
00497
00498 if (_savegame_type == SGT_TTO) {
00499 _old_vehicle_multiplier = 1;
00500 return;
00501 }
00502
00503
00504 _old_vehicle_multiplier = _old_map3[0];
00505
00506
00507 if (_old_vehicle_multiplier < 2) _old_vehicle_multiplier++;
00508
00509 _old_vehicle_names = MallocT<StringID>(_old_vehicle_multiplier * 850);
00510
00511
00512
00513
00514
00515
00516 _bump_assert_value = (_old_vehicle_multiplier - 1) * 850 * 128;
00517
00518 for (uint i = 0; i < 17; i++) {
00519 if (_old_map3[i] != 0) _savegame_type = SGT_TTDP1;
00520 }
00521
00522
00523 if (memcmp(&_old_map3[0x1FFFA], "TTDp", 4) == 0) _savegame_type = SGT_TTDP2;
00524
00525 _old_extra_chunk_nums = _old_map3[_savegame_type == SGT_TTDP2 ? 0x1FFFE : 0x2];
00526
00527
00528 for (uint i = 0; i < 17; i++) _old_map3[i] = 0;
00529 for (uint i = 0x1FE00; i < 0x20000; i++) _old_map3[i] = 0;
00530
00531 if (_savegame_type == SGT_TTDP2) DEBUG(oldloader, 2, "Found TTDPatch game");
00532
00533 DEBUG(oldloader, 3, "Vehicle-multiplier is set to %d (%d vehicles)", _old_vehicle_multiplier, _old_vehicle_multiplier * 850);
00534 }
00535
00536 static const OldChunks town_chunk[] = {
00537 OCL_SVAR( OC_TILE, Town, xy ),
00538 OCL_NULL( 2 ),
00539 OCL_SVAR( OC_UINT16, Town, townnametype ),
00540 OCL_SVAR( OC_UINT32, Town, townnameparts ),
00541 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Town, grow_counter ),
00542 OCL_NULL( 1 ),
00543 OCL_NULL( 4 ),
00544 OCL_NULL( 2 ),
00545 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, Town, flags ),
00546 OCL_NULL( 10 ),
00547
00548 OCL_SVAR( OC_INT16, Town, ratings[0] ),
00549 OCL_SVAR( OC_INT16, Town, ratings[1] ),
00550 OCL_SVAR( OC_INT16, Town, ratings[2] ),
00551 OCL_SVAR( OC_INT16, Town, ratings[3] ),
00552 OCL_SVAR( OC_INT16, Town, ratings[4] ),
00553 OCL_SVAR( OC_INT16, Town, ratings[5] ),
00554 OCL_SVAR( OC_INT16, Town, ratings[6] ),
00555 OCL_SVAR( OC_INT16, Town, ratings[7] ),
00556
00557 OCL_SVAR( OC_FILE_U32 | OC_VAR_U16, Town, have_ratings ),
00558 OCL_SVAR( OC_FILE_U32 | OC_VAR_U16, Town, statues ),
00559 OCL_NULL( 2 ),
00560 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Town, time_until_rebuild ),
00561 OCL_SVAR( OC_FILE_U8 | OC_VAR_I16, Town, growth_rate ),
00562
00563 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, new_max_pass ),
00564 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, new_max_mail ),
00565 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, new_act_pass ),
00566 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, new_act_mail ),
00567 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, max_pass ),
00568 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, max_mail ),
00569 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, act_pass ),
00570 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Town, act_mail ),
00571
00572 OCL_SVAR( OC_UINT8, Town, pct_pass_transported ),
00573 OCL_SVAR( OC_UINT8, Town, pct_mail_transported ),
00574
00575 OCL_SVAR( OC_TTD | OC_UINT16, Town, new_act_food ),
00576 OCL_SVAR( OC_TTD | OC_UINT16, Town, new_act_water ),
00577 OCL_SVAR( OC_TTD | OC_UINT16, Town, act_food ),
00578 OCL_SVAR( OC_TTD | OC_UINT16, Town, act_water ),
00579
00580 OCL_SVAR( OC_UINT8, Town, road_build_months ),
00581 OCL_SVAR( OC_UINT8, Town, fund_buildings_months ),
00582
00583 OCL_CNULL( OC_TTD, 8 ),
00584
00585 OCL_END()
00586 };
00587
00588 static bool LoadOldTown(LoadgameState *ls, int num)
00589 {
00590 Town *t = new (num) Town();
00591 if (!LoadChunk(ls, t, town_chunk)) return false;
00592
00593 if (t->xy != 0) {
00594 if (_savegame_type == SGT_TTO) {
00595
00596 t->townnametype = t->townnametype == 0x10B6 ? 0x20C1 : t->townnametype + 0x2A00;
00597 }
00598 } else {
00599 delete t;
00600 }
00601
00602 return true;
00603 }
00604
00605 static uint16 _old_order;
00606 static const OldChunks order_chunk[] = {
00607 OCL_VAR ( OC_UINT16, 1, &_old_order ),
00608 OCL_END()
00609 };
00610
00611 static bool LoadOldOrder(LoadgameState *ls, int num)
00612 {
00613 if (!LoadChunk(ls, NULL, order_chunk)) return false;
00614
00615 Order *o = new (num) Order();
00616 o->AssignOrder(UnpackOldOrder(_old_order));
00617
00618 if (o->IsType(OT_NOTHING)) {
00619 delete o;
00620 } else {
00621
00622
00623 Order *prev = Order::GetIfValid(num - 1);
00624 if (prev != NULL) prev->next = o;
00625 }
00626
00627 return true;
00628 }
00629
00630 static bool LoadOldAnimTileList(LoadgameState *ls, int num)
00631 {
00632
00633
00634
00635
00636
00637
00638 const OldChunks anim_chunk[] = {
00639 OCL_VAR ( OC_TILE, 256, _animated_tile_list ),
00640 OCL_END ()
00641 };
00642
00643 if (!LoadChunk(ls, NULL, anim_chunk)) return false;
00644
00645
00646 for (_animated_tile_count = 0; _animated_tile_count < 256; _animated_tile_count++) {
00647 if (_animated_tile_list[_animated_tile_count] == 0) break;
00648 }
00649
00650 return true;
00651 }
00652
00653 static const OldChunks depot_chunk[] = {
00654 OCL_SVAR( OC_TILE, Depot, xy ),
00655 OCL_VAR ( OC_UINT32, 1, &_old_town_index ),
00656 OCL_END()
00657 };
00658
00659 static bool LoadOldDepot(LoadgameState *ls, int num)
00660 {
00661 Depot *d = new (num) Depot();
00662 if (!LoadChunk(ls, d, depot_chunk)) return false;
00663
00664 if (d->xy != 0) {
00665 d->town_index = RemapTownIndex(_old_town_index);
00666 } else {
00667 delete d;
00668 }
00669
00670 return true;
00671 }
00672
00673 static StationID _current_station_id;
00674 static uint16 _waiting_acceptance;
00675 static uint8 _cargo_source;
00676 static uint8 _cargo_days;
00677
00678 static const OldChunks goods_chunk[] = {
00679 OCL_VAR ( OC_UINT16, 1, &_waiting_acceptance ),
00680 OCL_SVAR( OC_UINT8, GoodsEntry, days_since_pickup ),
00681 OCL_SVAR( OC_UINT8, GoodsEntry, rating ),
00682 OCL_VAR ( OC_UINT8, 1, &_cargo_source ),
00683 OCL_VAR ( OC_UINT8, 1, &_cargo_days ),
00684 OCL_SVAR( OC_UINT8, GoodsEntry, last_speed ),
00685 OCL_SVAR( OC_UINT8, GoodsEntry, last_age ),
00686
00687 OCL_END()
00688 };
00689
00690 static bool LoadOldGood(LoadgameState *ls, int num)
00691 {
00692
00693 if (_savegame_type == SGT_TTO && num == 11) return true;
00694
00695 Station *st = Station::Get(_current_station_id);
00696 GoodsEntry *ge = &st->goods[num];
00697
00698 if (!LoadChunk(ls, ge, goods_chunk)) return false;
00699
00700 SB(ge->acceptance_pickup, GoodsEntry::ACCEPTANCE, 1, HasBit(_waiting_acceptance, 15));
00701 SB(ge->acceptance_pickup, GoodsEntry::PICKUP, 1, _cargo_source != 0xFF);
00702 if (GB(_waiting_acceptance, 0, 12) != 0) {
00703 ge->cargo.Append(new CargoPacket(GB(_waiting_acceptance, 0, 12), _cargo_days, (_cargo_source == 0xFF) ? INVALID_STATION : _cargo_source, 0, 0));
00704 }
00705
00706 return true;
00707 }
00708
00709 static const OldChunks station_chunk[] = {
00710 OCL_SVAR( OC_TILE, Station, xy ),
00711 OCL_VAR ( OC_UINT32, 1, &_old_town_index ),
00712
00713 OCL_NULL( 4 ),
00714 OCL_SVAR( OC_TILE, Station, train_station.tile ),
00715 OCL_SVAR( OC_TILE, Station, airport_tile ),
00716 OCL_SVAR( OC_TILE, Station, dock_tile ),
00717 OCL_SVAR( OC_UINT8, Station, train_station.w ),
00718
00719 OCL_NULL( 1 ),
00720 OCL_NULL( 2 ),
00721
00722 OCL_VAR ( OC_UINT16, 1, &_old_string_id ),
00723
00724 OCL_NULL( 4 ),
00725
00726 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, Station, had_vehicle_of_type ),
00727
00728 OCL_CHUNK( 12, LoadOldGood ),
00729
00730 OCL_SVAR( OC_UINT8, Station, time_since_load ),
00731 OCL_SVAR( OC_UINT8, Station, time_since_unload ),
00732 OCL_SVAR( OC_UINT8, Station, delete_ctr ),
00733 OCL_SVAR( OC_UINT8, Station, owner ),
00734 OCL_SVAR( OC_UINT8, Station, facilities ),
00735 OCL_SVAR( OC_TTD | OC_UINT8, Station, airport_type ),
00736 OCL_SVAR( OC_TTO | OC_FILE_U16 | OC_VAR_U64, Station, airport_flags ),
00737 OCL_NULL( 3 ),
00738 OCL_CNULL( OC_TTD, 1 ),
00739 OCL_SVAR( OC_TTD | OC_FILE_U16 | OC_VAR_U64, Station, airport_flags ),
00740 OCL_CNULL( OC_TTD, 2 ),
00741 OCL_CNULL( OC_TTD, 4 ),
00742
00743 OCL_END()
00744 };
00745
00746 static bool LoadOldStation(LoadgameState *ls, int num)
00747 {
00748 Station *st = new (num) Station();
00749 _current_station_id = num;
00750
00751 if (!LoadChunk(ls, st, station_chunk)) return false;
00752
00753 if (st->xy != 0) {
00754 st->town = Town::Get(RemapTownIndex(_old_town_index));
00755
00756 if (_savegame_type == SGT_TTO) {
00757 if (IsInsideBS(_old_string_id, 0x180F, 32)) {
00758 st->string_id = STR_SV_STNAME + (_old_string_id - 0x180F);
00759 } else {
00760 st->string_id = _old_string_id + 0x2800;
00761 }
00762
00763 if (HasBit(st->airport_flags, 8)) {
00764 st->airport_type = 1;
00765 } else if (HasBit(st->airport_flags, 6)) {
00766 st->airport_type = 3;
00767 } else {
00768 st->airport_type = 0;
00769 }
00770 } else {
00771 st->string_id = RemapOldStringID(_old_string_id);
00772 }
00773 } else {
00774 delete st;
00775 }
00776
00777 return true;
00778 }
00779
00780 static const OldChunks industry_chunk[] = {
00781 OCL_SVAR( OC_TILE, Industry, location.tile ),
00782 OCL_VAR ( OC_UINT32, 1, &_old_town_index ),
00783 OCL_SVAR( OC_UINT8, Industry, location.w ),
00784 OCL_SVAR( OC_UINT8, Industry, location.h ),
00785 OCL_NULL( 2 ),
00786
00787 OCL_SVAR( OC_TTD | OC_UINT16, Industry, produced_cargo_waiting[0] ),
00788 OCL_SVAR( OC_TTD | OC_UINT16, Industry, produced_cargo_waiting[1] ),
00789 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Industry, produced_cargo_waiting[0] ),
00790 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Industry, produced_cargo_waiting[1] ),
00791
00792 OCL_SVAR( OC_UINT8, Industry, production_rate[0] ),
00793 OCL_SVAR( OC_UINT8, Industry, production_rate[1] ),
00794
00795 OCL_NULL( 3 ),
00796
00797 OCL_SVAR( OC_UINT8, Industry, prod_level ),
00798
00799 OCL_SVAR( OC_UINT16, Industry, this_month_production[0] ),
00800 OCL_SVAR( OC_UINT16, Industry, this_month_production[1] ),
00801 OCL_SVAR( OC_UINT16, Industry, this_month_transported[0] ),
00802 OCL_SVAR( OC_UINT16, Industry, this_month_transported[1] ),
00803
00804 OCL_SVAR( OC_UINT8, Industry, last_month_pct_transported[0] ),
00805 OCL_SVAR( OC_UINT8, Industry, last_month_pct_transported[1] ),
00806
00807 OCL_SVAR( OC_UINT16, Industry, last_month_production[0] ),
00808 OCL_SVAR( OC_UINT16, Industry, last_month_production[1] ),
00809 OCL_SVAR( OC_UINT16, Industry, last_month_transported[0] ),
00810 OCL_SVAR( OC_UINT16, Industry, last_month_transported[1] ),
00811
00812 OCL_SVAR( OC_UINT8, Industry, type ),
00813 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Industry, counter ),
00814 OCL_SVAR( OC_UINT8, Industry, owner ),
00815 OCL_SVAR( OC_UINT8, Industry, random_colour ),
00816 OCL_SVAR( OC_TTD | OC_FILE_U8 | OC_VAR_I32, Industry, last_prod_year ),
00817 OCL_SVAR( OC_TTD | OC_UINT16, Industry, counter ),
00818 OCL_SVAR( OC_TTD | OC_UINT8, Industry, was_cargo_delivered ),
00819
00820 OCL_CNULL( OC_TTD, 9 ),
00821
00822 OCL_END()
00823 };
00824
00825 static bool LoadOldIndustry(LoadgameState *ls, int num)
00826 {
00827 Industry *i = new (num) Industry();
00828 if (!LoadChunk(ls, i, industry_chunk)) return false;
00829
00830 if (i->location.tile != 0) {
00831 i->town = Town::Get(RemapTownIndex(_old_town_index));
00832
00833 if (_savegame_type == SGT_TTO) {
00834 if (i->type > 0x06) i->type++;
00835 if (i->type == 0x0A) i->type = 0x12;
00836
00837 YearMonthDay ymd;
00838 ConvertDateToYMD(_date, &ymd);
00839 i->last_prod_year = ymd.year;
00840
00841 i->random_colour = RemapTTOColour(i->random_colour);
00842 }
00843
00844 IncIndustryTypeCount(i->type);
00845 } else {
00846 delete i;
00847 }
00848
00849 return true;
00850 }
00851
00852 static CompanyID _current_company_id;
00853 static int32 _old_yearly;
00854
00855 static const OldChunks _company_yearly_chunk[] = {
00856 OCL_VAR( OC_INT32, 1, &_old_yearly ),
00857 OCL_END()
00858 };
00859
00860 static bool LoadOldCompanyYearly(LoadgameState *ls, int num)
00861 {
00862 Company *c = Company::Get(_current_company_id);
00863
00864 for (uint i = 0; i < 13; i++) {
00865 if (_savegame_type == SGT_TTO && i == 6) {
00866 _old_yearly = 0;
00867 } else {
00868 if (!LoadChunk(ls, NULL, _company_yearly_chunk)) return false;
00869 }
00870
00871 c->yearly_expenses[num][i] = _old_yearly;
00872 }
00873
00874 return true;
00875 }
00876
00877 static const OldChunks _company_economy_chunk[] = {
00878 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, CompanyEconomyEntry, income ),
00879 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, CompanyEconomyEntry, expenses ),
00880 OCL_SVAR( OC_INT32, CompanyEconomyEntry, delivered_cargo ),
00881 OCL_SVAR( OC_INT32, CompanyEconomyEntry, performance_history ),
00882 OCL_SVAR( OC_TTD | OC_FILE_I32 | OC_VAR_I64, CompanyEconomyEntry, company_value ),
00883
00884 OCL_END()
00885 };
00886
00887 static bool LoadOldCompanyEconomy(LoadgameState *ls, int num)
00888 {
00889 Company *c = Company::Get(_current_company_id);
00890
00891 if (!LoadChunk(ls, &c->cur_economy, _company_economy_chunk)) return false;
00892
00893
00894 c->cur_economy.income = -c->cur_economy.income;
00895 c->cur_economy.expenses = -c->cur_economy.expenses;
00896
00897 for (uint i = 0; i < 24; i++) {
00898 if (!LoadChunk(ls, &c->old_economy[i], _company_economy_chunk)) return false;
00899
00900 c->old_economy[i].income = -c->old_economy[i].income;
00901 c->old_economy[i].expenses = -c->old_economy[i].expenses;
00902 }
00903
00904 return true;
00905 }
00906
00907 static const OldChunks _company_chunk[] = {
00908 OCL_VAR ( OC_UINT16, 1, &_old_string_id ),
00909 OCL_SVAR( OC_UINT32, Company, name_2 ),
00910 OCL_SVAR( OC_UINT32, Company, face ),
00911 OCL_VAR ( OC_UINT16, 1, &_old_string_id_2 ),
00912 OCL_SVAR( OC_UINT32, Company, president_name_2 ),
00913
00914 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, Company, money ),
00915 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, Company, current_loan ),
00916
00917 OCL_SVAR( OC_UINT8, Company, colour ),
00918 OCL_SVAR( OC_UINT8, Company, money_fraction ),
00919 OCL_SVAR( OC_UINT8, Company, quarters_of_bankruptcy ),
00920 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Company, bankrupt_asked ),
00921 OCL_SVAR( OC_FILE_U32 | OC_VAR_I64, Company, bankrupt_value ),
00922 OCL_SVAR( OC_UINT16, Company, bankrupt_timeout ),
00923
00924 OCL_SVAR( OC_TTD | OC_UINT32, Company, cargo_types ),
00925 OCL_SVAR( OC_TTO | OC_FILE_U16 | OC_VAR_U32, Company, cargo_types ),
00926
00927 OCL_CHUNK( 3, LoadOldCompanyYearly ),
00928 OCL_CHUNK( 1, LoadOldCompanyEconomy ),
00929
00930 OCL_SVAR( OC_FILE_U16 | OC_VAR_I32, Company, inaugurated_year),
00931 OCL_SVAR( OC_TILE, Company, last_build_coordinate ),
00932 OCL_SVAR( OC_UINT8, Company, num_valid_stat_ent ),
00933
00934 OCL_NULL( 230 ),
00935
00936 OCL_SVAR( OC_UINT8, Company, block_preview ),
00937 OCL_CNULL( OC_TTD, 1 ),
00938 OCL_SVAR( OC_TTD | OC_UINT8, Company, avail_railtypes ),
00939 OCL_SVAR( OC_TILE, Company, location_of_HQ ),
00940 OCL_SVAR( OC_TTD | OC_UINT8, Company, share_owners[0] ),
00941 OCL_SVAR( OC_TTD | OC_UINT8, Company, share_owners[1] ),
00942 OCL_SVAR( OC_TTD | OC_UINT8, Company, share_owners[2] ),
00943 OCL_SVAR( OC_TTD | OC_UINT8, Company, share_owners[3] ),
00944
00945 OCL_CNULL( OC_TTD, 8 ),
00946
00947 OCL_END()
00948 };
00949
00950 static bool LoadOldCompany(LoadgameState *ls, int num)
00951 {
00952 Company *c = new (num) Company();
00953
00954 _current_company_id = (CompanyID)num;
00955
00956 if (!LoadChunk(ls, c, _company_chunk)) return false;
00957
00958 if (_old_string_id == 0) {
00959 delete c;
00960 return true;
00961 }
00962
00963 if (_savegame_type == SGT_TTO) {
00964
00965 if (HasBit(c->face, 27) && GB(c->face, 26, 1) == GB(c->face, 19, 1)) {
00966
00967 ClrBit(c->face, 27);
00968 }
00969
00970
00971 if (_old_string_id == 0 || _old_string_id == 0x4C00) {
00972 _old_string_id = STR_SV_UNNAMED;
00973 } else if (GB(_old_string_id, 8, 8) == 0x52) {
00974 _old_string_id += 0x2A00;
00975 } else {
00976 _old_string_id = RemapOldStringID(_old_string_id += 0x240D);
00977 }
00978 c->name_1 = _old_string_id;
00979
00980
00981 switch (_old_string_id_2) {
00982 case 0x4CDA: _old_string_id_2 = SPECSTR_PRESIDENT_NAME; break;
00983 case 0x0006: _old_string_id_2 = STR_SV_EMPTY; break;
00984 default: _old_string_id_2 = _old_string_id_2 + 0x2A00; break;
00985 }
00986 c->president_name_1 = _old_string_id_2;
00987
00988 c->colour = RemapTTOColour(c->colour);
00989
00990 if (num != 0) c->is_ai = true;
00991 } else {
00992 c->name_1 = RemapOldStringID(_old_string_id);
00993 c->president_name_1 = RemapOldStringID(_old_string_id_2);
00994
00995 if (num == 0) {
00996
00997 if (c->name_1 == 0)
00998 c->name_1 = STR_SV_UNNAMED;
00999 } else {
01000
01001
01002 c->is_ai = true;
01003 }
01004
01005
01006
01007
01008
01009
01010 if (c->money == 893288) c->money = c->current_loan = 100000;
01011 }
01012
01013 _company_colours[num] = (Colours)c->colour;
01014 c->inaugurated_year -= ORIGINAL_BASE_YEAR;
01015
01016 return true;
01017 }
01018
01019 static uint32 _old_order_ptr;
01020 static uint16 _old_next_ptr;
01021 static VehicleID _current_vehicle_id;
01022
01023 static const OldChunks vehicle_train_chunk[] = {
01024 OCL_SVAR( OC_UINT8, Train, track ),
01025 OCL_SVAR( OC_UINT8, Train, force_proceed ),
01026 OCL_SVAR( OC_UINT16, Train, crash_anim_pos ),
01027 OCL_SVAR( OC_UINT8, Train, railtype ),
01028
01029 OCL_NULL( 5 ),
01030
01031 OCL_END()
01032 };
01033
01034 static const OldChunks vehicle_road_chunk[] = {
01035 OCL_SVAR( OC_UINT8, RoadVehicle, state ),
01036 OCL_SVAR( OC_UINT8, RoadVehicle, frame ),
01037 OCL_SVAR( OC_UINT16, RoadVehicle, blocked_ctr ),
01038 OCL_SVAR( OC_UINT8, RoadVehicle, overtaking ),
01039 OCL_SVAR( OC_UINT8, RoadVehicle, overtaking_ctr ),
01040 OCL_SVAR( OC_UINT16, RoadVehicle, crashed_ctr ),
01041 OCL_SVAR( OC_UINT8, RoadVehicle, reverse_ctr ),
01042
01043 OCL_NULL( 1 ),
01044
01045 OCL_END()
01046 };
01047
01048 static const OldChunks vehicle_ship_chunk[] = {
01049 OCL_SVAR( OC_UINT8, Ship, state ),
01050
01051 OCL_NULL( 9 ),
01052
01053 OCL_END()
01054 };
01055
01056 static const OldChunks vehicle_air_chunk[] = {
01057 OCL_SVAR( OC_UINT8, Aircraft, pos ),
01058 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Aircraft, targetairport ),
01059 OCL_SVAR( OC_UINT16, Aircraft, crashed_counter ),
01060 OCL_SVAR( OC_UINT8, Aircraft, state ),
01061
01062 OCL_NULL( 5 ),
01063
01064 OCL_END()
01065 };
01066
01067 static const OldChunks vehicle_effect_chunk[] = {
01068 OCL_SVAR( OC_UINT16, EffectVehicle, animation_state ),
01069 OCL_SVAR( OC_UINT8, EffectVehicle, animation_substate ),
01070
01071 OCL_NULL( 7 ),
01072
01073 OCL_END()
01074 };
01075
01076 static const OldChunks vehicle_disaster_chunk[] = {
01077 OCL_SVAR( OC_UINT16, DisasterVehicle, image_override ),
01078 OCL_SVAR( OC_UINT16, DisasterVehicle, big_ufo_destroyer_target ),
01079
01080 OCL_NULL( 6 ),
01081
01082 OCL_END()
01083 };
01084
01085 static const OldChunks vehicle_empty_chunk[] = {
01086 OCL_NULL( 10 ),
01087
01088 OCL_END()
01089 };
01090
01091 static bool LoadOldVehicleUnion(LoadgameState *ls, int num)
01092 {
01093 Vehicle *v = Vehicle::GetIfValid(_current_vehicle_id);
01094 uint temp = ls->total_read;
01095 bool res;
01096
01097 if (v == NULL) {
01098 res = LoadChunk(ls, NULL, vehicle_empty_chunk);
01099 } else {
01100 switch (v->type) {
01101 default: NOT_REACHED();
01102 case VEH_TRAIN : res = LoadChunk(ls, v, vehicle_train_chunk); break;
01103 case VEH_ROAD : res = LoadChunk(ls, v, vehicle_road_chunk); break;
01104 case VEH_SHIP : res = LoadChunk(ls, v, vehicle_ship_chunk); break;
01105 case VEH_AIRCRAFT: res = LoadChunk(ls, v, vehicle_air_chunk); break;
01106 case VEH_EFFECT : res = LoadChunk(ls, v, vehicle_effect_chunk); break;
01107 case VEH_DISASTER: res = LoadChunk(ls, v, vehicle_disaster_chunk); break;
01108 }
01109 }
01110
01111
01112 if (ls->total_read - temp != 10) {
01113 DEBUG(oldloader, 0, "Assert failed in VehicleUnion: invalid chunk size");
01114 return false;
01115 }
01116
01117 return res;
01118 }
01119
01120 static uint16 _cargo_count;
01121
01122 static const OldChunks vehicle_chunk[] = {
01123 OCL_SVAR( OC_UINT8, Vehicle, subtype ),
01124
01125 OCL_NULL( 2 ),
01126 OCL_NULL( 2 ),
01127
01128 OCL_VAR ( OC_UINT32, 1, &_old_order_ptr ),
01129 OCL_VAR ( OC_UINT16, 1, &_old_order ),
01130
01131 OCL_NULL ( 1 ),
01132 OCL_SVAR( OC_UINT8, Vehicle, cur_order_index ),
01133 OCL_SVAR( OC_TILE, Vehicle, dest_tile ),
01134 OCL_SVAR( OC_UINT16, Vehicle, load_unload_ticks ),
01135 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Vehicle, date_of_last_service ),
01136 OCL_SVAR( OC_UINT16, Vehicle, service_interval ),
01137 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Vehicle, last_station_visited ),
01138 OCL_SVAR( OC_TTD | OC_UINT8, Vehicle, tick_counter ),
01139 OCL_SVAR( OC_TTD | OC_UINT16, Vehicle, max_speed ),
01140 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Vehicle, max_speed ),
01141
01142 OCL_SVAR( OC_FILE_U16 | OC_VAR_I32, Vehicle, x_pos ),
01143 OCL_SVAR( OC_FILE_U16 | OC_VAR_I32, Vehicle, y_pos ),
01144 OCL_SVAR( OC_UINT8, Vehicle, z_pos ),
01145 OCL_SVAR( OC_UINT8, Vehicle, direction ),
01146 OCL_NULL( 2 ),
01147 OCL_NULL( 2 ),
01148 OCL_NULL( 1 ),
01149
01150 OCL_SVAR( OC_UINT8, Vehicle, owner ),
01151 OCL_SVAR( OC_TILE, Vehicle, tile ),
01152 OCL_SVAR( OC_UINT16, Vehicle, cur_image ),
01153
01154 OCL_NULL( 8 ),
01155
01156 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, Vehicle, vehstatus ),
01157 OCL_SVAR( OC_TTD | OC_UINT16, Vehicle, cur_speed ),
01158 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Vehicle, cur_speed ),
01159 OCL_SVAR( OC_UINT8, Vehicle, subspeed ),
01160 OCL_SVAR( OC_UINT8, Vehicle, acceleration ),
01161 OCL_SVAR( OC_UINT8, Vehicle, progress ),
01162
01163 OCL_SVAR( OC_UINT8, Vehicle, cargo_type ),
01164 OCL_SVAR( OC_TTD | OC_UINT16, Vehicle, cargo_cap ),
01165 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Vehicle, cargo_cap ),
01166 OCL_VAR ( OC_TTD | OC_UINT16, 1, &_cargo_count ),
01167 OCL_VAR ( OC_TTO | OC_FILE_U8 | OC_VAR_U16, 1, &_cargo_count ),
01168 OCL_VAR ( OC_UINT8, 1, &_cargo_source ),
01169 OCL_VAR ( OC_UINT8, 1, &_cargo_days ),
01170
01171 OCL_SVAR( OC_TTO | OC_UINT8, Vehicle, tick_counter ),
01172
01173 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Vehicle, age ),
01174 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Vehicle, max_age ),
01175 OCL_SVAR( OC_FILE_U8 | OC_VAR_I32, Vehicle, build_year ),
01176 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Vehicle, unitnumber ),
01177
01178 OCL_SVAR( OC_TTD | OC_UINT16, Vehicle, engine_type ),
01179 OCL_SVAR( OC_TTO | OC_FILE_U8 | OC_VAR_U16, Vehicle, engine_type ),
01180
01181 OCL_SVAR( OC_UINT8, Vehicle, spritenum ),
01182 OCL_SVAR( OC_UINT8, Vehicle, day_counter ),
01183
01184 OCL_SVAR( OC_UINT8, Vehicle, breakdowns_since_last_service ),
01185 OCL_SVAR( OC_UINT8, Vehicle, breakdown_ctr ),
01186 OCL_SVAR( OC_UINT8, Vehicle, breakdown_delay ),
01187 OCL_SVAR( OC_UINT8, Vehicle, breakdown_chance ),
01188
01189 OCL_CNULL( OC_TTO, 1 ),
01190
01191 OCL_SVAR( OC_UINT16, Vehicle, reliability ),
01192 OCL_SVAR( OC_UINT16, Vehicle, reliability_spd_dec ),
01193
01194 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, Vehicle, profit_this_year ),
01195 OCL_SVAR( OC_FILE_I32 | OC_VAR_I64, Vehicle, profit_last_year ),
01196
01197 OCL_VAR ( OC_UINT16, 1, &_old_next_ptr ),
01198
01199 OCL_SVAR( OC_FILE_U32 | OC_VAR_I64, Vehicle, value ),
01200
01201 OCL_VAR ( OC_UINT16, 1, &_old_string_id ),
01202
01203 OCL_CHUNK( 1, LoadOldVehicleUnion ),
01204
01205 OCL_CNULL( OC_TTO, 24 ),
01206 OCL_CNULL( OC_TTD, 20 ),
01207
01208 OCL_END()
01209 };
01210
01211 bool LoadOldVehicle(LoadgameState *ls, int num)
01212 {
01213
01214 ReadTTDPatchFlags();
01215
01216 for (uint i = 0; i < _old_vehicle_multiplier; i++) {
01217 _current_vehicle_id = num * _old_vehicle_multiplier + i;
01218
01219 Vehicle *v;
01220
01221 if (_savegame_type == SGT_TTO) {
01222 uint type = ReadByte(ls);
01223 switch (type) {
01224 default: return false;
01225 case 0x00 : v = NULL; break;
01226 case 0x25 :
01227 case 0x20 : v = new (_current_vehicle_id) Train(); break;
01228 case 0x21 : v = new (_current_vehicle_id) RoadVehicle(); break;
01229 case 0x22 : v = new (_current_vehicle_id) Ship(); break;
01230 case 0x23 : v = new (_current_vehicle_id) Aircraft(); break;
01231 case 0x24 : v = new (_current_vehicle_id) EffectVehicle(); break;
01232 case 0x26 : v = new (_current_vehicle_id) DisasterVehicle(); break;
01233 }
01234
01235 if (!LoadChunk(ls, v, vehicle_chunk)) return false;
01236 if (v == NULL) continue;
01237
01238 SpriteID sprite = v->cur_image;
01239
01240 if (IsInsideMM(sprite, 1460, 1465)) {
01241 sprite += 580;
01242 } else if (IsInsideMM(sprite, 2096, 2115)) {
01243 sprite += 977;
01244 } else if (IsInsideMM(sprite, 2396, 2436)) {
01245 sprite += 1305;
01246 } else if (IsInsideMM(sprite, 2516, 2539)) {
01247 sprite += 1385;
01248 }
01249 v->cur_image = sprite;
01250
01251 switch (v->type) {
01252 case VEH_TRAIN: {
01253 static const byte spriteset_rail[] = {
01254 0, 2, 4, 4, 8, 10, 12, 14, 16, 18, 20, 22, 40, 42, 44, 46,
01255 48, 52, 54, 66, 68, 70, 72, 74, 76, 78, 80, 82, 84, 86, 120, 122,
01256 124, 126, 128, 130, 132, 134, 136, 138, 140
01257 };
01258 if (v->spritenum / 2 >= lengthof(spriteset_rail)) return false;
01259 v->spritenum = spriteset_rail[v->spritenum / 2];
01260 Train::From(v)->railtype = type == 0x25 ? 1 : 0;
01261 break;
01262 }
01263
01264 case VEH_ROAD:
01265 if (v->spritenum >= 22) v->spritenum += 12;
01266 break;
01267
01268 case VEH_SHIP:
01269 v->spritenum += 2;
01270
01271 switch (v->spritenum) {
01272 case 2:
01273 if (v->cargo_type != CT_OIL) v->spritenum = 0;
01274 break;
01275 case 4:
01276 if (v->cargo_type == CT_MAIL) v->spritenum = 0;
01277 break;
01278 default:
01279 break;
01280 }
01281 break;
01282
01283 default:
01284 break;
01285 }
01286
01287 switch (_old_string_id) {
01288 case 0x0000: break;
01289 case 0x0006: _old_string_id = STR_SV_EMPTY; break;
01290 case 0x8495: _old_string_id = STR_SV_TRAIN_NAME; break;
01291 case 0x8842: _old_string_id = STR_SV_ROAD_VEHICLE_NAME; break;
01292 case 0x8C3B: _old_string_id = STR_SV_SHIP_NAME; break;
01293 case 0x9047: _old_string_id = STR_SV_AIRCRAFT_NAME; break;
01294 default: _old_string_id += 0x2A00; break;
01295 }
01296
01297 _old_vehicle_names[_current_vehicle_id] = _old_string_id;
01298 } else {
01299
01300 switch (ReadByte(ls)) {
01301 default: NOT_REACHED();
01302 case 0x00 : v = NULL; break;
01303 case 0x10 : v = new (_current_vehicle_id) Train(); break;
01304 case 0x11 : v = new (_current_vehicle_id) RoadVehicle(); break;
01305 case 0x12 : v = new (_current_vehicle_id) Ship(); break;
01306 case 0x13 : v = new (_current_vehicle_id) Aircraft(); break;
01307 case 0x14 : v = new (_current_vehicle_id) EffectVehicle(); break;
01308 case 0x15 : v = new (_current_vehicle_id) DisasterVehicle(); break;
01309 }
01310
01311 if (!LoadChunk(ls, v, vehicle_chunk)) return false;
01312 if (v == NULL) continue;
01313
01314 _old_vehicle_names[_current_vehicle_id] = RemapOldStringID(_old_string_id);
01315
01316
01317 if (v->index != _current_vehicle_id) {
01318 DEBUG(oldloader, 0, "Loading failed - vehicle-array is invalid");
01319 return false;
01320 }
01321 }
01322
01323 if (_old_order_ptr != 0 && _old_order_ptr != 0xFFFFFFFF) {
01324 uint max = _savegame_type == SGT_TTO ? 3000 : 5000;
01325 uint old_id = RemapOrderIndex(_old_order_ptr);
01326 if (old_id < max) v->orders.old = Order::Get(old_id);
01327 }
01328 v->current_order.AssignOrder(UnpackOldOrder(_old_order));
01329
01330 v->next = (Vehicle *)(size_t)_old_next_ptr;
01331
01332 if (_cargo_count != 0) {
01333 StationID source = (_cargo_source == 0xFF) ? INVALID_STATION : _cargo_source;
01334 TileIndex source_xy = (source != INVALID_STATION) ? Station::Get(source)->xy : 0;
01335 v->cargo.Append(new CargoPacket(_cargo_count, _cargo_days, source, source_xy, source_xy));
01336 }
01337 }
01338
01339 return true;
01340 }
01341
01342 static const OldChunks sign_chunk[] = {
01343 OCL_VAR ( OC_UINT16, 1, &_old_string_id ),
01344 OCL_SVAR( OC_FILE_U16 | OC_VAR_I32, Sign, x ),
01345 OCL_SVAR( OC_FILE_U16 | OC_VAR_I32, Sign, y ),
01346 OCL_SVAR( OC_FILE_U16 | OC_VAR_I8, Sign, z ),
01347
01348 OCL_NULL( 6 ),
01349
01350 OCL_END()
01351 };
01352
01353 static bool LoadOldSign(LoadgameState *ls, int num)
01354 {
01355 Sign *si = new (num) Sign();
01356 if (!LoadChunk(ls, si, sign_chunk)) return false;
01357
01358 if (_old_string_id != 0) {
01359 if (_savegame_type == SGT_TTO) {
01360 if (_old_string_id != 0x140A) si->name = CopyFromOldName(_old_string_id + 0x2A00);
01361 } else {
01362 si->name = CopyFromOldName(RemapOldStringID(_old_string_id));
01363 }
01364 si->owner = OWNER_NONE;
01365 } else {
01366 delete si;
01367 }
01368
01369 return true;
01370 }
01371
01372 static const OldChunks engine_chunk[] = {
01373 OCL_SVAR( OC_UINT16, Engine, company_avail ),
01374 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Engine, intro_date ),
01375 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, Engine, age ),
01376 OCL_SVAR( OC_UINT16, Engine, reliability ),
01377 OCL_SVAR( OC_UINT16, Engine, reliability_spd_dec ),
01378 OCL_SVAR( OC_UINT16, Engine, reliability_start ),
01379 OCL_SVAR( OC_UINT16, Engine, reliability_max ),
01380 OCL_SVAR( OC_UINT16, Engine, reliability_final ),
01381 OCL_SVAR( OC_UINT16, Engine, duration_phase_1 ),
01382 OCL_SVAR( OC_UINT16, Engine, duration_phase_2 ),
01383 OCL_SVAR( OC_UINT16, Engine, duration_phase_3 ),
01384
01385 OCL_NULL( 1 ),
01386 OCL_SVAR( OC_UINT8, Engine, flags ),
01387 OCL_SVAR( OC_UINT8, Engine, preview_company_rank ),
01388 OCL_SVAR( OC_UINT8, Engine, preview_wait ),
01389
01390 OCL_CNULL( OC_TTD, 2 ),
01391
01392 OCL_END()
01393 };
01394
01395 static bool LoadOldEngine(LoadgameState *ls, int num)
01396 {
01397 Engine *e = _savegame_type == SGT_TTO ? &_old_engines[num] : GetTempDataEngine(num);
01398 return LoadChunk(ls, e, engine_chunk);
01399 }
01400
01401 static bool LoadOldEngineName(LoadgameState *ls, int num)
01402 {
01403 Engine *e = GetTempDataEngine(num);
01404 e->name = CopyFromOldName(RemapOldStringID(ReadUint16(ls)));
01405 return true;
01406 }
01407
01408 static const OldChunks subsidy_chunk[] = {
01409 OCL_SVAR( OC_UINT8, Subsidy, cargo_type ),
01410 OCL_SVAR( OC_UINT8, Subsidy, remaining ),
01411 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Subsidy, src ),
01412 OCL_SVAR( OC_FILE_U8 | OC_VAR_U16, Subsidy, dst ),
01413
01414 OCL_END()
01415 };
01416
01417 static bool LoadOldSubsidy(LoadgameState *ls, int num)
01418 {
01419 Subsidy *s = new (num) Subsidy();
01420 bool ret = LoadChunk(ls, s, subsidy_chunk);
01421 if (s->cargo_type == CT_INVALID) delete s;
01422 return ret;
01423 }
01424
01425 static const OldChunks game_difficulty_chunk[] = {
01426 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, max_no_competitors ),
01427 OCL_NULL( 2),
01428 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, number_towns ),
01429 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, number_industries ),
01430 OCL_SVAR( OC_FILE_U16 | OC_VAR_U32, DifficultySettings, max_loan ),
01431 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, initial_interest ),
01432 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, vehicle_costs ),
01433 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, competitor_speed ),
01434 OCL_NULL( 2),
01435 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, vehicle_breakdowns ),
01436 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, subsidy_multiplier ),
01437 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, construction_cost ),
01438 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, terrain_type ),
01439 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, quantity_sea_lakes ),
01440 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, economy ),
01441 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, line_reverse_mode ),
01442 OCL_SVAR( OC_FILE_U16 | OC_VAR_U8, DifficultySettings, disasters ),
01443 OCL_END()
01444 };
01445
01446 static bool LoadOldGameDifficulty(LoadgameState *ls, int num)
01447 {
01448 bool ret = LoadChunk(ls, &_settings_game.difficulty, game_difficulty_chunk);
01449 _settings_game.difficulty.max_loan *= 1000;
01450 return ret;
01451 }
01452
01453
01454 static bool LoadOldMapPart1(LoadgameState *ls, int num)
01455 {
01456 if (_savegame_type == SGT_TTO) {
01457 MemSetT(_m, 0, OLD_MAP_SIZE);
01458 MemSetT(_me, 0, OLD_MAP_SIZE);
01459 }
01460
01461 for (uint i = 0; i < OLD_MAP_SIZE; i++) {
01462 _m[i].m1 = ReadByte(ls);
01463 }
01464 for (uint i = 0; i < OLD_MAP_SIZE; i++) {
01465 _m[i].m2 = ReadByte(ls);
01466 }
01467
01468 if (_savegame_type != SGT_TTO) {
01469 for (uint i = 0; i < OLD_MAP_SIZE; i++) {
01470 _old_map3[i * 2] = ReadByte(ls);
01471 _old_map3[i * 2 + 1] = ReadByte(ls);
01472 }
01473 for (uint i = 0; i < OLD_MAP_SIZE / 4; i++) {
01474 byte b = ReadByte(ls);
01475 _m[i * 4 + 0].m6 = GB(b, 0, 2);
01476 _m[i * 4 + 1].m6 = GB(b, 2, 2);
01477 _m[i * 4 + 2].m6 = GB(b, 4, 2);
01478 _m[i * 4 + 3].m6 = GB(b, 6, 2);
01479 }
01480 }
01481
01482 return !ls->failed;
01483 }
01484
01485 static bool LoadOldMapPart2(LoadgameState *ls, int num)
01486 {
01487 uint i;
01488
01489 for (i = 0; i < OLD_MAP_SIZE; i++) {
01490 _m[i].type_height = ReadByte(ls);
01491 }
01492 for (i = 0; i < OLD_MAP_SIZE; i++) {
01493 _m[i].m5 = ReadByte(ls);
01494 }
01495
01496 return !ls->failed;
01497 }
01498
01499 static bool LoadTTDPatchExtraChunks(LoadgameState *ls, int num)
01500 {
01501 ReadTTDPatchFlags();
01502
01503 DEBUG(oldloader, 2, "Found %d extra chunk(s)", _old_extra_chunk_nums);
01504
01505 for (int i = 0; i != _old_extra_chunk_nums; i++) {
01506 uint16 id = ReadUint16(ls);
01507 uint32 len = ReadUint32(ls);
01508
01509 switch (id) {
01510
01511
01512 case 0x2:
01513 case 0x8004: {
01514
01515 ReadUint32(ls); ReadByte(ls); len -= 5;
01516
01517 ClearGRFConfigList(&_grfconfig);
01518 while (len != 0) {
01519 uint32 grfid = ReadUint32(ls);
01520
01521 if (ReadByte(ls) == 1) {
01522 GRFConfig *c = CallocT<GRFConfig>(1);
01523 c->grfid = grfid;
01524 c->filename = strdup("TTDP game, no information");
01525
01526 AppendToGRFConfigList(&_grfconfig, c);
01527 DEBUG(oldloader, 3, "TTDPatch game using GRF file with GRFID %0X", BSWAP32(c->grfid));
01528 }
01529 len -= 5;
01530 };
01531
01532
01533 AppendStaticGRFConfigs(&_grfconfig);
01534 } break;
01535
01536
01537 case 0x3:
01538 _ttdp_version = ReadUint32(ls);
01539 DEBUG(oldloader, 3, "Game saved with TTDPatch version %d.%d.%d r%d",
01540 GB(_ttdp_version, 24, 8), GB(_ttdp_version, 20, 4), GB(_ttdp_version, 16, 4), GB(_ttdp_version, 0, 16));
01541 len -= 4;
01542 while (len-- != 0) ReadByte(ls);
01543 break;
01544
01545 default:
01546 DEBUG(oldloader, 4, "Skipping unknown extra chunk %X", id);
01547 while (len-- != 0) ReadByte(ls);
01548 break;
01549 }
01550 }
01551
01552 return !ls->failed;
01553 }
01554
01555 extern TileIndex _cur_tileloop_tile;
01556 static const OldChunks main_chunk[] = {
01557 OCL_ASSERT( OC_TTD, 0 ),
01558 OCL_ASSERT( OC_TTO, 0 ),
01559 OCL_VAR ( OC_FILE_U16 | OC_VAR_U32, 1, &_date ),
01560 OCL_VAR ( OC_UINT16, 1, &_date_fract ),
01561 OCL_NULL( 600 ),
01562 OCL_VAR ( OC_UINT32, 2, &_random.state ),
01563
01564 OCL_ASSERT( OC_TTD, 0x264 ),
01565 OCL_ASSERT( OC_TTO, 0x264 ),
01566
01567 OCL_CCHUNK( OC_TTD, 70, LoadOldTown ),
01568 OCL_CCHUNK( OC_TTO, 80, LoadOldTown ),
01569
01570 OCL_ASSERT( OC_TTD, 0x1C18 ),
01571 OCL_ASSERT( OC_TTO, 0x1AC4 ),
01572
01573 OCL_CCHUNK( OC_TTD, 5000, LoadOldOrder ),
01574 OCL_CCHUNK( OC_TTO, 3000, LoadOldOrder ),
01575
01576 OCL_ASSERT( OC_TTD, 0x4328 ),
01577 OCL_ASSERT( OC_TTO, 0x3234 ),
01578
01579 OCL_CHUNK( 1, LoadOldAnimTileList ),
01580 OCL_NULL( 4 ),
01581
01582 OCL_ASSERT( OC_TTO, 0x3438 ),
01583
01584 OCL_CCHUNK( OC_TTD, 255, LoadOldDepot ),
01585 OCL_CCHUNK( OC_TTO, 252, LoadOldDepot ),
01586
01587 OCL_ASSERT( OC_TTD, 0x4B26 ),
01588 OCL_ASSERT( OC_TTO, 0x3A20 ),
01589
01590 OCL_NULL( 4 ),
01591 OCL_NULL( 2 ),
01592 OCL_NULL( 2 ),
01593
01594 OCL_VAR ( OC_FILE_U16 | OC_VAR_U8, 1, &_age_cargo_skip_counter ),
01595 OCL_VAR ( OC_UINT16, 1, &_tick_counter ),
01596 OCL_VAR ( OC_TILE, 1, &_cur_tileloop_tile ),
01597
01598 OCL_ASSERT( OC_TTO, 0x3A2E ),
01599
01600 OCL_CNULL( OC_TTO, 48 * 6 ),
01601 OCL_CNULL( OC_TTD, 49 * 6 ),
01602
01603 OCL_ASSERT( OC_TTO, 0x3B4E ),
01604
01605 OCL_CNULL( OC_TTO, 11 * 8 ),
01606 OCL_CNULL( OC_TTD, 12 * 8 ),
01607
01608 OCL_ASSERT( OC_TTD, 0x4CBA ),
01609 OCL_ASSERT( OC_TTO, 0x3BA6 ),
01610
01611 OCL_CHUNK( 1, LoadOldMapPart1 ),
01612
01613 OCL_ASSERT( OC_TTD, 0x48CBA ),
01614 OCL_ASSERT( OC_TTO, 0x23BA6 ),
01615
01616 OCL_CCHUNK( OC_TTD, 250, LoadOldStation ),
01617 OCL_CCHUNK( OC_TTO, 200, LoadOldStation ),
01618
01619 OCL_ASSERT( OC_TTO, 0x29E16 ),
01620
01621 OCL_CCHUNK( OC_TTD, 90, LoadOldIndustry ),
01622 OCL_CCHUNK( OC_TTO, 100, LoadOldIndustry ),
01623
01624 OCL_ASSERT( OC_TTO, 0x2ADB6 ),
01625
01626 OCL_CHUNK( 8, LoadOldCompany ),
01627
01628 OCL_ASSERT( OC_TTD, 0x547F2 ),
01629 OCL_ASSERT( OC_TTO, 0x2C746 ),
01630
01631 OCL_CCHUNK( OC_TTD, 850, LoadOldVehicle ),
01632 OCL_CCHUNK( OC_TTO, 800, LoadOldVehicle ),
01633
01634 OCL_ASSERT( OC_TTD, 0x6F0F2 ),
01635 OCL_ASSERT( OC_TTO, 0x45746 ),
01636
01637 OCL_VAR ( OC_TTD | OC_UINT8 | OC_DEREFERENCE_POINTER, 32 * 500, &_old_name_array ),
01638 OCL_VAR ( OC_TTO | OC_UINT8 | OC_DEREFERENCE_POINTER, 24 * 200, &_old_name_array ),
01639
01640 OCL_ASSERT( OC_TTO, 0x46A06 ),
01641
01642 OCL_NULL( 0x2000 ),
01643
01644 OCL_CHUNK( 40, LoadOldSign ),
01645
01646 OCL_ASSERT( OC_TTO, 0x48C36 ),
01647
01648 OCL_CCHUNK( OC_TTD, 256, LoadOldEngine ),
01649 OCL_CCHUNK( OC_TTO, 103, LoadOldEngine ),
01650
01651 OCL_ASSERT( OC_TTO, 0x496AC ),
01652
01653 OCL_VAR ( OC_UINT16, 1, &_vehicle_id_ctr_day ),
01654
01655 OCL_CHUNK( 8, LoadOldSubsidy ),
01656
01657 OCL_ASSERT( OC_TTO, 0x496CE ),
01658
01659 OCL_VAR ( OC_FILE_U16 | OC_VAR_U32, 1, &_next_competitor_start ),
01660
01661 OCL_CNULL( OC_TTO, 2 ),
01662
01663 OCL_VAR ( OC_FILE_I16 | OC_VAR_I32, 1, &_saved_scrollpos_x ),
01664 OCL_VAR ( OC_FILE_I16 | OC_VAR_I32, 1, &_saved_scrollpos_y ),
01665 OCL_VAR ( OC_FILE_U16 | OC_VAR_U8, 1, &_saved_scrollpos_zoom ),
01666
01667 OCL_NULL( 4 ),
01668 OCL_VAR ( OC_FILE_U32 | OC_VAR_I64, 1, &_economy.old_max_loan_unround ),
01669 OCL_VAR ( OC_INT16, 1, &_economy.fluct ),
01670
01671 OCL_VAR ( OC_UINT16, 1, &_disaster_delay ),
01672
01673 OCL_ASSERT( OC_TTO, 0x496E4 ),
01674
01675 OCL_CNULL( OC_TTD, 144 ),
01676
01677 OCL_CCHUNK( OC_TTD, 256, LoadOldEngineName ),
01678
01679 OCL_CNULL( OC_TTD, 144 ),
01680 OCL_NULL( 2 ),
01681 OCL_NULL( 1 ),
01682
01683 OCL_VAR ( OC_UINT8, 1, &_settings_game.locale.currency ),
01684 OCL_VAR ( OC_UINT8, 1, &_settings_game.locale.units ),
01685 OCL_VAR ( OC_FILE_U8 | OC_VAR_U32, 1, &_cur_company_tick_index ),
01686
01687 OCL_NULL( 2 ),
01688 OCL_NULL( 8 ),
01689
01690 OCL_VAR ( OC_UINT8, 1, &_economy.infl_amount ),
01691 OCL_VAR ( OC_UINT8, 1, &_economy.infl_amount_pr ),
01692 OCL_VAR ( OC_UINT8, 1, &_economy.interest_rate ),
01693 OCL_NULL( 1 ),
01694 OCL_VAR ( OC_UINT8, 1, &_settings_game.vehicle.road_side ),
01695 OCL_VAR ( OC_UINT8, 1, &_settings_game.game_creation.town_name ),
01696
01697 OCL_CHUNK( 1, LoadOldGameDifficulty ),
01698
01699 OCL_ASSERT( OC_TTD, 0x77130 ),
01700
01701 OCL_VAR ( OC_UINT8, 1, &_settings_game.difficulty.diff_level ),
01702
01703 OCL_VAR ( OC_TTD | OC_UINT8, 1, &_settings_game.game_creation.landscape ),
01704 OCL_VAR ( OC_TTD | OC_UINT8, 1, &_trees_tick_ctr ),
01705
01706 OCL_CNULL( OC_TTD, 1 ),
01707 OCL_VAR ( OC_TTD | OC_UINT8, 1, &_settings_game.game_creation.snow_line ),
01708
01709 OCL_CNULL( OC_TTD, 32 ),
01710 OCL_CNULL( OC_TTD, 36 ),
01711
01712 OCL_ASSERT( OC_TTD, 0x77179 ),
01713 OCL_ASSERT( OC_TTO, 0x4971D ),
01714
01715 OCL_CHUNK( 1, LoadOldMapPart2 ),
01716
01717 OCL_ASSERT( OC_TTD, 0x97179 ),
01718 OCL_ASSERT( OC_TTO, 0x6971D ),
01719
01720
01721 OCL_CHUNK(1, LoadTTDPatchExtraChunks),
01722
01723 OCL_END()
01724 };
01725
01726 bool LoadTTDMain(LoadgameState *ls)
01727 {
01728 _read_ttdpatch_flags = false;
01729 _ttdp_version = 0;
01730
01731 DEBUG(oldloader, 3, "Reading main chunk...");
01732
01733 SmallStackSafeStackAlloc<byte, OLD_MAP_SIZE * 2> map3;
01734 _old_map3 = map3.data;
01735 _old_vehicle_names = NULL;
01736 if (!LoadChunk(ls, NULL, main_chunk)) {
01737 DEBUG(oldloader, 0, "Loading failed");
01738 free(_old_vehicle_names);
01739 return false;
01740 }
01741 DEBUG(oldloader, 3, "Done, converting game data...");
01742
01743 FixTTDMapArray();
01744 FixTTDDepots();
01745
01746
01747 _settings_game.game_creation.landscape = _settings_game.game_creation.landscape & 0xF;
01748
01749
01750 FixOldTowns();
01751 FixOldVehicles();
01752
01753
01754 _settings_game.difficulty.town_council_tolerance = Clamp(_settings_game.difficulty.diff_level, 0, 2);
01755
01756 DEBUG(oldloader, 3, "Finished converting game data");
01757 DEBUG(oldloader, 1, "TTD(Patch) savegame successfully converted");
01758
01759 free(_old_vehicle_names);
01760
01761 return true;
01762 }
01763
01764 bool LoadTTOMain(LoadgameState *ls)
01765 {
01766 DEBUG(oldloader, 3, "Reading main chunk...");
01767
01768 SmallStackSafeStackAlloc<byte, 103 * sizeof(Engine)> engines;
01769 _old_engines = (Engine *)engines.data;
01770 SmallStackSafeStackAlloc<StringID, 800> vehnames;
01771 _old_vehicle_names = vehnames.data;
01772
01773
01774 if (!LoadChunk(ls, NULL, main_chunk)) {
01775 DEBUG(oldloader, 0, "Loading failed");
01776 return false;
01777 }
01778 DEBUG(oldloader, 3, "Done, converting game data...");
01779
01780 if (_settings_game.game_creation.town_name != 0) _settings_game.game_creation.town_name++;
01781
01782 _settings_game.game_creation.landscape = 0;
01783 _trees_tick_ctr = 0xFF;
01784
01785 if (!FixTTOMapArray() || !FixTTOEngines()) {
01786 DEBUG(oldloader, 0, "Conversion failed");
01787 return false;
01788 }
01789
01790 FixOldTowns();
01791 FixOldVehicles();
01792 FixTTOCompanies();
01793
01794
01795 _settings_game.difficulty.town_council_tolerance = Clamp(_settings_game.difficulty.diff_level, 0, 2);
01796
01797
01798
01799
01800
01801 _economy.inflation_payment = min(_economy.inflation_payment * 124 / 74, MAX_INFLATION);
01802
01803 DEBUG(oldloader, 3, "Finished converting game data");
01804 DEBUG(oldloader, 1, "TTO savegame successfully converted");
01805
01806 return true;
01807 }