Changeset - r6832:856e7cea465f
[Not reviewed]
master
0 5 0
rubidium - 17 years ago 2007-06-08 18:59:29
rubidium@openttd.org
(svn r10071) -Feature [FS#828]: moving of orders (skidd13).
5 files changed with 168 insertions and 6 deletions:
0 comments (0 inline, 0 general)
src/command.cpp
Show inline comments
 
@@ -176,6 +176,8 @@ DEF_COMMAND(CmdAddSharedVehicleGroup);
 
DEF_COMMAND(CmdRemoveAllVehiclesGroup);
 
DEF_COMMAND(CmdSetGroupReplaceProtection);
 

	
 
DEF_COMMAND(CmdMoveOrder);
 

	
 
/* The master command table */
 
static const Command _command_proc_table[] = {
 
	{CmdBuildRailroadTrack,                  0}, /*   0 */
 
@@ -328,6 +330,7 @@ static const Command _command_proc_table
 
	{CmdAddSharedVehicleGroup,               0}, /* 124 */
 
	{CmdRemoveAllVehiclesGroup,              0}, /* 125 */
 
	{CmdSetGroupReplaceProtection,           0}, /* 126 */
 
	{CmdMoveOrder,                           0}, /* 127 */
 
};
 

	
 
/* This function range-checks a cmd, and checks if the cmd is not NULL */
src/command.h
Show inline comments
 
@@ -143,6 +143,7 @@ enum {
 
	CMD_MASS_START_STOP              = 117,
 
	CMD_DEPOT_SELL_ALL_VEHICLES      = 118,
 
	CMD_DEPOT_MASS_AUTOREPLACE       = 119,
 

	
 
	CMD_CREATE_GROUP                 = 120,
 
	CMD_DELETE_GROUP                 = 121,
 
	CMD_RENAME_GROUP                 = 122,
 
@@ -150,6 +151,8 @@ enum {
 
	CMD_ADD_SHARED_VEHICLE_GROUP     = 124,
 
	CMD_REMOVE_ALL_VEHICLES_GROUP    = 125,
 
	CMD_SET_GROUP_REPLACE_PROTECTION = 126,
 

	
 
	CMD_MOVE_ORDER                   = 127,
 
};
 

	
 
enum {
src/lang/english.txt
Show inline comments
 
@@ -2663,6 +2663,7 @@ STR_8832_TOO_MANY_ORDERS                
 
STR_8833_CAN_T_INSERT_NEW_ORDER                                 :{WHITE}Can't insert new order...
 
STR_8834_CAN_T_DELETE_THIS_ORDER                                :{WHITE}Can't delete this order...
 
STR_8835_CAN_T_MODIFY_THIS_ORDER                                :{WHITE}Can't modify this order...
 
STR_CAN_T_MOVE_THIS_ORDER                                       :{WHITE}Can't move this order...
 
STR_CAN_T_SKIP_ORDER                                            :{WHITE}Can't skip current order...
 
STR_CAN_T_SKIP_TO_ORDER                                         :{WHITE}Can't skip to selected order...
 
STR_8837_CAN_T_MOVE_VEHICLE                                     :{WHITE}Can't move vehicle...
src/order_cmd.cpp
Show inline comments
 
@@ -598,6 +598,91 @@ int32 CmdSkipToOrder(TileIndex tile, uin
 
	return 0;
 
}
 

	
 
/**
 
 * Move an order inside the orderlist
 
 * @param tile unused
 
 * @param p1 the ID of the vehicle
 
 * @param p2 order to move and target
 
 *           bit 0-15  : the order to move
 
 *           bit 16-31 : the target order
 
 * @note The target order will move one place down in the orderlist
 
 *  if you move the order upwards else it'll move it one place down
 
 */
 
int32 CmdMoveOrder(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
 
{
 
	VehicleID veh = p1;
 
	VehicleOrderID moving_order = GB(p2,  0, 16);
 
	VehicleOrderID target_order = GB(p2, 16, 16);
 

	
 
	if (!IsValidVehicleID(veh)) return CMD_ERROR;
 

	
 
	Vehicle *v = GetVehicle(veh);
 
	if (!CheckOwnership(v->owner)) return CMD_ERROR;
 

	
 
	/* Don't make senseless movements */
 
	if (moving_order >= v->num_orders || target_order >= v->num_orders ||
 
			moving_order == target_order || v->num_orders <= 1)
 
		return CMD_ERROR;
 

	
 
	Order *moving_one = GetVehicleOrder(v, moving_order);
 
	/* Don't move an empty order */
 
	if (moving_one == NULL) return CMD_ERROR;
 

	
 
	if (flags & DC_EXEC) {
 
		/* Take the moving order out of the pointer-chain */
 
		Order *one_before = GetVehicleOrder(v, moving_order - 1);
 
		Order *one_past = GetVehicleOrder(v, moving_order + 1);
 

	
 
		if (one_before == NULL) {
 
			/* First order edit */
 
			v->orders = moving_one->next;
 
		} else {
 
			one_before->next = moving_one->next;
 
		}
 

	
 
		/* Insert the moving_order again in the pointer-chain */
 
		one_before = GetVehicleOrder(v, target_order - 1);
 
		one_past = GetVehicleOrder(v, target_order);
 

	
 
		moving_one->next = one_past;
 

	
 
		if (one_before == NULL) {
 
			/* first order edit */
 
			SwapOrders(v->orders, moving_one);
 
			v->orders->next = moving_one;
 
		} else {
 
			one_before->next = moving_one;
 
		}
 

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

	
 
		DeleteOrderWarnings(u);
 

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

	
 
			/* Update the current order */
 
			if (u->cur_order_index == moving_order) {
 
				u->cur_order_index = target_order;
 
			} else if(u->cur_order_index > moving_order && u->cur_order_index <= target_order) {
 
				u->cur_order_index--;
 
			} else if(u->cur_order_index < moving_order && u->cur_order_index >= target_order) {
 
				u->cur_order_index++;
 
			}
 

	
 
			assert(v->orders == u->orders);
 
			/* Update any possible open window of the vehicle */
 
			InvalidateVehicleOrder(u);
 
		}
 

	
 
		/* Make sure to rebuild the whole list */
 
		RebuildVehicleLists();
 
	}
 

	
 
	return 0;
 
}
 

	
 
/** Modify an order in the orderlist of a vehicle.
 
 * @param tile unused
src/order_gui.cpp
Show inline comments
 
@@ -44,6 +44,13 @@ enum OrderWindowWidgets {
 
	ORDER_WIDGET_RESIZE,
 
};
 

	
 
/**
 
 * Return the memorised selected order.
 
 *
 
 * @param w current window
 
 * @return the memorised order if it is a vaild one
 
 *  else return the number of orders
 
 */
 
static int OrderGetSel(const Window *w)
 
{
 
	const Vehicle *v = GetVehicle(w->window_number);
 
@@ -52,6 +59,33 @@ static int OrderGetSel(const Window *w)
 
	return (num >= 0 && num < v->num_orders) ? num : v->num_orders;
 
}
 

	
 
/**
 
 * Calculate the selected order.
 
 * The calculation is based on the relative (to the window) y click position and
 
 *  the position of the scrollbar.
 
 *
 
 * @param w current window
 
 * @param y Y-value of the click relative to the window origin
 
 * @param v current vehicle
 
 * @return the new selected order if the order is valid else return that
 
 *  an invalid one has been selected.
 
 */
 
static int GetOrderFromOrderWndPt(Window *w, int y, const Vehicle *v)
 
{
 
	/*
 
	 * Calculation description:
 
	 * 15 = 14 (w->widget[ORDER_WIDGET_ORDER_LIST].top) + 1 (frame-line)
 
	 * 10 = order text hight
 
	 */
 
	int sel = (y - 15) / 10;
 

	
 
	if ((uint)sel >= w->vscroll.cap) return INVALID_ORDER;
 

	
 
	sel += w->vscroll.pos;
 

	
 
	return (sel <= v->num_orders && sel >= 0) ? sel : INVALID_ORDER;
 
}
 

	
 
static StringID StationOrderStrings[] = {
 
	STR_8806_GO_TO,
 
	STR_8807_GO_TO_TRANSFER,
 
@@ -513,14 +547,14 @@ static void OrdersWndProc(Window *w, Win
 
		break;
 

	
 
	case WE_CLICK: {
 
		Vehicle *v = GetVehicle(w->window_number);
 
		const Vehicle *v = GetVehicle(w->window_number);
 
		switch (e->we.click.widget) {
 
		case ORDER_WIDGET_ORDER_LIST: {
 
			int sel = (e->we.click.pt.y - 15) / 10;
 
			ResetObjectToPlace();
 

	
 
			if ((uint)sel >= w->vscroll.cap) return;
 
			int sel = GetOrderFromOrderWndPt(w, e->we.click.pt.y, v);
 

	
 
			sel += w->vscroll.pos;
 
			if (sel == INVALID_ORDER) return;
 

	
 
			if (_ctrl_pressed && sel < v->num_orders) {
 
				const Order *ord = GetVehicleOrder(v, sel);
 
@@ -535,10 +569,21 @@ static void OrdersWndProc(Window *w, Win
 

	
 
				if (xy != 0) ScrollMainWindowToTile(xy);
 
				return;
 
			} else {
 
				if (sel == WP(w,order_d).sel) {
 
					/* Deselect clicked order */
 
					WP(w,order_d).sel = -1;
 
				} else {
 
					/* Select clicked order */
 
					WP(w,order_d).sel = sel;
 

	
 
					if (v->owner == _local_player) {
 
						/* Activate drag and drop */
 
						SetObjectToPlaceWnd(SPR_CURSOR_MOUSE, PAL_NONE, 4, w);
 
					}
 
				}
 
			}
 

	
 
			if (sel == WP(w,order_d).sel) sel = -1;
 
			WP(w,order_d).sel = sel;
 
			SetWindowDirty(w);
 
		} break;
 

	
 
@@ -578,6 +623,31 @@ static void OrdersWndProc(Window *w, Win
 
		}
 
	} break;
 

	
 
	case WE_DRAGDROP: {
 
		const Vehicle *v = GetVehicle(w->window_number);
 

	
 
		switch (e->we.click.widget) {
 
			case ORDER_WIDGET_ORDER_LIST: {
 
				int from_order = OrderGetSel(w);
 
				int to_order = GetOrderFromOrderWndPt(w, e->we.dragdrop.pt.y, v);
 

	
 
				if (!(from_order == to_order || from_order == INVALID_ORDER || from_order > v->num_orders || to_order == INVALID_ORDER || to_order > v->num_orders) &&
 
						DoCommandP(v->tile, v->index, from_order | (to_order << 16), NULL, CMD_MOVE_ORDER | CMD_MSG(STR_CAN_T_MOVE_THIS_ORDER))) {
 
					WP(w, order_d).sel = -1;
 
				}
 

	
 
				break;
 
			}
 

	
 
			case ORDER_WIDGET_DELETE:
 
				OrderClick_Delete(w, v);
 
				break;
 
		}
 

	
 
		ResetObjectToPlace();
 
		break;
 
	}
 

	
 
	case WE_KEYPRESS: {
 
		Vehicle *v = GetVehicle(w->window_number);
 
		uint i;
0 comments (0 inline, 0 general)