--- a/src/engine.cpp Tue Mar 27 23:27:27 2007 +0000
+++ b/src/engine.cpp Sat Jun 02 19:59:29 2007 +0000
@@ -20,6 +20,7 @@
#include "newgrf_cargo.h"
#include "date.h"
#include "table/engines.h"
+#include "group.h"
EngineInfo _engine_info[TOTAL_NUM_ENGINES];
RailVehicleInfo _rail_vehicle_info[NUM_TRAIN_ENGINES];
@@ -70,6 +71,16 @@
{
uint age = e->age;
+ /* Check for early retirement */
+ if (e->player_avail != 0 && !_patches.never_expire_vehicles) {
+ uint retire_early = EngInfo(e - _engines)->retire_early;
+ if (retire_early > 0 && age >= e->duration_phase_1 + e->duration_phase_2 - retire_early * 12) {
+ /* Early retirement is enabled and we're past the date... */
+ e->player_avail = 0;
+ AddRemoveEngineFromAutoreplaceAndBuildWindows(e->type);
+ }
+ }
+
if (age < e->duration_phase_1) {
uint start = e->reliability_start;
e->reliability = age * (e->reliability_max - start) / e->duration_phase_1 + start;
@@ -167,14 +178,16 @@
static void AcceptEnginePreview(EngineID eid, PlayerID player)
{
Engine *e = GetEngine(eid);
+ Player *p = GetPlayer(player);
SETBIT(e->player_avail, player);
if (e->type == VEH_TRAIN) {
const RailVehicleInfo *rvi = RailVehInfo(eid);
- Player *p = GetPlayer(player);
assert(rvi->railtype < RAILTYPE_END);
SETBIT(p->avail_railtypes, rvi->railtype);
+ } else if (e->type == VEH_ROAD) {
+ SETBIT(p->avail_roadtypes, HASBIT(EngInfo(eid)->misc_flags, EF_ROAD_TRAM) ? ROADTYPE_TRAM : ROADTYPE_ROAD);
}
e->preview_player = INVALID_PLAYER;
@@ -249,6 +262,7 @@
/** Accept an engine prototype. XXX - it is possible that the top-player
* changes while you are waiting to accept the offer? Then it becomes invalid
* @param tile unused
+ * @param flags operation to perfom
* @param p1 engine-prototype offered
* @param p2 unused
*/
@@ -318,6 +332,12 @@
if (p->is_active) SETBIT(p->avail_railtypes, railtype);
}
}
+ if ((index - NUM_TRAIN_ENGINES) < NUM_ROAD_ENGINES) {
+ /* maybe make another road type available */
+ FOR_ALL_PLAYERS(p) {
+ if (p->is_active) SETBIT(p->avail_roadtypes, HASBIT(EngInfo(index)->misc_flags, EF_ROAD_TRAM) ? ROADTYPE_TRAM : ROADTYPE_ROAD);
+ }
+ }
AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_VEHICLEAVAIL), 0, 0);
}
@@ -350,6 +370,7 @@
/** Rename an engine.
* @param tile unused
+ * @param flags operation to perfom
* @param p1 engine ID to rename
* @param p2 unused
*/
@@ -399,9 +420,44 @@
/* check if it's available */
if (!HASBIT(e->player_avail, player)) return false;
+ if (type == VEH_TRAIN) {
+ /* Check if the rail type is available to this player */
+ const Player *p = GetPlayer(player);
+ if (!HASBIT(p->avail_railtypes, RailVehInfo(engine)->railtype)) return false;
+ }
+
return true;
}
+/** Get the default cargo type for a certain engine type
+ * @param engine The ID to get the cargo for
+ * @return The cargo type. CT_INVALID means no cargo capacity
+ */
+CargoID GetEngineCargoType(EngineID engine)
+{
+ assert(IsEngineIndex(engine));
+
+ switch (GetEngine(engine)->type) {
+ case VEH_TRAIN:
+ if (RailVehInfo(engine)->capacity == 0) return CT_INVALID;
+ return RailVehInfo(engine)->cargo_type;
+
+ case VEH_ROAD:
+ if (RoadVehInfo(engine)->capacity == 0) return CT_INVALID;
+ return RoadVehInfo(engine)->cargo_type;
+
+ case VEH_SHIP:
+ if (ShipVehInfo(engine)->capacity == 0) return CT_INVALID;
+ return ShipVehInfo(engine)->cargo_type;
+
+ case VEH_AIRCRAFT:
+ /* all aircraft starts as passenger planes with cargo capacity */
+ return CT_PASSENGERS;
+
+ default: NOT_REACHED(); return CT_INVALID;
+ }
+}
+
/************************************************************************
* Engine Replacement stuff
************************************************************************/
@@ -434,6 +490,7 @@
er->to = INVALID_ENGINE;
er->next = NULL;
+ er->group_id = DEFAULT_GROUP;
return er;
}
@@ -446,12 +503,12 @@
/**
* Retrieves the EngineRenew that specifies the replacement of the given
* engine type from the given renewlist */
-static EngineRenew *GetEngineReplacement(EngineRenewList erl, EngineID engine)
+static EngineRenew *GetEngineReplacement(EngineRenewList erl, EngineID engine, GroupID group)
{
EngineRenew *er = (EngineRenew *)erl;
while (er) {
- if (er->from == engine) return er;
+ if (er->from == engine && er->group_id == group) return er;
er = er->next;
}
return NULL;
@@ -470,18 +527,18 @@
*erl = NULL; // Empty list
}
-EngineID EngineReplacement(EngineRenewList erl, EngineID engine)
+EngineID EngineReplacement(EngineRenewList erl, EngineID engine, GroupID group)
{
- const EngineRenew *er = GetEngineReplacement(erl, engine);
+ const EngineRenew *er = GetEngineReplacement(erl, engine, group);
return er == NULL ? INVALID_ENGINE : er->to;
}
-int32 AddEngineReplacement(EngineRenewList *erl, EngineID old_engine, EngineID new_engine, uint32 flags)
+int32 AddEngineReplacement(EngineRenewList *erl, EngineID old_engine, EngineID new_engine, GroupID group, uint32 flags)
{
EngineRenew *er;
/* Check if the old vehicle is already in the list */
- er = GetEngineReplacement(*erl, old_engine);
+ er = GetEngineReplacement(*erl, old_engine, group);
if (er != NULL) {
if (flags & DC_EXEC) er->to = new_engine;
return 0;
@@ -493,6 +550,7 @@
if (flags & DC_EXEC) {
er->from = old_engine;
er->to = new_engine;
+ er->group_id = group;
/* Insert before the first element */
er->next = (EngineRenew *)(*erl);
@@ -502,14 +560,14 @@
return 0;
}
-int32 RemoveEngineReplacement(EngineRenewList *erl, EngineID engine, uint32 flags)
+int32 RemoveEngineReplacement(EngineRenewList *erl, EngineID engine, GroupID group, uint32 flags)
{
EngineRenew *er = (EngineRenew *)(*erl);
EngineRenew *prev = NULL;
while (er)
{
- if (er->from == engine) {
+ if (er->from == engine && er->group_id == group) {
if (flags & DC_EXEC) {
if (prev == NULL) { // First element
/* The second becomes the new first element */
@@ -530,11 +588,11 @@
}
static const SaveLoad _engine_renew_desc[] = {
- SLE_VAR(EngineRenew, from, SLE_UINT16),
- SLE_VAR(EngineRenew, to, SLE_UINT16),
+ SLE_VAR(EngineRenew, from, SLE_UINT16),
+ SLE_VAR(EngineRenew, to, SLE_UINT16),
- SLE_REF(EngineRenew, next, REF_ENGINE_RENEWS),
-
+ SLE_REF(EngineRenew, next, REF_ENGINE_RENEWS),
+ SLE_CONDVAR(EngineRenew, group_id, SLE_UINT16, 60, SL_MAX_VERSION),
SLE_END()
};
@@ -560,6 +618,9 @@
er = GetEngineRenew(index);
SlObject(er, _engine_renew_desc);
+
+ /* Advanced vehicle lists got added */
+ if (CheckSavegameVersion(60)) er->group_id = DEFAULT_GROUP;
}
}