Changeset - r9941:945cc0c6ccbc
[Not reviewed]
master
0 9 0
rubidium - 16 years ago 2008-08-17 19:56:17
rubidium@openttd.org
(svn r14096) -Codechange: merge the shared order's vehicle list management to a single location.
9 files changed with 119 insertions and 114 deletions:
0 comments (0 inline, 0 general)
src/group_cmd.cpp
Show inline comments
 
@@ -263,7 +263,7 @@ CommandCost CmdAddSharedVehicleGroup(Til
 
				if (v->group_id != id_g) continue;
 

	
 
				/* For each shared vehicles add it to the group */
 
				for (Vehicle *v2 = GetFirstVehicleFromSharedList(v); v2 != NULL; v2 = v2->next_shared) {
 
				for (Vehicle *v2 = v->FirstShared(); v2 != NULL; v2 = v2->NextShared()) {
 
					if (v2->group_id != id_g) CmdAddVehicleGroup(tile, flags, id_g, v2->index);
 
				}
 
			}
src/oldloader.cpp
Show inline comments
 
@@ -372,8 +372,7 @@ static void FixOldVehicles()
 
			/* If a vehicle has the same orders, add the link to eachother
 
			 * in both vehicles */
 
			if (v->orders == u->orders) {
 
				v->next_shared = u;
 
				u->prev_shared = v;
 
				u->AddToShared(v);
 
				break;
 
			}
 
		}
src/openttd.cpp
Show inline comments
 
@@ -2272,7 +2272,7 @@ bool AfterLoadGame()
 
			if (v->orders != NULL && !v->orders->IsValid()) v->orders = NULL;
 

	
 
			v->current_order.ConvertFromOldSavegame();
 
			if (v->type == VEH_ROAD && v->IsPrimaryVehicle() && v->prev_shared == NULL) {
 
			if (v->type == VEH_ROAD && v->IsPrimaryVehicle() && v->FirstShared() == v) {
 
				FOR_VEHICLE_ORDERS(v, order) order->SetNonStopType(ONSF_NO_STOP_AT_INTERMEDIATE_STATIONS);
 
			}
 
		}
src/order_cmd.cpp
Show inline comments
 
@@ -506,7 +506,6 @@ CommandCost CmdInsertOrder(TileIndex til
 
	}
 

	
 
	if (flags & DC_EXEC) {
 
		Vehicle *u;
 
		Order *new_o = new Order();
 
		new_o->AssignOrder(new_order);
 

	
 
@@ -537,9 +536,9 @@ CommandCost CmdInsertOrder(TileIndex til
 
			}
 
		}
 

	
 
		u = GetFirstVehicleFromSharedList(v);
 
		Vehicle *u = v->FirstShared();
 
		DeleteOrderWarnings(u);
 
		for (; u != NULL; u = u->next_shared) {
 
		for (; u != NULL; u = u->NextShared()) {
 
			/* Increase amount of orders */
 
			u->num_orders++;
 

	
 
@@ -601,7 +600,7 @@ static CommandCost DecloneOrder(Vehicle 
 
 * Remove the VehicleList that shows all the vehicles with the same shared
 
 *  orders.
 
 */
 
static void RemoveSharedOrderVehicleList(Vehicle *v)
 
void RemoveSharedOrderVehicleList(Vehicle *v)
 
{
 
	assert(v->orders != NULL);
 
	WindowClass window_class = WC_NONE;
 
@@ -624,7 +623,7 @@ static void RemoveSharedOrderVehicleList
 
 */
 
CommandCost CmdDeleteOrder(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
 
{
 
	Vehicle *v, *u;
 
	Vehicle *v;
 
	VehicleID veh_id = p1;
 
	VehicleOrderID sel_ord = p2;
 
	Order *order;
 
@@ -665,9 +664,9 @@ CommandCost CmdDeleteOrder(TileIndex til
 
		/* Give the item free */
 
		order->Free();
 

	
 
		u = GetFirstVehicleFromSharedList(v);
 
		Vehicle *u = v->FirstShared();
 
		DeleteOrderWarnings(u);
 
		for (; u != NULL; u = u->next_shared) {
 
		for (; u != NULL; u = u->NextShared()) {
 
			u->num_orders--;
 

	
 
			if (sel_ord < u->cur_order_index)
 
@@ -803,11 +802,11 @@ CommandCost CmdMoveOrder(TileIndex tile,
 
		}
 

	
 
		/* Update shared list */
 
		Vehicle *u = GetFirstVehicleFromSharedList(v);
 
		Vehicle *u = v->FirstShared();
 

	
 
		DeleteOrderWarnings(u);
 

	
 
		for (; u != NULL; u = u->next_shared) {
 
		for (; u != NULL; u = u->NextShared()) {
 
			/* Update the first order */
 
			if (u->orders != v->orders) u->orders = v->orders;
 

	
 
@@ -1027,9 +1026,9 @@ CommandCost CmdModifyOrder(TileIndex til
 
		}
 

	
 
		/* Update the windows and full load flags, also for vehicles that share the same order list */
 
		Vehicle *u = GetFirstVehicleFromSharedList(v);
 
		Vehicle *u = v->FirstShared();
 
		DeleteOrderWarnings(u);
 
		for (; u != NULL; u = u->next_shared) {
 
		for (; u != NULL; u = u->NextShared()) {
 
			/* Toggle u->current_order "Full load" flag if it changed.
 
			 * However, as the same flag is used for depot orders, check
 
			 * whether we are not going to a depot as there are three
 
@@ -1090,13 +1089,7 @@ CommandCost CmdCloneOrder(TileIndex tile
 
			}
 

	
 
			/* Is the vehicle already in the shared list? */
 
			{
 
				const Vehicle* u;
 

	
 
				for (u = GetFirstVehicleFromSharedList(src); u != NULL; u = u->next_shared) {
 
					if (u == dst) return CMD_ERROR;
 
				}
 
			}
 
			if (src->FirstShared() == dst->FirstShared()) return CMD_ERROR;
 

	
 
			if (flags & DC_EXEC) {
 
				/* If the destination vehicle had a OrderList, destroy it */
 
@@ -1106,10 +1099,7 @@ CommandCost CmdCloneOrder(TileIndex tile
 
				dst->num_orders = src->num_orders;
 

	
 
				/* Link this vehicle in the shared-list */
 
				dst->next_shared = src->next_shared;
 
				dst->prev_shared = src;
 
				if (src->next_shared != NULL) src->next_shared->prev_shared = dst;
 
				src->next_shared = dst;
 
				dst->AddToShared(src);
 

	
 
				InvalidateVehicleOrder(dst);
 
				InvalidateVehicleOrder(src);
 
@@ -1212,12 +1202,9 @@ CommandCost CmdOrderRefit(TileIndex tile
 
	if (order == NULL) return CMD_ERROR;
 

	
 
	if (flags & DC_EXEC) {
 
		Vehicle *u;
 

	
 
		order->SetRefit(cargo, subtype);
 

	
 
		u = GetFirstVehicleFromSharedList(v);
 
		for (; u != NULL; u = u->next_shared) {
 
		for (Vehicle *u = v->FirstShared(); u != NULL; u = u->NextShared()) {
 
			/* Update any possible open window of the vehicle */
 
			InvalidateVehicleOrder(u);
 

	
 
@@ -1253,7 +1240,7 @@ void BackupVehicleOrders(const Vehicle *
 

	
 
	/* If we have shared orders, store it on a special way */
 
	if (v->IsOrderListShared()) {
 
		const Vehicle *u = (v->next_shared) ? v->next_shared : v->prev_shared;
 
		const Vehicle *u = (v->FirstShared() == v) ? v->NextShared() : v->FirstShared();
 

	
 
		bak->clone = u->index;
 
	} else {
 
@@ -1413,7 +1400,7 @@ void CheckOrders(const Vehicle* v)
 
		return;
 

	
 
	/* do nothing we we're not the first vehicle in a share-chain */
 
	if (v->next_shared != NULL) return;
 
	if (v->FirstShared() != v) return;
 

	
 
	/* Only check every 20 days, so that we don't flood the message log */
 
	if (v->owner == _local_player && v->day_counter % 20 == 0) {
 
@@ -1541,49 +1528,16 @@ void DeleteVehicleOrders(Vehicle *v)
 
{
 
	DeleteOrderWarnings(v);
 

	
 
	/* If we have a shared order-list, don't delete the list, but just
 
	    remove our pointer */
 
	if (v->IsOrderListShared()) {
 
		Vehicle *u = v;
 

	
 
		v->orders = NULL;
 
		v->num_orders = 0;
 

	
 
		/* Unlink ourself */
 
		if (v->prev_shared != NULL) {
 
			v->prev_shared->next_shared = v->next_shared;
 
			u = v->prev_shared;
 
		}
 
		if (v->next_shared != NULL) {
 
			v->next_shared->prev_shared = v->prev_shared;
 
			u = v->next_shared;
 
		}
 
		v->prev_shared = NULL;
 
		v->next_shared = NULL;
 

	
 
		/* If we are the only one left in the Shared Order Vehicle List,
 
		 *  remove it, as we are no longer a Shared Order Vehicle */
 
		if (u->prev_shared == NULL && u->next_shared == NULL && u->orders != NULL) RemoveSharedOrderVehicleList(u);
 

	
 
		/* We only need to update this-one, because if there is a third
 
		 *  vehicle which shares the same order-list, nothing will change. If
 
		 *  this is the last vehicle, the last line of the order-window
 
		 *  will change from Shared order list, to Order list, so it needs
 
		 *  an update */
 
		InvalidateVehicleOrder(u);
 
		return;
 
		/* Remove ourself from the shared order list. */
 
		v->RemoveFromShared();
 
	} else if (v->orders != NULL) {
 
		/* Remove the orders */
 
		v->orders->FreeChain();
 
	}
 

	
 
	/* Remove the orders */
 
	Order *cur = v->orders;
 
	/* Delete the vehicle list of shared orders, if any */
 
	if (cur != NULL) RemoveSharedOrderVehicleList(v);
 
	v->orders = NULL;
 
	v->num_orders = 0;
 

	
 
	if (cur != NULL) {
 
		cur->FreeChain(); // Free the orders.
 
	}
 
}
 

	
 
Date GetServiceIntervalClamped(uint index)
src/timetable_cmd.cpp
Show inline comments
 
@@ -32,7 +32,7 @@ static void ChangeTimetable(Vehicle *v, 
 
		}
 
	}
 

	
 
	for (v = GetFirstVehicleFromSharedList(v); v != NULL; v = v->next_shared) {
 
	for (v = v->FirstShared(); v != NULL; v = v->NextShared()) {
 
		InvalidateWindow(WC_VEHICLE_TIMETABLE, v->index);
 
	}
 
}
 
@@ -165,7 +165,7 @@ CommandCost CmdAutofillTimetable(TileInd
 
		}
 
	}
 

	
 
	for (v = GetFirstVehicleFromSharedList(v); v != NULL; v = v->next_shared) {
 
	for (v = v->FirstShared(); v != NULL; v = v->NextShared()) {
 
		InvalidateWindow(WC_VEHICLE_TIMETABLE, v->index);
 
	}
 

	
 
@@ -215,7 +215,7 @@ void UpdateVehicleTimetable(Vehicle *v, 
 

	
 
	v->lateness_counter -= (timetabled - time_taken);
 

	
 
	for (v = GetFirstVehicleFromSharedList(v); v != NULL; v = v->next_shared) {
 
	for (v = v->FirstShared(); v != NULL; v = v->NextShared()) {
 
		InvalidateWindow(WC_VEHICLE_TIMETABLE, v->index);
 
	}
 
}
src/train_cmd.cpp
Show inline comments
 
@@ -1427,27 +1427,13 @@ CommandCost CmdSellRailWagon(TileIndex t
 
					new_f->cur_order_index = first->cur_order_index;
 
					new_f->orders          = first->orders;
 
					new_f->num_orders      = first->num_orders;
 

	
 
					/* Make sure the group counts stay correct. */
 
					new_f->group_id        = first->group_id;
 

	
 
					if (first->prev_shared != NULL) {
 
						first->prev_shared->next_shared = new_f;
 
						new_f->prev_shared = first->prev_shared;
 
					}
 

	
 
					if (first->next_shared != NULL) {
 
						first->next_shared->prev_shared = new_f;
 
						new_f->next_shared = first->next_shared;
 
					}
 

	
 
					/*
 
					 * Remove all order information from the front train, to
 
					 * prevent the order and the shared order list to be
 
					 * destroyed by Destroy/DeleteVehicle.
 
					 */
 
					first->orders      = NULL;
 
					first->prev_shared = NULL;
 
					first->next_shared = NULL;
 
					first->group_id    = DEFAULT_GROUP;
 
					first->group_id        = DEFAULT_GROUP;
 

	
 
					new_f->AddToShared(first);
 
					first->RemoveFromShared();
 

	
 
					/* If we deleted a window then open a new one for the 'new' train */
 
					if (IsLocalPlayer() && w != NULL) ShowVehicleViewWindow(new_f);
src/vehicle.cpp
Show inline comments
 
@@ -255,6 +255,7 @@ void AfterLoadVehicles(bool clear_te_id)
 
	FOR_ALL_VEHICLES(v) {
 
		/* Reinstate the previous pointer */
 
		if (v->Next() != NULL) v->Next()->previous = v;
 
		if (v->NextShared() != NULL) v->NextShared()->previous_shared = v;
 

	
 
		v->UpdateDeltaXY(v->direction);
 

	
 
@@ -272,6 +273,13 @@ void AfterLoadVehicles(bool clear_te_id)
 
			for (Vehicle *u = v; u != NULL; u = u->Next()) {
 
				u->first = v;
 
			}
 

	
 
			/* Shared orders are only valid for first vehicles in chains. */
 
			if (v->previous_shared == NULL) {
 
				for (Vehicle *u = v; u != NULL; u = u->NextShared()) {
 
					u->first_shared = v;
 
				}
 
			}
 
		}
 
	}
 

	
 
@@ -329,6 +337,7 @@ Vehicle::Vehicle()
 
	this->group_id           = DEFAULT_GROUP;
 
	this->fill_percent_te_id = INVALID_TE_ID;
 
	this->first              = this;
 
	this->first_shared       = this;
 
	this->colormap           = PAL_NONE;
 
}
 

	
 
@@ -2155,7 +2164,8 @@ static const SaveLoad _common_veh_desc[]
 
	 SLE_CONDVAR(Vehicle, waiting_triggers,     SLE_UINT8,                 2, SL_MAX_VERSION),
 

	
 
	 SLE_CONDREF(Vehicle, next_shared,        REF_VEHICLE,                 2, SL_MAX_VERSION),
 
	 SLE_CONDREF(Vehicle, prev_shared,        REF_VEHICLE,                 2, SL_MAX_VERSION),
 
	SLE_CONDNULL(2,                                                        2, 68),
 
	SLE_CONDNULL(4,                                                       69, 100),
 

	
 
	SLE_CONDVAR(Vehicle, group_id,             SLE_UINT16,                60, SL_MAX_VERSION),
 

	
 
@@ -2390,8 +2400,7 @@ void Load_VEHS()
 
				/* If a vehicle has the same orders, add the link to eachother
 
				 *  in both vehicles */
 
				if (v->orders == u->orders) {
 
					v->next_shared = u;
 
					u->prev_shared = v;
 
					u->AddToShared(v);
 
					break;
 
				}
 
			}
 
@@ -2574,6 +2583,49 @@ void Vehicle::SetNext(Vehicle *next)
 
	}
 
}
 

	
 
void Vehicle::AddToShared(Vehicle *shared_chain)
 
{
 
	assert(!this->IsOrderListShared());
 

	
 
	this->next_shared     = shared_chain->next_shared;
 
	this->previous_shared = shared_chain;
 
	this->first_shared    = shared_chain->first_shared;
 

	
 
	shared_chain->next_shared = this;
 

	
 
	if (this->next_shared != NULL) this->next_shared->previous_shared = this;
 
}
 

	
 
void Vehicle::RemoveFromShared()
 
{
 
	Vehicle *new_first;
 

	
 
	if (this->FirstShared() == this) {
 
		/* We are the first shared one, so update all the first pointers of our next shared ones. */
 
		new_first = this->NextShared();
 
		for (Vehicle *u = new_first; u != NULL; u = u->NextShared()) {
 
			u->first_shared = new_first;
 
		}
 
	} else {
 
		/* We are not the first shared one, so only relink our previous one. */
 
		new_first = this->FirstShared();
 
		this->previous_shared->next_shared = this->NextShared();
 
	}
 

	
 
	if (this->next_shared != NULL) this->next_shared->previous_shared = this->previous_shared;
 

	
 
	if (new_first->NextShared() == NULL) {
 
		/* When there is only one vehicle, remove the shared order list window. */
 
		extern void RemoveSharedOrderVehicleList(Vehicle *v);
 
		if (new_first->orders != NULL) RemoveSharedOrderVehicleList(new_first);
 
		InvalidateVehicleOrder(new_first);
 
	}
 

	
 
	this->first_shared    = this;
 
	this->next_shared     = NULL;
 
	this->previous_shared = NULL;
 
}
 

	
 
void StopAllVehicles()
 
{
 
	Vehicle *v;
src/vehicle_base.h
Show inline comments
 
@@ -202,6 +202,10 @@ private:
 
	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
 

	
 
	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
 
	Vehicle *first_shared;    ///< NOSAVE: pointer to the first vehicle in the shared order chain
 
public:
 
	friend const SaveLoad *GetVehicleDescription(VehicleType vt); ///< So we can use private/protected variables in the saveload code
 
	friend void AfterLoadVehicles(bool clear_te_id);              ///< So we can set the previous and first pointers while loading
 
@@ -214,9 +218,6 @@ public:
 
	TileIndex tile;          ///< Current tile index
 
	TileIndex dest_tile;     ///< Heading for this tile
 

	
 
	Vehicle *next_shared;    ///< If not NULL, this points to the next vehicle that shared the order
 
	Vehicle *prev_shared;    ///< If not NULL, this points to the prev vehicle that shared the order
 

	
 
	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;
 
@@ -476,12 +477,37 @@ public:
 
	 */
 
	inline Vehicle *First() const { return this->first; }
 

	
 

	
 
	/**
 
	 * Adds this vehicle to a shared vehicle chain.
 
	 * @param shared_chain a vehicle of the chain with shared vehicles.
 
	 * @pre !this->IsOrderListShared()
 
	 */
 
	void AddToShared(Vehicle *shared_chain);
 

	
 
	/**
 
	 * Removes the vehicle from the shared order list.
 
	 */
 
	void RemoveFromShared();
 

	
 
	/**
 
	 * 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 *NextShared() const { return this->next_shared; }
 

	
 
	/**
 
	 * Get the first vehicle of this vehicle chain.
 
	 * @return the first vehicle of the chain.
 
	 */
 
	inline Vehicle *FirstShared() const { return this->first_shared; }
 

	
 
	/**
 
	 * Check if we share our orders with another vehicle.
 
	 * This is done by checking the previous and next pointers in the shared chain.
 
	 * @return true if there are other vehicles sharing the same order
 
	 */
 
	inline bool IsOrderListShared() const { return this->next_shared != NULL || this->prev_shared != NULL; };
 
	inline bool IsOrderListShared() const { return this->previous_shared != NULL || this->next_shared != NULL; };
 

	
 
	/**
 
	 * Copy certain configurations and statistics of a vehicle after successful autoreplace/renew
 
@@ -648,18 +674,6 @@ static inline Order *GetLastVehicleOrder
 
	return order;
 
}
 

	
 
/** Get the first vehicle of a shared-list, so we only have to walk forwards
 
 * @param v Vehicle to query
 
 * @return first vehicle of a shared-list
 
 */
 
static inline Vehicle *GetFirstVehicleFromSharedList(const Vehicle *v)
 
{
 
	Vehicle *u = (Vehicle *)v;
 
	while (u->prev_shared != NULL) u = u->prev_shared;
 

	
 
	return u;
 
}
 

	
 
/**
 
 * Returns the Trackdir on which the vehicle is currently located.
 
 * Works for trains and ships.
src/vehiclelist.cpp
Show inline comments
 
@@ -97,7 +97,7 @@ void GenerateVehicleSortList(VehicleList
 
				/* Find a vehicle with the order in question */
 
				if (v->orders != NULL && v->orders->index == index) {
 
					/* Add all vehicles from this vehicle's shared order list */
 
					for (v = GetFirstVehicleFromSharedList(v); v != NULL; v = v->next_shared) {
 
					for (v = v->FirstShared(); v != NULL; v = v->NextShared()) {
 
						*list->Append() = v;
 
					}
 
					break;
0 comments (0 inline, 0 general)