2005-07-24 14:12:37 +00:00
/* $Id$ */
2009-08-21 20:21:05 +00:00
/*
* This file is part of OpenTTD .
* OpenTTD is free software ; you can redistribute it and / or modify it under the terms of the GNU General Public License as published by the Free Software Foundation , version 2.
* OpenTTD is distributed in the hope that it will be useful , but WITHOUT ANY WARRANTY ; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE .
* See the GNU General Public License for more details . You should have received a copy of the GNU General Public License along with OpenTTD . If not , see < http : //www.gnu.org/licenses/>.
*/
2007-12-27 13:35:39 +00:00
/** @file vehicle_base.h Base class for all vehicles. */
2007-04-04 04:08:47 +00:00
2007-12-27 13:35:39 +00:00
# ifndef VEHICLE_BASE_H
# define VEHICLE_BASE_H
2004-08-09 17:04:08 +00:00
2013-05-19 14:22:04 +00:00
# include "core/smallmap_type.hpp"
2007-12-18 20:38:16 +00:00
# include "track_type.h"
2007-12-23 10:56:02 +00:00
# include "command_type.h"
2008-03-30 23:24:18 +00:00
# include "order_base.h"
2007-06-22 11:58:59 +00:00
# include "cargopacket.h"
2007-06-21 16:17:47 +00:00
# include "texteff.hpp"
2008-03-28 18:00:38 +00:00
# include "engine_type.h"
2008-04-27 20:09:29 +00:00
# include "order_func.h"
2008-05-07 09:07:19 +00:00
# include "transport_type.h"
2010-08-18 15:15:59 +00:00
# include "group_type.h"
2012-07-29 16:44:39 +00:00
# include "base_consist.h"
2016-05-22 11:30:25 +00:00
# include "network/network.h"
2013-08-20 21:22:37 +00:00
# include <list>
# include <map>
2007-02-13 10:26:53 +00:00
2010-11-05 16:34:22 +00:00
/** Vehicle status bits in #Vehicle::vehstatus. */
2005-05-02 23:59:11 +00:00
enum VehStatus {
2010-11-05 16:34:22 +00:00
VS_HIDDEN = 0x01 , ///< Vehicle is not visible.
VS_STOPPED = 0x02 , ///< Vehicle is stopped by the player.
VS_UNCLICKABLE = 0x04 , ///< Vehicle is not clickable by the user (shadow vehicles).
VS_DEFPAL = 0x08 , ///< Use default vehicle palette. @see DoDrawVehicle
VS_TRAIN_SLOWING = 0x10 , ///< Train is slowing down.
VS_SHADOW = 0x20 , ///< Vehicle is a shadow vehicle.
VS_AIRCRAFT_BROKEN = 0x40 , ///< Aircraft is broken down.
VS_CRASHED = 0x80 , ///< Vehicle is crashed.
2005-05-02 23:59:11 +00:00
} ;
2010-11-05 16:34:22 +00:00
/** Bit numbers in #Vehicle::vehicle_flags. */
2007-02-28 17:18:36 +00:00
enum VehicleFlags {
2010-11-05 16:34:22 +00:00
VF_LOADING_FINISHED , ///< Vehicle has finished loading.
VF_CARGO_UNLOADING , ///< Vehicle is unloading cargo.
VF_BUILT_AS_PROTOTYPE , ///< Vehicle is a prototype (accepted as exclusive preview).
2008-11-18 23:53:37 +00:00
VF_TIMETABLE_STARTED , ///< Whether the vehicle has started running on the timetable yet.
VF_AUTOFILL_TIMETABLE , ///< Whether the vehicle should fill in the timetable automatically.
VF_AUTOFILL_PRES_WAIT_TIME , ///< Whether non-destructive auto-fill should preserve waiting times
2010-08-15 22:37:30 +00:00
VF_STOP_LOADING , ///< Don't load anymore during the next load cycle.
2010-12-13 21:52:39 +00:00
VF_PATHFINDER_LOST , ///< Vehicle's pathfinder is lost.
2013-02-14 17:24:55 +00:00
VF_SERVINT_IS_CUSTOM , ///< Service interval is custom.
VF_SERVINT_IS_PERCENT , ///< Service interval is percent.
2006-12-02 16:56:32 +00:00
} ;
2010-11-06 12:39:18 +00:00
/** Bit numbers used to indicate which of the #NewGRFCache values are valid. */
enum NewGRFCacheValidValues {
NCVV_POSITION_CONSIST_LENGTH = 0 , ///< This bit will be set if the NewGRF var 40 currently stored is valid.
NCVV_POSITION_SAME_ID_LENGTH = 1 , ///< This bit will be set if the NewGRF var 41 currently stored is valid.
NCVV_CONSIST_CARGO_INFORMATION = 2 , ///< This bit will be set if the NewGRF var 42 currently stored is valid.
NCVV_COMPANY_INFORMATION = 3 , ///< This bit will be set if the NewGRF var 43 currently stored is valid.
2013-12-13 20:21:04 +00:00
NCVV_POSITION_IN_VEHICLE = 4 , ///< This bit will be set if the NewGRF var 4D currently stored is valid.
2010-11-27 21:09:41 +00:00
NCVV_END , ///< End of the bits.
2010-11-06 12:39:18 +00:00
} ;
2010-11-05 15:48:30 +00:00
/** Cached often queried (NewGRF) values */
2010-11-06 12:37:55 +00:00
struct NewGRFCache {
/* Values calculated when they are requested for the first time after invalidating the NewGRF cache. */
uint32 position_consist_length ; ///< Cache for NewGRF var 40.
uint32 position_same_id_length ; ///< Cache for NewGRF var 41.
2011-12-12 19:30:36 +00:00
uint32 consist_cargo_information ; ///< Cache for NewGRF var 42. (Note: The cargotype is untranslated in the cache because the accessing GRF is yet unknown.)
2010-11-06 12:37:55 +00:00
uint32 company_information ; ///< Cache for NewGRF var 43.
2013-12-13 20:21:04 +00:00
uint32 position_in_vehicle ; ///< Cache for NewGRF var 4D.
2010-11-06 12:37:55 +00:00
uint8 cache_valid ; ///< Bitset that indicates which cache values are valid.
2009-05-23 09:10:56 +00:00
} ;
2010-11-18 14:04:36 +00:00
/** Meaning of the various bits of the visual effect. */
enum VisualEffect {
VE_OFFSET_START = 0 , ///< First bit that contains the offset (0 = front, 8 = centre, 15 = rear)
VE_OFFSET_COUNT = 4 , ///< Number of bits used for the offset
VE_OFFSET_CENTRE = 8 , ///< Value of offset corresponding to a position above the centre of the vehicle
VE_TYPE_START = 4 , ///< First bit used for the type of effect
VE_TYPE_COUNT = 2 , ///< Number of bits used for the effect type
VE_TYPE_DEFAULT = 0 , ///< Use default from engine class
VE_TYPE_STEAM = 1 , ///< Steam plumes
VE_TYPE_DIESEL = 2 , ///< Diesel fumes
VE_TYPE_ELECTRIC = 3 , ///< Electric sparks
VE_DISABLE_EFFECT = 6 , ///< Flag to disable visual effect
2014-08-17 14:53:11 +00:00
VE_ADVANCED_EFFECT = VE_DISABLE_EFFECT , ///< Flag for advanced effects
2010-11-18 14:04:36 +00:00
VE_DISABLE_WAGON_POWER = 7 , ///< Flag to disable wagon power
2010-11-18 14:20:03 +00:00
VE_DEFAULT = 0xFF , ///< Default value to indicate that visual effect should be based on engine class
2010-11-18 14:04:36 +00:00
} ;
2014-08-17 14:52:48 +00:00
/** Models for spawning visual effects. */
enum VisualEffectSpawnModel {
VESM_NONE = 0 , ///< No visual effect
VESM_STEAM , ///< Steam model
VESM_DIESEL , ///< Diesel model
VESM_ELECTRIC , ///< Electric model
VESM_END
} ;
2011-01-29 17:21:39 +00:00
/**
* Enum to handle ground vehicle subtypes .
* This is defined here instead of at # GroundVehicle because some common function require access to these flags .
* Do not access it directly unless you have to . Use the subtype access functions .
*/
enum GroundVehicleSubtypeFlags {
GVSF_FRONT = 0 , ///< Leading engine of a consist.
GVSF_ARTICULATED_PART = 1 , ///< Articulated part of an engine.
GVSF_WAGON = 2 , ///< Wagon (not used for road vehicles).
GVSF_ENGINE = 3 , ///< Engine that can be front engine, but might be placed behind another engine (not used for road vehicles).
GVSF_FREE_WAGON = 4 , ///< First in a wagon chain (in depot) (not used for road vehicles).
GVSF_MULTIHEADED = 5 , ///< Engine is multiheaded (not used for road vehicles).
} ;
2010-11-06 12:53:31 +00:00
/** Cached often queried values common to all vehicles. */
struct VehicleCache {
2011-08-03 20:55:08 +00:00
uint16 cached_max_speed ; ///< Maximum speed of the consist (minimum of the max speed of all vehicles in the consist).
uint16 cached_cargo_age_period ; ///< Number of ticks before carried cargo is aged.
2010-11-18 14:04:36 +00:00
byte cached_vis_effect ; ///< Visual effect to show (see #VisualEffect)
2010-11-06 12:53:31 +00:00
} ;
2010-08-19 20:58:30 +00:00
/** A vehicle pool for a little over 1 million vehicles. */
typedef Pool < Vehicle , VehicleID , 512 , 0xFF000 > VehiclePool ;
2009-05-22 15:13:50 +00:00
extern VehiclePool _vehicle_pool ;
2004-08-09 17:04:08 +00:00
2007-09-07 22:06:52 +00:00
/* Some declarations of functions, so we can make them friendly */
2007-08-30 13:09:44 +00:00
struct SaveLoad ;
2010-12-14 21:31:00 +00:00
struct GroundVehicleCache ;
2007-09-07 22:06:52 +00:00
extern const SaveLoad * GetVehicleDescription ( VehicleType vt ) ;
struct LoadgameState ;
extern bool LoadOldVehicle ( LoadgameState * ls , int num ) ;
2009-05-22 15:13:50 +00:00
extern void FixOldVehicles ( ) ;
2007-08-30 13:09:44 +00:00
2011-11-01 00:23:41 +00:00
struct GRFFile ;
2013-08-20 21:22:37 +00:00
/**
* Simulated cargo type and capacity for prediction of future links .
*/
struct RefitDesc {
CargoID cargo ; ///< Cargo type the vehicle will be carrying.
uint16 capacity ; ///< Capacity the vehicle will have.
uint16 remaining ; ///< Capacity remaining from before the previous refit.
RefitDesc ( CargoID cargo , uint16 capacity , uint16 remaining ) :
cargo ( cargo ) , capacity ( capacity ) , remaining ( remaining ) { }
} ;
2011-01-29 21:37:11 +00:00
/** %Vehicle data structure. */
2012-07-29 16:44:39 +00:00
struct Vehicle : VehiclePool : : PoolItem < & _vehicle_pool > , BaseVehicle , BaseConsist {
2007-08-30 13:09:44 +00:00
private :
2013-08-20 21:22:37 +00:00
typedef std : : list < RefitDesc > RefitList ;
typedef std : : map < CargoID , uint > CapacitiesMap ;
2010-11-05 15:48:30 +00:00
Vehicle * next ; ///< pointer to the next vehicle in the chain
Vehicle * previous ; ///< NOSAVE: pointer to the previous vehicle in the chain
Vehicle * first ; ///< NOSAVE: pointer to the first vehicle in the chain
2008-08-17 19:56:17 +00:00
2010-11-05 15:48:30 +00:00
Vehicle * next_shared ; ///< pointer to the next vehicle that shares the order
Vehicle * previous_shared ; ///< NOSAVE: pointer to the previous vehicle in the shared order chain
2013-08-20 21:22:37 +00:00
2007-08-30 13:09:44 +00:00
public :
2008-04-21 08:35:27 +00:00
friend const SaveLoad * GetVehicleDescription ( VehicleType vt ) ; ///< So we can use private/protected variables in the saveload code
2009-05-22 15:13:50 +00:00
friend void FixOldVehicles ( ) ;
2011-05-14 18:35:40 +00:00
friend void AfterLoadVehicles ( bool part_of_load ) ; ///< So we can set the #previous and #first pointers while loading
2008-04-21 08:35:27 +00:00
friend bool LoadOldVehicle ( LoadgameState * ls , int num ) ; ///< So we can set the proper next pointer while loading
2007-08-30 13:09:44 +00:00
2010-11-05 15:48:30 +00:00
TileIndex tile ; ///< Current tile index
2008-12-20 11:51:52 +00:00
/**
* Heading for this tile .
* For airports and train stations this tile does not necessarily belong to the destination station ,
2011-01-29 21:37:11 +00:00
* but it can be used for heuristic purposes to estimate the distance .
2008-12-20 11:51:52 +00:00
*/
TileIndex dest_tile ;
2008-04-21 08:35:27 +00:00
2010-11-05 15:48:30 +00:00
Money profit_this_year ; ///< Profit this year << 8, low 8 bits are fract
Money profit_last_year ; ///< Profit last year << 8, low 8 bits are fract
Money value ; ///< Value of the vehicle
2009-06-29 19:55:36 +00:00
2010-11-05 15:48:30 +00:00
CargoPayment * cargo_payment ; ///< The cargo payment we're currently in
2004-08-09 17:04:08 +00:00
2011-01-31 20:27:33 +00:00
Rect coord ; ///< NOSAVE: Graphical bounding box of the vehicle, i.e. what to redraw on moves.
2012-01-02 12:07:50 +00:00
Vehicle * hash_viewport_next ; ///< NOSAVE: Next vehicle in the visual location hash.
Vehicle * * hash_viewport_prev ; ///< NOSAVE: Previous vehicle in the visual location hash.
2011-01-31 20:27:33 +00:00
2012-01-02 12:07:50 +00:00
Vehicle * hash_tile_next ; ///< NOSAVE: Next vehicle in the tile location hash.
Vehicle * * hash_tile_prev ; ///< NOSAVE: Previous vehicle in the tile location hash.
Vehicle * * hash_tile_current ; ///< NOSAVE: Cache of the current hash chain.
2008-04-21 08:35:27 +00:00
2010-11-05 15:48:30 +00:00
SpriteID colourmap ; ///< NOSAVE: cached colour mapping
2008-04-21 08:35:27 +00:00
/* Related to age and service time */
2011-01-31 20:27:33 +00:00
Year build_year ; ///< Year the vehicle has been built.
2010-11-05 15:48:30 +00:00
Date age ; ///< Age in days
Date max_age ; ///< Maximum age
2011-01-31 20:27:33 +00:00
Date date_of_last_service ; ///< Last date the vehicle had a service at a depot.
2010-11-05 16:34:22 +00:00
uint16 reliability ; ///< Reliability.
uint16 reliability_spd_dec ; ///< Reliability decrease speed.
byte breakdown_ctr ; ///< Counter for managing breakdown events. @see Vehicle::HandleBreakdown
byte breakdown_delay ; ///< Counter for managing breakdown length.
2011-01-31 20:27:33 +00:00
byte breakdowns_since_last_service ; ///< Counter for the amount of breakdowns.
byte breakdown_chance ; ///< Current chance of breakdowns.
2004-08-09 17:04:08 +00:00
2010-11-05 15:48:30 +00:00
int32 x_pos ; ///< x coordinate.
int32 y_pos ; ///< y coordinate.
2011-11-04 11:09:06 +00:00
int32 z_pos ; ///< z coordinate.
2010-11-05 15:48:30 +00:00
DirectionByte direction ; ///< facing
OwnerByte owner ; ///< Which company owns the vehicle?
2011-12-19 17:40:54 +00:00
/**
* currently displayed sprite index
* 0xfd = = custom sprite , 0xfe = = custom second head sprite
* 0xff = = reserved for another custom sprite
*/
byte spritenum ;
2011-01-04 12:04:09 +00:00
SpriteID cur_image ; ///< sprite number for this vehicle
2010-11-05 15:48:30 +00:00
byte x_extent ; ///< x-extent of vehicle bounding box
byte y_extent ; ///< y-extent of vehicle bounding box
byte z_extent ; ///< z-extent of vehicle bounding box
2011-11-21 20:51:43 +00:00
int8 x_bb_offs ; ///< x offset of vehicle bounding box
int8 y_bb_offs ; ///< y offset of vehicle bounding box
2010-11-05 15:48:30 +00:00
int8 x_offs ; ///< x offset for vehicle sprite
int8 y_offs ; ///< y offset for vehicle sprite
2011-01-31 20:27:33 +00:00
EngineID engine_type ; ///< The type of engine used for this vehicle.
2004-08-09 17:04:08 +00:00
2010-11-05 15:48:30 +00:00
TextEffectID fill_percent_te_id ; ///< a text-effect id to a loading indicator object
UnitID unitnumber ; ///< unit number, for display purposes only
2008-04-21 08:35:27 +00:00
2010-11-05 15:48:30 +00:00
uint16 cur_speed ; ///< current speed
byte subspeed ; ///< fractional speed
byte acceleration ; ///< used by train & aircraft
2011-01-31 20:27:33 +00:00
uint32 motion_counter ; ///< counter to occasionally play a vehicle sound.
byte progress ; ///< The percentage (if divided by 256) this vehicle already crossed the tile unit.
2007-06-21 16:17:47 +00:00
2011-01-31 20:27:33 +00:00
byte random_bits ; ///< Bits used for determining which randomized variational spritegroups to use when drawing.
byte waiting_triggers ; ///< Triggers to be yet matched before rerandomizing the random bits.
2004-08-09 17:04:08 +00:00
2011-01-31 20:27:33 +00:00
StationID last_station_visited ; ///< The last station we stopped at.
2013-05-19 14:22:04 +00:00
StationID last_loading_station ; ///< Last station the vehicle has stopped at and could possibly leave from with any cargo loaded.
2004-09-10 19:02:27 +00:00
2010-11-05 15:48:30 +00:00
CargoID cargo_type ; ///< type of cargo this vehicle is carrying
byte cargo_subtype ; ///< Used for livery refits (NewGRF variations)
uint16 cargo_cap ; ///< total capacity
2013-05-19 14:22:04 +00:00
uint16 refit_cap ; ///< Capacity left over from before last refit.
2010-11-05 15:48:30 +00:00
VehicleCargoList cargo ; ///< The cargo this vehicle is carrying
2011-08-03 20:55:08 +00:00
uint16 cargo_age_counter ; ///< Ticks till cargo is aged next.
2007-06-22 11:58:59 +00:00
2010-11-05 15:48:30 +00:00
byte day_counter ; ///< Increased by one for each day
byte tick_counter ; ///< Increased by one for each tick
byte running_ticks ; ///< Number of ticks this vehicle was not stopped this day
2004-08-09 17:04:08 +00:00
2010-11-05 15:48:30 +00:00
byte vehstatus ; ///< Status
Order current_order ; ///< The current order (+ status, like: loading)
2005-01-15 19:06:22 +00:00
2009-01-03 13:52:06 +00:00
union {
2010-11-05 15:48:30 +00:00
OrderList * list ; ///< Pointer to the order list for this vehicle
Order * old ; ///< Only used during conversion of old save games
2011-01-31 20:27:33 +00:00
} orders ; ///< The orders currently assigned to the vehicle.
2004-08-09 17:04:08 +00:00
2011-02-01 21:18:27 +00:00
uint16 load_unload_ticks ; ///< Ticks to wait before starting next cycle.
2010-11-05 15:48:30 +00:00
GroupID group_id ; ///< Index of group Pool array
byte subtype ; ///< subtype (Filled with values from #EffectVehicles/#TrainSubTypes/#AircraftSubTypes)
2007-10-28 15:40:18 +00:00
2010-11-06 12:37:55 +00:00
NewGRFCache grf_cache ; ///< Cache of often used calculated NewGRF values
2010-11-06 12:53:31 +00:00
VehicleCache vcache ; ///< Cache of often used vehicle values.
2007-08-03 19:36:00 +00:00
2009-05-30 20:13:12 +00:00
Vehicle ( VehicleType type = VEH_INVALID ) ;
2007-08-03 19:36:00 +00:00
2007-08-05 17:43:04 +00:00
void PreDestructor ( ) ;
2007-08-03 19:36:00 +00:00
/** We want to 'destruct' the right class. */
virtual ~ Vehicle ( ) ;
2007-01-13 18:55:54 +00:00
void BeginLoading ( ) ;
2013-06-09 13:03:48 +00:00
void CancelReservation ( StationID next , Station * st ) ;
2007-01-13 18:55:54 +00:00
void LeaveStation ( ) ;
2007-04-29 21:24:08 +00:00
2010-12-14 21:31:00 +00:00
GroundVehicleCache * GetGroundVehicleCache ( ) ;
const GroundVehicleCache * GetGroundVehicleCache ( ) const ;
2011-04-16 16:41:02 +00:00
uint16 & GetGroundVehicleFlags ( ) ;
const uint16 & GetGroundVehicleFlags ( ) const ;
2011-05-18 12:19:58 +00:00
void DeleteUnreachedImplicitOrders ( ) ;
2011-01-15 18:14:29 +00:00
2007-05-07 16:21:34 +00:00
void HandleLoading ( bool mode = false ) ;
2013-05-19 14:22:04 +00:00
void GetConsistFreeCapacities ( SmallMap < CargoID , uint > & capacities ) const ;
uint GetConsistTotalCapacity ( ) const ;
2007-04-29 22:33:51 +00:00
/**
* Marks the vehicles to be redrawn and updates cached variables
2007-09-09 10:13:17 +00:00
*
* This method marks the area of the vehicle on the screen as dirty .
* It can be use to repaint the vehicle .
*
* @ ingroup dirty
2007-04-29 22:33:51 +00:00
*/
virtual void MarkDirty ( ) { }
2007-05-01 16:35:14 +00:00
/**
* Updates the x and y offsets and the size of the sprite used
* for this vehicle .
* @ param direction the direction the vehicle is facing
*/
virtual void UpdateDeltaXY ( Direction direction ) { }
2007-05-02 09:29:41 +00:00
2010-07-04 13:07:47 +00:00
/**
* Determines the effective direction - specific vehicle movement speed .
*
* This method belongs to the old vehicle movement method :
* A vehicle moves a step every 256 progress units .
* The vehicle speed is scaled by 3 / 4 when moving in X or Y direction due to the longer distance .
*
* However , this method is slightly wrong in corners , as the leftover progress is not scaled correctly
* when changing movement direction . # GetAdvanceSpeed ( ) and # GetAdvanceDistance ( ) are better wrt . this .
*
* @ param speed Direction - independent unscaled speed .
* @ return speed scaled by movement direction . 256 units are required for each movement step .
*/
2011-12-20 17:57:56 +00:00
inline uint GetOldAdvanceSpeed ( uint speed )
2010-07-04 13:07:47 +00:00
{
return ( this - > direction & 1 ) ? speed : speed * 3 / 4 ;
}
/**
* Determines the effective vehicle movement speed .
*
* Together with # GetAdvanceDistance ( ) this function is a replacement for # GetOldAdvanceSpeed ( ) .
*
* A vehicle progresses independent of it ' s movement direction .
* However different amounts of " progress " are needed for moving a step in a specific direction .
* That way the leftover progress does not need any adaption when changing movement direction .
*
* @ param speed Direction - independent unscaled speed .
* @ return speed , scaled to match # GetAdvanceDistance ( ) .
*/
2011-12-20 17:57:56 +00:00
static inline uint GetAdvanceSpeed ( uint speed )
2010-07-04 13:07:47 +00:00
{
return speed * 3 / 4 ;
}
/**
* Determines the vehicle " progress " needed for moving a step .
*
* Together with # GetAdvanceSpeed ( ) this function is a replacement for # GetOldAdvanceSpeed ( ) .
*
* @ return distance to drive for a movement step on the map .
*/
2011-12-20 17:57:56 +00:00
inline uint GetAdvanceDistance ( )
2010-07-04 13:07:47 +00:00
{
return ( this - > direction & 1 ) ? 192 : 256 ;
}
2007-05-02 09:29:41 +00:00
/**
* Sets the expense type associated to this vehicle type
* @ param income whether this is income or ( running ) expenses of the vehicle
*/
2007-05-02 09:39:11 +00:00
virtual ExpensesType GetExpenseType ( bool income ) const { return EXPENSES_OTHER ; }
2007-05-02 09:29:41 +00:00
2007-05-07 15:58:05 +00:00
/**
* Play the sound associated with leaving the station
*/
virtual void PlayLeaveStationSound ( ) const { }
2007-06-01 12:03:10 +00:00
/**
* Whether this is the primary vehicle in the chain .
*/
virtual bool IsPrimaryVehicle ( ) const { return false ; }
2011-11-01 00:21:08 +00:00
const Engine * GetEngine ( ) const ;
2007-07-01 19:11:47 +00:00
/**
* Gets the sprite to show for the given direction
* @ param direction the direction the vehicle is facing
* @ return the sprite for the given vehicle in the given direction
*/
2011-11-01 16:51:47 +00:00
virtual SpriteID GetImage ( Direction direction , EngineImageType image_type ) const { return 0 ; }
2007-07-01 19:24:54 +00:00
2011-11-01 00:23:41 +00:00
const GRFFile * GetGRF ( ) const ;
uint32 GetGRFID ( ) const ;
2009-05-31 12:03:14 +00:00
/**
* Invalidates cached NewGRF variables
* @ see InvalidateNewGRFCacheOfChain
*/
2011-12-20 17:57:56 +00:00
inline void InvalidateNewGRFCache ( )
2009-05-31 12:03:14 +00:00
{
2010-11-06 12:37:55 +00:00
this - > grf_cache . cache_valid = 0 ;
2009-05-31 12:03:14 +00:00
}
/**
* Invalidates cached NewGRF variables of all vehicles in the chain ( after the current vehicle )
* @ see InvalidateNewGRFCache
*/
2011-12-20 17:57:56 +00:00
inline void InvalidateNewGRFCacheOfChain ( )
2009-05-31 12:03:14 +00:00
{
for ( Vehicle * u = this ; u ! = NULL ; u = u - > Next ( ) ) {
u - > InvalidateNewGRFCache ( ) ;
}
}
2010-12-14 21:26:03 +00:00
/**
* Check if the vehicle is a ground vehicle .
* @ return True iff the vehicle is a train or a road vehicle .
*/
2011-12-20 17:57:56 +00:00
inline bool IsGroundVehicle ( ) const
2010-12-14 21:26:03 +00:00
{
return this - > type = = VEH_TRAIN | | this - > type = = VEH_ROAD ;
}
2007-08-26 20:43:22 +00:00
/**
2009-02-01 17:14:39 +00:00
* Gets the speed in km - ish / h that can be sent into SetDParam for string processing .
2007-08-26 20:43:22 +00:00
* @ return the vehicle ' s speed
*/
virtual int GetDisplaySpeed ( ) const { return 0 ; }
2007-08-28 06:46:33 +00:00
/**
2009-02-01 17:14:39 +00:00
* Gets the maximum speed in km - ish / h that can be sent into SetDParam for string processing .
2007-08-28 06:46:33 +00:00
* @ return the vehicle ' s maximum speed
*/
virtual int GetDisplayMaxSpeed ( ) const { return 0 ; }
2012-05-14 19:56:49 +00:00
/**
* Calculates the maximum speed of the vehicle under its current conditions .
* @ return Current maximum speed in native units .
*/
virtual int GetCurrentMaxSpeed ( ) const { return 0 ; }
2007-08-29 21:27:16 +00:00
/**
* Gets the running cost of a vehicle
* @ return the vehicle ' s running cost
*/
virtual Money GetRunningCost ( ) const { return 0 ; }
2007-08-29 21:49:08 +00:00
/**
* Check whether the vehicle is in the depot .
* @ return true if and only if the vehicle is in the depot .
*/
virtual bool IsInDepot ( ) const { return false ; }
2012-07-07 15:39:46 +00:00
/**
* Check whether the whole vehicle chain is in the depot .
* @ return true if and only if the whole chain is in the depot .
*/
virtual bool IsChainInDepot ( ) const { return this - > IsInDepot ( ) ; }
2007-08-29 21:49:08 +00:00
/**
* Check whether the vehicle is in the depot * and * stopped .
* @ return true if and only if the vehicle is in the depot and stopped .
*/
2012-07-07 15:39:46 +00:00
bool IsStoppedInDepot ( ) const
{
assert ( this = = this - > First ( ) ) ;
/* Free wagons have no VS_STOPPED state */
if ( this - > IsPrimaryVehicle ( ) & & ! ( this - > vehstatus & VS_STOPPED ) ) return false ;
return this - > IsChainInDepot ( ) ;
}
2007-08-29 21:49:08 +00:00
2007-07-01 19:24:54 +00:00
/**
* Calls the tick handler of the vehicle
2009-05-22 13:53:14 +00:00
* @ return is this vehicle still valid ?
2007-07-01 19:24:54 +00:00
*/
2009-05-22 13:53:14 +00:00
virtual bool Tick ( ) { return true ; } ;
2007-08-02 21:19:07 +00:00
2008-02-01 22:02:14 +00:00
/**
* Calls the new day handler of the vehicle
*/
virtual void OnNewDay ( ) { } ;
2009-12-04 20:29:46 +00:00
/**
* Crash the ( whole ) vehicle chain .
* @ param flooded whether the cause of the crash is flooding or not .
* @ return the number of lost souls .
*/
virtual uint Crash ( bool flooded = false ) ;
2009-05-22 18:17:20 +00:00
/**
* Returns the Trackdir on which the vehicle is currently located .
* Works for trains and ships .
* Currently works only sortof for road vehicles , since they have a fuzzy
* concept of being " on " a trackdir . Dunno really what it returns for a road
* vehicle that is halfway a tile , never really understood that part . For road
* vehicles that are at the beginning or end of the tile , should just return
* the diagonal trackdir on which they are driving . I _think_ .
* For other vehicles types , or vehicles with no clear trackdir ( such as those
* in depots ) , returns 0xFF .
* @ return the trackdir of the vehicle
*/
virtual Trackdir GetVehicleTrackdir ( ) const { return INVALID_TRACKDIR ; }
2007-08-29 21:27:16 +00:00
/**
* Gets the running cost of a vehicle that can be sent into SetDParam for string processing .
* @ return the vehicle ' s running cost
*/
Money GetDisplayRunningCost ( ) const { return ( this - > GetRunningCost ( ) > > 8 ) ; }
2008-02-20 17:06:58 +00:00
/**
* Gets the profit vehicle had this year . It can be sent into SetDParam for string processing .
* @ return the vehicle ' s profit this year
*/
Money GetDisplayProfitThisYear ( ) const { return ( this - > profit_this_year > > 8 ) ; }
/**
* Gets the profit vehicle had last year . It can be sent into SetDParam for string processing .
* @ return the vehicle ' s profit last year
*/
Money GetDisplayProfitLastYear ( ) const { return ( this - > profit_last_year > > 8 ) ; }
2007-08-30 21:11:12 +00:00
void SetNext ( Vehicle * next ) ;
2007-08-30 13:03:56 +00:00
/**
* Get the next vehicle of this vehicle .
* @ note articulated parts are also counted as vehicles .
* @ return the next vehicle or NULL when there isn ' t a next vehicle .
*/
inline Vehicle * Next ( ) const { return this - > next ; }
2007-08-30 21:11:12 +00:00
/**
* Get the previous vehicle of this vehicle .
* @ note articulated parts are also counted as vehicles .
* @ return the previous vehicle or NULL when there isn ' t a previous vehicle .
*/
inline Vehicle * Previous ( ) const { return this - > previous ; }
/**
* Get the first vehicle of this vehicle chain .
* @ return the first vehicle of the chain .
*/
inline Vehicle * First ( ) const { return this - > first ; }
2008-02-02 02:45:09 +00:00
2009-07-20 19:58:33 +00:00
/**
* Get the last vehicle of this vehicle chain .
* @ return the last vehicle of the chain .
*/
inline Vehicle * Last ( )
{
Vehicle * v = this ;
while ( v - > Next ( ) ! = NULL ) v = v - > Next ( ) ;
return v ;
}
/**
* Get the last vehicle of this vehicle chain .
* @ return the last vehicle of the chain .
*/
inline const Vehicle * Last ( ) const
{
const Vehicle * v = this ;
while ( v - > Next ( ) ! = NULL ) v = v - > Next ( ) ;
return v ;
}
2008-08-17 19:56:17 +00:00
2011-10-04 21:35:29 +00:00
/**
2012-01-01 17:22:32 +00:00
* Get the vehicle at offset \ a n of this vehicle chain .
2011-10-04 21:35:29 +00:00
* @ param n Offset from the current vehicle .
* @ return The new vehicle or NULL if the offset is out - of - bounds .
*/
inline Vehicle * Move ( int n )
{
Vehicle * v = this ;
if ( n < 0 ) {
for ( int i = 0 ; i ! = n & & v ! = NULL ; i - - ) v = v - > Previous ( ) ;
} else {
for ( int i = 0 ; i ! = n & & v ! = NULL ; i + + ) v = v - > Next ( ) ;
}
return v ;
}
2012-09-16 16:31:53 +00:00
/**
* Get the vehicle at offset \ a n of this vehicle chain .
* @ param n Offset from the current vehicle .
* @ return The new vehicle or NULL if the offset is out - of - bounds .
*/
inline const Vehicle * Move ( int n ) const
{
const Vehicle * v = this ;
if ( n < 0 ) {
for ( int i = 0 ; i ! = n & & v ! = NULL ; i - - ) v = v - > Previous ( ) ;
} else {
for ( int i = 0 ; i ! = n & & v ! = NULL ; i + + ) v = v - > Next ( ) ;
}
return v ;
}
2009-01-03 13:52:06 +00:00
/**
* Get the first order of the vehicles order list .
* @ return first order of order list .
*/
inline Order * GetFirstOrder ( ) const { return ( this - > orders . list = = NULL ) ? NULL : this - > orders . list - > GetFirstOrder ( ) ; }
2008-08-17 19:56:17 +00:00
void AddToShared ( Vehicle * shared_chain ) ;
void RemoveFromShared ( ) ;
/**
2009-01-03 13:52:06 +00:00
* Get the next vehicle of the shared vehicle chain .
* @ return the next shared vehicle or NULL when there isn ' t a next vehicle .
2008-08-17 19:56:17 +00:00
*/
inline Vehicle * NextShared ( ) const { return this - > next_shared ; }
2009-01-03 13:52:06 +00:00
/**
* Get the previous vehicle of the shared vehicle chain
* @ return the previous shared vehicle or NULL when there isn ' t a previous vehicle .
*/
inline Vehicle * PreviousShared ( ) const { return this - > previous_shared ; }
2008-08-17 19:56:17 +00:00
/**
* Get the first vehicle of this vehicle chain .
* @ return the first vehicle of the chain .
*/
2009-02-05 15:58:42 +00:00
inline Vehicle * FirstShared ( ) const { return ( this - > orders . list = = NULL ) ? this - > First ( ) : this - > orders . list - > GetFirstSharedVehicle ( ) ; }
2008-08-17 19:56:17 +00:00
2008-02-02 02:45:09 +00:00
/**
* Check if we share our orders with another vehicle .
* @ return true if there are other vehicles sharing the same order
*/
2009-01-03 13:52:06 +00:00
inline bool IsOrderListShared ( ) const { return this - > orders . list ! = NULL & & this - > orders . list - > IsShared ( ) ; }
2008-02-23 22:01:55 +00:00
2009-01-03 13:52:06 +00:00
/**
2009-01-03 13:20:32 +00:00
* Get the number of orders this vehicle has .
* @ return the number of orders this vehicle has .
*/
2009-01-03 13:52:06 +00:00
inline VehicleOrderID GetNumOrders ( ) const { return ( this - > orders . list = = NULL ) ? 0 : this - > orders . list - > GetNumOrders ( ) ; }
2009-01-03 13:20:32 +00:00
2010-12-26 13:25:34 +00:00
/**
* Get the number of manually added orders this vehicle has .
* @ return the number of manually added orders this vehicle has .
*/
inline VehicleOrderID GetNumManualOrders ( ) const { return ( this - > orders . list = = NULL ) ? 0 : this - > orders . list - > GetNumManualOrders ( ) ; }
2013-05-19 14:22:04 +00:00
/**
* Get the next station the vehicle will stop at .
* @ return ID of the next station the vehicle will stop at or INVALID_STATION .
*/
2013-10-20 13:47:58 +00:00
inline StationIDStack GetNextStoppingStation ( ) const
2013-05-19 14:22:04 +00:00
{
return ( this - > orders . list = = NULL ) ? INVALID_STATION : this - > orders . list - > GetNextStoppingStation ( this ) ;
}
2013-07-06 17:01:31 +00:00
void ResetRefitCaps ( ) ;
2008-08-16 14:02:20 +00:00
/**
* Copy certain configurations and statistics of a vehicle after successful autoreplace / renew
* The function shall copy everything that cannot be copied by a command ( like orders / group etc ) ,
* and that shall not be resetted for the new vehicle .
* @ param src The old vehicle
*/
inline void CopyVehicleConfigAndStatistics ( const Vehicle * src )
{
2012-07-29 16:44:39 +00:00
this - > CopyConsistPropertiesFrom ( src ) ;
2008-08-16 14:02:20 +00:00
this - > unitnumber = src - > unitnumber ;
this - > current_order = src - > current_order ;
this - > dest_tile = src - > dest_tile ;
this - > profit_this_year = src - > profit_this_year ;
this - > profit_last_year = src - > profit_last_year ;
}
2010-08-28 14:14:37 +00:00
bool HandleBreakdown ( ) ;
2010-08-28 14:01:50 +00:00
2012-04-17 19:44:02 +00:00
bool NeedsAutorenewing ( const Company * c , bool use_renew_setting = true ) const ;
2008-04-05 10:55:50 +00:00
2008-04-08 15:48:32 +00:00
bool NeedsServicing ( ) const ;
bool NeedsAutomaticServicing ( ) const ;
2008-04-05 10:55:50 +00:00
/**
* Determine the location for the station where the vehicle goes to next .
* Things done for example are allocating slots in a road stop or exact
* location of the platform is determined for ships .
* @ param station the station to make the next location of the vehicle .
* @ return the location ( tile ) to aim for .
*/
virtual TileIndex GetOrderStationLocation ( StationID station ) { return INVALID_TILE ; }
2008-04-11 08:14:43 +00:00
/**
* Find the closest depot for this vehicle and tell us the location ,
* DestinationID and whether we should reverse .
* @ param location where do we go to ?
* @ param destination what hangar do we go to ?
* @ param reverse should the vehicle be reversed ?
* @ return true if a depot could be found .
*/
virtual bool FindClosestDepot ( TileIndex * location , DestinationID * destination , bool * reverse ) { return false ; }
2008-04-11 08:40:10 +00:00
2009-02-09 21:20:05 +00:00
CommandCost SendToDepot ( DoCommandFlag flags , DepotCommand command ) ;
2009-05-09 13:37:18 +00:00
2010-11-18 14:09:39 +00:00
void UpdateVisualEffect ( bool allow_power_change = true ) ;
2010-11-18 14:15:27 +00:00
void ShowVisualEffect ( ) const ;
2014-09-20 15:31:26 +00:00
void UpdatePosition ( ) ;
void UpdateViewport ( bool dirty ) ;
void UpdatePositionAndViewport ( ) ;
void MarkAllViewportsDirty ( ) const ;
2013-02-14 17:24:55 +00:00
inline uint16 GetServiceInterval ( ) const { return this - > service_interval ; }
2013-02-14 17:04:01 +00:00
2013-02-14 17:24:55 +00:00
inline void SetServiceInterval ( uint16 interval ) { this - > service_interval = interval ; }
2013-02-14 17:06:49 +00:00
2013-02-14 17:24:55 +00:00
inline bool ServiceIntervalIsCustom ( ) const { return HasBit ( this - > vehicle_flags , VF_SERVINT_IS_CUSTOM ) ; }
2013-02-14 17:06:49 +00:00
2013-02-14 17:24:55 +00:00
inline bool ServiceIntervalIsPercent ( ) const { return HasBit ( this - > vehicle_flags , VF_SERVINT_IS_PERCENT ) ; }
2013-02-14 17:06:49 +00:00
2013-02-14 17:24:55 +00:00
inline void SetServiceIntervalIsCustom ( bool on ) { SB ( this - > vehicle_flags , VF_SERVINT_IS_CUSTOM , 1 , on ) ; }
inline void SetServiceIntervalIsPercent ( bool on ) { SB ( this - > vehicle_flags , VF_SERVINT_IS_PERCENT , 1 , on ) ; }
2013-02-14 17:06:49 +00:00
2011-01-31 20:44:15 +00:00
private :
2009-05-09 13:37:18 +00:00
/**
2011-01-31 20:44:15 +00:00
* Advance cur_real_order_index to the next real order .
2011-05-18 12:19:58 +00:00
* cur_implicit_order_index is not touched .
2011-01-31 20:44:15 +00:00
*/
void SkipToNextRealOrderIndex ( )
{
if ( this - > GetNumManualOrders ( ) > 0 ) {
/* Advance to next real order */
do {
this - > cur_real_order_index + + ;
if ( this - > cur_real_order_index > = this - > GetNumOrders ( ) ) this - > cur_real_order_index = 0 ;
2011-05-18 12:19:58 +00:00
} while ( this - > GetOrder ( this - > cur_real_order_index ) - > IsType ( OT_IMPLICIT ) ) ;
2011-01-31 20:44:15 +00:00
} else {
this - > cur_real_order_index = 0 ;
}
}
public :
/**
2011-05-18 12:19:58 +00:00
* Increments cur_implicit_order_index , keeps care of the wrap - around and invalidates the GUI .
2011-01-31 20:44:15 +00:00
* cur_real_order_index is incremented as well , if needed .
2009-05-09 13:37:18 +00:00
* Note : current_order is not invalidated .
*/
2011-05-18 12:19:58 +00:00
void IncrementImplicitOrderIndex ( )
2009-05-09 14:23:19 +00:00
{
2011-05-18 12:19:58 +00:00
if ( this - > cur_implicit_order_index = = this - > cur_real_order_index ) {
2011-01-31 20:44:15 +00:00
/* Increment real order index as well */
this - > SkipToNextRealOrderIndex ( ) ;
}
assert ( this - > cur_real_order_index = = 0 | | this - > cur_real_order_index < this - > GetNumOrders ( ) ) ;
2011-05-18 12:19:58 +00:00
/* Advance to next implicit order */
2011-01-31 20:44:15 +00:00
do {
2011-05-18 12:19:58 +00:00
this - > cur_implicit_order_index + + ;
if ( this - > cur_implicit_order_index > = this - > GetNumOrders ( ) ) this - > cur_implicit_order_index = 0 ;
} while ( this - > cur_implicit_order_index ! = this - > cur_real_order_index & & ! this - > GetOrder ( this - > cur_implicit_order_index ) - > IsType ( OT_IMPLICIT ) ) ;
2011-01-31 20:44:15 +00:00
2009-05-09 13:37:18 +00:00
InvalidateVehicleOrder ( this , 0 ) ;
}
2009-05-23 12:27:42 +00:00
2011-01-31 20:44:15 +00:00
/**
* Advanced cur_real_order_index to the next real order , keeps care of the wrap - around and invalidates the GUI .
2011-05-18 12:19:58 +00:00
* cur_implicit_order_index is incremented as well , if it was equal to cur_real_order_index , i . e . cur_real_order_index is skipped
* but not any implicit orders .
2011-01-31 20:44:15 +00:00
* Note : current_order is not invalidated .
*/
void IncrementRealOrderIndex ( )
{
2011-05-18 12:19:58 +00:00
if ( this - > cur_implicit_order_index = = this - > cur_real_order_index ) {
/* Increment both real and implicit order */
this - > IncrementImplicitOrderIndex ( ) ;
2011-01-31 20:44:15 +00:00
} else {
/* Increment real order only */
this - > SkipToNextRealOrderIndex ( ) ;
InvalidateVehicleOrder ( this , 0 ) ;
}
}
/**
2011-05-18 12:19:58 +00:00
* Skip implicit orders until cur_real_order_index is a non - implicit order .
2011-01-31 20:44:15 +00:00
*/
void UpdateRealOrderIndex ( )
{
/* Make sure the index is valid */
if ( this - > cur_real_order_index > = this - > GetNumOrders ( ) ) this - > cur_real_order_index = 0 ;
if ( this - > GetNumManualOrders ( ) > 0 ) {
/* Advance to next real order */
2011-05-18 12:19:58 +00:00
while ( this - > GetOrder ( this - > cur_real_order_index ) - > IsType ( OT_IMPLICIT ) ) {
2011-01-31 20:44:15 +00:00
this - > cur_real_order_index + + ;
if ( this - > cur_real_order_index > = this - > GetNumOrders ( ) ) this - > cur_real_order_index = 0 ;
}
} else {
this - > cur_real_order_index = 0 ;
}
}
2009-05-23 12:27:42 +00:00
/**
* Returns order ' index ' of a vehicle or NULL when it doesn ' t exists
* @ param index the order to fetch
* @ return the found ( or not ) order
*/
inline Order * GetOrder ( int index ) const
{
return ( this - > orders . list = = NULL ) ? NULL : this - > orders . list - > GetOrderAt ( index ) ;
}
/**
* Returns the last order of a vehicle , or NULL if it doesn ' t exists
* @ return last order of a vehicle , if available
*/
inline Order * GetLastOrder ( ) const
{
return ( this - > orders . list = = NULL ) ? NULL : this - > orders . list - > GetLastOrder ( ) ;
}
2009-07-13 16:35:22 +00:00
bool IsEngineCountable ( ) const ;
2011-09-19 19:23:23 +00:00
bool HasEngineType ( ) const ;
2010-12-11 13:48:30 +00:00
bool HasDepotOrder ( ) const ;
2010-12-13 21:55:06 +00:00
void HandlePathfindingResult ( bool path_found ) ;
2011-01-29 17:26:23 +00:00
/**
* Check if the vehicle is a front engine .
* @ return Returns true if the vehicle is a front engine .
*/
2011-12-20 17:57:56 +00:00
inline bool IsFrontEngine ( ) const
2011-01-29 17:26:23 +00:00
{
return this - > IsGroundVehicle ( ) & & HasBit ( this - > subtype , GVSF_FRONT ) ;
}
/**
* Check if the vehicle is an articulated part of an engine .
* @ return Returns true if the vehicle is an articulated part .
*/
2011-12-20 17:57:56 +00:00
inline bool IsArticulatedPart ( ) const
2011-01-29 17:26:23 +00:00
{
return this - > IsGroundVehicle ( ) & & HasBit ( this - > subtype , GVSF_ARTICULATED_PART ) ;
}
/**
* Check if an engine has an articulated part .
* @ return True if the engine has an articulated part .
*/
2011-12-20 17:57:56 +00:00
inline bool HasArticulatedPart ( ) const
2011-01-29 17:26:23 +00:00
{
return this - > Next ( ) ! = NULL & & this - > Next ( ) - > IsArticulatedPart ( ) ;
}
2011-01-29 17:27:32 +00:00
/**
* Get the next part of an articulated engine .
* @ return Next part of the articulated engine .
* @ pre The vehicle is an articulated engine .
*/
2011-12-20 17:57:56 +00:00
inline Vehicle * GetNextArticulatedPart ( ) const
2011-01-29 17:27:32 +00:00
{
assert ( this - > HasArticulatedPart ( ) ) ;
return this - > Next ( ) ;
}
/**
* Get the first part of an articulated engine .
* @ return First part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline Vehicle * GetFirstEnginePart ( )
2011-01-29 17:27:32 +00:00
{
Vehicle * v = this ;
while ( v - > IsArticulatedPart ( ) ) v = v - > Previous ( ) ;
return v ;
}
/**
* Get the first part of an articulated engine .
* @ return First part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline const Vehicle * GetFirstEnginePart ( ) const
2011-01-29 17:27:32 +00:00
{
const Vehicle * v = this ;
while ( v - > IsArticulatedPart ( ) ) v = v - > Previous ( ) ;
return v ;
}
/**
* Get the last part of an articulated engine .
* @ return Last part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline Vehicle * GetLastEnginePart ( )
2011-01-29 17:27:32 +00:00
{
Vehicle * v = this ;
while ( v - > HasArticulatedPart ( ) ) v = v - > GetNextArticulatedPart ( ) ;
return v ;
}
/**
* Get the next real ( non - articulated part ) vehicle in the consist .
* @ return Next vehicle in the consist .
*/
2011-12-20 17:57:56 +00:00
inline Vehicle * GetNextVehicle ( ) const
2011-01-29 17:27:32 +00:00
{
const Vehicle * v = this ;
while ( v - > HasArticulatedPart ( ) ) v = v - > GetNextArticulatedPart ( ) ;
/* v now contains the last articulated part in the engine */
return v - > Next ( ) ;
}
/**
* Get the previous real ( non - articulated part ) vehicle in the consist .
* @ return Previous vehicle in the consist .
*/
2011-12-20 17:57:56 +00:00
inline Vehicle * GetPrevVehicle ( ) const
2011-01-29 17:27:32 +00:00
{
Vehicle * v = this - > Previous ( ) ;
while ( v ! = NULL & & v - > IsArticulatedPart ( ) ) v = v - > Previous ( ) ;
return v ;
}
2007-04-29 21:24:08 +00:00
} ;
2011-01-31 20:27:33 +00:00
/**
* Iterate over all vehicles from a given point .
* @ param var The variable used to iterate over .
* @ param start The vehicle to start the iteration at .
*/
2009-05-26 22:45:48 +00:00
# define FOR_ALL_VEHICLES_FROM(var, start) FOR_ALL_ITEMS_FROM(Vehicle, vehicle_index, var, start)
2011-01-31 20:27:33 +00:00
/**
* Iterate over all vehicles .
* @ param var The variable used to iterate over .
*/
2009-05-26 22:45:48 +00:00
# define FOR_ALL_VEHICLES(var) FOR_ALL_VEHICLES_FROM(var, 0)
2009-05-26 22:10:13 +00:00
/**
* Class defining several overloaded accessors so we don ' t
* have to cast vehicle types that often
*/
template < class T , VehicleType Type >
struct SpecializedVehicle : public Vehicle {
static const VehicleType EXPECTED_TYPE = Type ; ///< Specialized type
2011-01-21 14:43:38 +00:00
typedef SpecializedVehicle < T , Type > SpecializedVehicleBase ; ///< Our type
2009-05-30 20:13:12 +00:00
/**
* Set vehicle type correctly
*/
2011-12-20 17:57:56 +00:00
inline SpecializedVehicle < T , Type > ( ) : Vehicle ( Type ) { }
2009-05-30 20:13:12 +00:00
2009-05-26 22:10:13 +00:00
/**
* Get the first vehicle in the chain
* @ return first vehicle in the chain
*/
2011-12-20 17:57:56 +00:00
inline T * First ( ) const { return ( T * ) this - > Vehicle : : First ( ) ; }
2009-05-26 22:10:13 +00:00
2009-07-20 19:58:33 +00:00
/**
* Get the last vehicle in the chain
* @ return last vehicle in the chain
*/
2011-12-20 17:57:56 +00:00
inline T * Last ( ) { return ( T * ) this - > Vehicle : : Last ( ) ; }
2009-07-20 19:58:33 +00:00
/**
* Get the last vehicle in the chain
* @ return last vehicle in the chain
*/
2011-12-20 17:57:56 +00:00
inline const T * Last ( ) const { return ( const T * ) this - > Vehicle : : Last ( ) ; }
2009-07-20 19:58:33 +00:00
2009-05-26 22:10:13 +00:00
/**
* Get next vehicle in the chain
* @ return next vehicle in the chain
*/
2011-12-20 17:57:56 +00:00
inline T * Next ( ) const { return ( T * ) this - > Vehicle : : Next ( ) ; }
2009-05-26 22:10:13 +00:00
/**
* Get previous vehicle in the chain
* @ return previous vehicle in the chain
*/
2011-12-20 17:57:56 +00:00
inline T * Previous ( ) const { return ( T * ) this - > Vehicle : : Previous ( ) ; }
2009-05-26 22:10:13 +00:00
2011-01-29 17:27:32 +00:00
/**
* Get the next part of an articulated engine .
* @ return Next part of the articulated engine .
* @ pre The vehicle is an articulated engine .
*/
2011-12-20 17:57:56 +00:00
inline T * GetNextArticulatedPart ( ) { return ( T * ) this - > Vehicle : : GetNextArticulatedPart ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the next part of an articulated engine .
* @ return Next part of the articulated engine .
* @ pre The vehicle is an articulated engine .
*/
2011-12-20 17:57:56 +00:00
inline T * GetNextArticulatedPart ( ) const { return ( T * ) this - > Vehicle : : GetNextArticulatedPart ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the first part of an articulated engine .
* @ return First part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline T * GetFirstEnginePart ( ) { return ( T * ) this - > Vehicle : : GetFirstEnginePart ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the first part of an articulated engine .
* @ return First part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline const T * GetFirstEnginePart ( ) const { return ( const T * ) this - > Vehicle : : GetFirstEnginePart ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the last part of an articulated engine .
* @ return Last part of the engine .
*/
2011-12-20 17:57:56 +00:00
inline T * GetLastEnginePart ( ) { return ( T * ) this - > Vehicle : : GetLastEnginePart ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the next real ( non - articulated part ) vehicle in the consist .
* @ return Next vehicle in the consist .
*/
2011-12-20 17:57:56 +00:00
inline T * GetNextVehicle ( ) const { return ( T * ) this - > Vehicle : : GetNextVehicle ( ) ; }
2011-01-29 17:27:32 +00:00
/**
* Get the previous real ( non - articulated part ) vehicle in the consist .
* @ return Previous vehicle in the consist .
*/
2011-12-20 17:57:56 +00:00
inline T * GetPrevVehicle ( ) const { return ( T * ) this - > Vehicle : : GetPrevVehicle ( ) ; }
2009-05-26 22:10:13 +00:00
/**
* Tests whether given index is a valid index for vehicle of this type
* @ param index tested index
* @ return is this index valid index of T ?
*/
2011-12-20 17:57:56 +00:00
static inline bool IsValidID ( size_t index )
2009-05-26 22:10:13 +00:00
{
return Vehicle : : IsValidID ( index ) & & Vehicle : : Get ( index ) - > type = = Type ;
}
/**
* Gets vehicle with given index
* @ return pointer to vehicle with given index casted to T *
*/
2011-12-20 17:57:56 +00:00
static inline T * Get ( size_t index )
2009-05-26 22:10:13 +00:00
{
return ( T * ) Vehicle : : Get ( index ) ;
}
/**
* Returns vehicle if the index is a valid index for this vehicle type
* @ return pointer to vehicle with given index if it ' s a vehicle of this type
*/
2011-12-20 17:57:56 +00:00
static inline T * GetIfValid ( size_t index )
2009-05-26 22:10:13 +00:00
{
2009-11-29 19:20:39 +00:00
return IsValidID ( index ) ? Get ( index ) : NULL ;
2009-05-26 22:10:13 +00:00
}
2009-06-06 16:54:22 +00:00
/**
* Converts a Vehicle to SpecializedVehicle with type checking .
* @ param v Vehicle pointer
* @ return pointer to SpecializedVehicle
*/
2011-12-20 17:57:56 +00:00
static inline T * From ( Vehicle * v )
2009-06-06 16:54:22 +00:00
{
assert ( v - > type = = Type ) ;
return ( T * ) v ;
}
/**
* Converts a const Vehicle to const SpecializedVehicle with type checking .
* @ param v Vehicle pointer
* @ return pointer to SpecializedVehicle
*/
2011-12-20 17:57:56 +00:00
static inline const T * From ( const Vehicle * v )
2009-06-06 16:54:22 +00:00
{
assert ( v - > type = = Type ) ;
return ( const T * ) v ;
}
2010-05-03 23:36:17 +00:00
/**
* Update vehicle sprite - and position caches
2012-01-02 13:44:37 +00:00
* @ param force_update Force updating the vehicle on the viewport .
* @ param update_delta Also update the delta ?
2010-05-03 23:36:17 +00:00
*/
2012-01-02 13:44:37 +00:00
inline void UpdateViewport ( bool force_update , bool update_delta )
2010-05-03 23:36:17 +00:00
{
2016-05-22 11:30:25 +00:00
/* Skip updating sprites on dedicated servers without screen */
if ( _network_dedicated ) return ;
2010-05-03 23:36:17 +00:00
/* Explicitly choose method to call to prevent vtable dereference -
* it gives ~ 3 % runtime improvements in games with many vehicles */
2012-01-02 13:44:37 +00:00
if ( update_delta ) ( ( T * ) this ) - > T : : UpdateDeltaXY ( this - > direction ) ;
2010-05-03 23:36:17 +00:00
SpriteID old_image = this - > cur_image ;
2011-11-01 16:51:47 +00:00
this - > cur_image = ( ( T * ) this ) - > T : : GetImage ( this - > direction , EIT_ON_MAP ) ;
2014-09-20 15:31:26 +00:00
if ( force_update | | this - > cur_image ! = old_image ) this - > Vehicle : : UpdateViewport ( true ) ;
2010-05-03 23:36:17 +00:00
}
2009-05-26 22:10:13 +00:00
} ;
2011-01-31 20:27:33 +00:00
/**
* Iterate over all vehicles of a particular type .
* @ param name The type of vehicle to iterate over .
* @ param var The variable used to iterate over .
*/
2009-05-26 22:10:13 +00:00
# define FOR_ALL_VEHICLES_OF_TYPE(name, var) FOR_ALL_ITEMS_FROM(name, vehicle_index, var, 0) if (var->type == name::EXPECTED_TYPE)
2008-12-26 23:53:07 +00:00
/** Generates sequence of free UnitID numbers */
struct FreeUnitIDGenerator {
bool * cache ; ///< array of occupied unit id numbers
UnitID maxid ; ///< maximum ID at the moment of constructor call
2009-11-29 19:20:39 +00:00
UnitID curid ; ///< last ID returned; 0 if none
2008-12-26 23:53:07 +00:00
FreeUnitIDGenerator ( VehicleType type , CompanyID owner ) ;
UnitID NextID ( ) ;
/** Releases allocated memory */
~ FreeUnitIDGenerator ( ) { free ( this - > cache ) ; }
} ;
2011-01-31 20:27:33 +00:00
/** Sentinel for an invalid coordinate. */
2009-01-04 15:32:25 +00:00
static const int32 INVALID_COORD = 0x7fffffff ;
2007-12-27 13:35:39 +00:00
# endif /* VEHICLE_BASE_H */