tron@2186: /* $Id$ */ tron@2186: truelight@1313: #include "stdafx.h" Darkvater@1891: #include "openttd.h" truelight@1313: #include "depot.h" tron@2163: #include "functions.h" truelight@1313: #include "tile.h" truelight@1313: #include "map.h" truelight@1313: #include "table/strings.h" truelight@1313: #include "saveload.h" truelight@1313: #include "order.h" truelight@1313: truelight@1313: enum { truelight@1313: /* Max depots: 64000 (8 * 8000) */ truelight@1313: DEPOT_POOL_BLOCK_SIZE_BITS = 3, /* In bits, so (1 << 3) == 8 */ truelight@1313: DEPOT_POOL_MAX_BLOCKS = 8000, truelight@1313: }; truelight@1313: truelight@1313: /** truelight@1313: * Called if a new block is added to the depot-pool truelight@1313: */ truelight@1313: static void DepotPoolNewBlock(uint start_item) truelight@1313: { truelight@1313: Depot *depot; truelight@1313: truelight@1313: FOR_ALL_DEPOTS_FROM(depot, start_item) truelight@1313: depot->index = start_item++; truelight@1313: } truelight@1313: truelight@1313: /* Initialize the town-pool */ truelight@1313: MemoryPool _depot_pool = { "Depots", DEPOT_POOL_MAX_BLOCKS, DEPOT_POOL_BLOCK_SIZE_BITS, sizeof(Depot), &DepotPoolNewBlock, 0, 0, NULL }; truelight@1313: truelight@1313: truelight@1313: /** truelight@1313: * Gets a depot from a tile truelight@1313: * truelight@1313: * @return Returns the depot if the tile had a depot, else it returns NULL truelight@1313: */ tron@1977: Depot *GetDepotByTile(TileIndex tile) truelight@1313: { truelight@1313: Depot *depot; truelight@1313: truelight@1313: FOR_ALL_DEPOTS(depot) { truelight@1313: if (depot->xy == tile) truelight@1313: return depot; truelight@1313: } truelight@1313: truelight@1313: return NULL; truelight@1313: } truelight@1313: truelight@1313: /** truelight@1313: * Allocate a new depot truelight@1313: */ truelight@1313: Depot *AllocateDepot(void) truelight@1313: { truelight@1313: Depot *depot; truelight@1313: truelight@1313: FOR_ALL_DEPOTS(depot) { matthijs@1330: if (!IsValidDepot(depot)) { truelight@1313: uint index = depot->index; truelight@1313: truelight@1313: memset(depot, 0, sizeof(Depot)); truelight@1313: depot->index = index; truelight@1313: truelight@1313: return depot; truelight@1313: } truelight@1313: } truelight@1313: truelight@1313: /* Check if we can add a block to the pool */ truelight@1313: if (AddBlockToPool(&_depot_pool)) truelight@1313: return AllocateDepot(); truelight@1313: truelight@1313: return NULL; truelight@1313: } truelight@1313: truelight@1313: /** truelight@1313: * Delete a depot truelight@1313: */ tron@1977: void DoDeleteDepot(TileIndex tile) truelight@1313: { truelight@1313: Order order; truelight@1313: Depot *depot; truelight@1313: truelight@1313: /* Get the depot */ truelight@1313: depot = GetDepotByTile(tile); truelight@1313: truelight@1313: /* Clear the tile */ truelight@1313: DoClearSquare(tile); truelight@1313: truelight@1313: /* Clear the depot */ truelight@1313: depot->xy = 0; truelight@1313: truelight@1313: /* Clear the depot from all order-lists */ truelight@1313: order.type = OT_GOTO_DEPOT; truelight@1313: order.station = depot->index; truelight@1313: DeleteDestinationFromVehicleOrder(order); truelight@1313: truelight@1313: /* Delete the depot-window */ truelight@1313: DeleteWindowById(WC_VEHICLE_DEPOT, tile); truelight@1313: } truelight@1313: truelight@1313: void InitializeDepot(void) truelight@1313: { truelight@1313: CleanPool(&_depot_pool); truelight@1313: AddBlockToPool(&_depot_pool); truelight@1313: } truelight@1313: truelight@1313: Darkvater@1881: static const SaveLoad _depot_desc[] = { truelight@1313: SLE_CONDVAR(Depot, xy, SLE_FILE_U16 | SLE_VAR_U32, 0, 5), truelight@1313: SLE_CONDVAR(Depot, xy, SLE_UINT32, 6, 255), truelight@1313: SLE_VAR(Depot,town_index, SLE_UINT16), truelight@1313: SLE_END() truelight@1313: }; truelight@1313: truelight@1313: static void Save_DEPT(void) truelight@1313: { truelight@1313: Depot *depot; truelight@1313: truelight@1313: FOR_ALL_DEPOTS(depot) { matthijs@1330: if (IsValidDepot(depot)) { truelight@1313: SlSetArrayIndex(depot->index); truelight@1313: SlObject(depot, _depot_desc); truelight@1313: } truelight@1313: } truelight@1313: } truelight@1313: truelight@1313: static void Load_DEPT(void) truelight@1313: { truelight@1313: int index; truelight@1313: truelight@1313: while ((index = SlIterateArray()) != -1) { truelight@1313: Depot *depot; truelight@1313: truelight@1313: if (!AddBlockIfNeeded(&_depot_pool, index)) truelight@1313: error("Depots: failed loading savegame: too many depots"); truelight@1313: truelight@1313: depot = GetDepot(index); truelight@1313: SlObject(depot, _depot_desc); truelight@1313: } truelight@1313: } truelight@1313: truelight@1313: const ChunkHandler _depot_chunk_handlers[] = { truelight@1313: { 'DEPT', Save_DEPT, Load_DEPT, CH_ARRAY | CH_LAST}, truelight@1313: };