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