mirror of
https://github.com/OpenTTD/OpenTTD
synced 2026-01-23 04:04:09 +01:00
Codechange: Use enum class and EnumBitSet for various order flags. (#14783)
This commit is contained in:
@@ -164,10 +164,10 @@ bool Order::Equals(const Order &other) const
|
||||
* evaluation. If we do not do this the order will continuously be seen as
|
||||
* a different order and it will try to find a "nearest depot" every tick. */
|
||||
if ((this->IsType(OT_GOTO_DEPOT) && this->type == other.type) &&
|
||||
((this->GetDepotActionType() & ODATFB_NEAREST_DEPOT) != 0 ||
|
||||
(other.GetDepotActionType() & ODATFB_NEAREST_DEPOT) != 0)) {
|
||||
(this->GetDepotActionType().Test(OrderDepotActionFlag::NearestDepot) ||
|
||||
other.GetDepotActionType().Test(OrderDepotActionFlag::NearestDepot))) {
|
||||
return this->GetDepotOrderType() == other.GetDepotOrderType() &&
|
||||
(this->GetDepotActionType() & ~ODATFB_NEAREST_DEPOT) == (other.GetDepotActionType() & ~ODATFB_NEAREST_DEPOT);
|
||||
this->GetDepotActionType().Reset(OrderDepotActionFlag::NearestDepot) == other.GetDepotActionType().Reset(OrderDepotActionFlag::NearestDepot);
|
||||
}
|
||||
|
||||
return this->type == other.type && this->flags == other.flags && this->dest == other.dest;
|
||||
@@ -185,11 +185,11 @@ uint16_t Order::MapOldOrder() const
|
||||
case OT_GOTO_STATION:
|
||||
if (this->GetUnloadType() & OUFB_UNLOAD) SetBit(order, 5);
|
||||
if (this->GetLoadType() & OLFB_FULL_LOAD) SetBit(order, 6);
|
||||
if (this->GetNonStopType() & ONSF_NO_STOP_AT_INTERMEDIATE_STATIONS) SetBit(order, 7);
|
||||
if (this->GetNonStopType().Test(OrderNonStopFlag::NoIntermediate)) SetBit(order, 7);
|
||||
order |= GB(this->GetDestination().value, 0, 8) << 8;
|
||||
break;
|
||||
case OT_GOTO_DEPOT:
|
||||
if (!(this->GetDepotOrderType() & ODTFB_PART_OF_ORDERS)) SetBit(order, 6);
|
||||
if (!this->GetDepotOrderType().Test(OrderDepotTypeFlag::PartOfOrders)) SetBit(order, 6);
|
||||
SetBit(order, 7);
|
||||
order |= GB(this->GetDestination().value, 0, 8) << 8;
|
||||
break;
|
||||
@@ -331,7 +331,7 @@ VehicleOrderID OrderList::GetNextDecisionNode(VehicleOrderID next, uint hops) co
|
||||
|
||||
const Order &order_next = this->orders[next];
|
||||
if (order_next.IsType(OT_CONDITIONAL)) {
|
||||
if (order_next.GetConditionVariable() != OCV_UNCONDITIONALLY) return next;
|
||||
if (order_next.GetConditionVariable() != OrderConditionVariable::Unconditionally) return next;
|
||||
|
||||
/* We can evaluate trivial conditions right away. They're conceptually
|
||||
* the same as regular order progression. */
|
||||
@@ -341,7 +341,7 @@ VehicleOrderID OrderList::GetNextDecisionNode(VehicleOrderID next, uint hops) co
|
||||
}
|
||||
|
||||
if (order_next.IsType(OT_GOTO_DEPOT)) {
|
||||
if ((order_next.GetDepotActionType() & ODATFB_HALT) != 0) return INVALID_VEH_ORDER_ID;
|
||||
if (order_next.GetDepotActionType().Test(OrderDepotActionFlag::Halt)) return INVALID_VEH_ORDER_ID;
|
||||
if (order_next.IsRefit()) return next;
|
||||
}
|
||||
|
||||
@@ -648,7 +648,7 @@ CommandCost CmdInsertOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
}
|
||||
|
||||
/* Non stop only allowed for ground vehicles. */
|
||||
if (new_order.GetNonStopType() != ONSF_STOP_EVERYWHERE && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
if (new_order.GetNonStopType().Any() && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
|
||||
/* Filter invalid load/unload types. */
|
||||
switch (new_order.GetLoadType()) {
|
||||
@@ -671,12 +671,12 @@ CommandCost CmdInsertOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
|
||||
/* Filter invalid stop locations */
|
||||
switch (new_order.GetStopLocation()) {
|
||||
case OSL_PLATFORM_NEAR_END:
|
||||
case OSL_PLATFORM_MIDDLE:
|
||||
case OrderStopLocation::NearEnd:
|
||||
case OrderStopLocation::Middle:
|
||||
if (v->type != VEH_TRAIN) return CMD_ERROR;
|
||||
[[fallthrough]];
|
||||
|
||||
case OSL_PLATFORM_FAR_END:
|
||||
case OrderStopLocation::FarEnd:
|
||||
break;
|
||||
|
||||
default:
|
||||
@@ -687,7 +687,7 @@ CommandCost CmdInsertOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
}
|
||||
|
||||
case OT_GOTO_DEPOT: {
|
||||
if ((new_order.GetDepotActionType() & ODATFB_NEAREST_DEPOT) == 0) {
|
||||
if (!new_order.GetDepotActionType().Test(OrderDepotActionFlag::NearestDepot)) {
|
||||
if (v->type == VEH_AIRCRAFT) {
|
||||
const Station *st = Station::GetIfValid(new_order.GetDestination().ToStationID());
|
||||
|
||||
@@ -725,15 +725,22 @@ CommandCost CmdInsertOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
}
|
||||
}
|
||||
|
||||
if (new_order.GetNonStopType() != ONSF_STOP_EVERYWHERE && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
if (new_order.GetDepotOrderType() & ~(ODTFB_PART_OF_ORDERS | ((new_order.GetDepotOrderType() & ODTFB_PART_OF_ORDERS) != 0 ? ODTFB_SERVICE : 0))) return CMD_ERROR;
|
||||
if (new_order.GetDepotActionType() & ~(ODATFB_HALT | ODATFB_NEAREST_DEPOT | ODATFB_UNBUNCH)) return CMD_ERROR;
|
||||
if (new_order.GetNonStopType().Any() && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
|
||||
/* Check depot order type is valid. */
|
||||
OrderDepotTypeFlags depot_order_type = new_order.GetDepotOrderType();
|
||||
if (depot_order_type.Test(OrderDepotTypeFlag::PartOfOrders)) depot_order_type.Reset(OrderDepotTypeFlag::Service);
|
||||
depot_order_type.Reset(OrderDepotTypeFlag::PartOfOrders);
|
||||
if (depot_order_type.Any()) return CMD_ERROR;
|
||||
|
||||
/* Check depot action type is valid. */
|
||||
if (new_order.GetDepotActionType().Reset({OrderDepotActionFlag::Halt, OrderDepotActionFlag::NearestDepot, OrderDepotActionFlag::Unbunch}).Any()) return CMD_ERROR;
|
||||
|
||||
/* Vehicles cannot have a "service if needed" order that also has a depot action. */
|
||||
if ((new_order.GetDepotOrderType() & ODTFB_SERVICE) && (new_order.GetDepotActionType() & (ODATFB_HALT | ODATFB_UNBUNCH))) return CMD_ERROR;
|
||||
if (new_order.GetDepotOrderType().Test(OrderDepotTypeFlag::Service) && new_order.GetDepotActionType().Any({OrderDepotActionFlag::Halt, OrderDepotActionFlag::Unbunch})) return CMD_ERROR;
|
||||
|
||||
/* Check if we're allowed to have a new unbunching order. */
|
||||
if ((new_order.GetDepotActionType() & ODATFB_UNBUNCH)) {
|
||||
if (new_order.GetDepotActionType().Test(OrderDepotActionFlag::Unbunch)) {
|
||||
if (v->HasFullLoadOrder()) return CommandCost(STR_ERROR_CAN_T_ADD_ORDER, STR_ERROR_UNBUNCHING_NO_UNBUNCHING_FULL_LOAD);
|
||||
if (v->HasUnbunchingOrder()) return CommandCost(STR_ERROR_CAN_T_ADD_ORDER, STR_ERROR_UNBUNCHING_ONLY_ONE_ALLOWED);
|
||||
if (v->HasConditionalOrder()) return CommandCost(STR_ERROR_CAN_T_ADD_ORDER, STR_ERROR_UNBUNCHING_NO_UNBUNCHING_CONDITIONAL);
|
||||
@@ -776,35 +783,35 @@ CommandCost CmdInsertOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
/* Order flags can be any of the following for waypoints:
|
||||
* [non-stop]
|
||||
* non-stop orders (if any) are only valid for trains and road vehicles */
|
||||
if (new_order.GetNonStopType() != ONSF_STOP_EVERYWHERE && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
if (new_order.GetNonStopType().Any() && !v->IsGroundVehicle()) return CMD_ERROR;
|
||||
break;
|
||||
}
|
||||
|
||||
case OT_CONDITIONAL: {
|
||||
VehicleOrderID skip_to = new_order.GetConditionSkipToOrder();
|
||||
if (skip_to != 0 && skip_to >= v->GetNumOrders()) return CMD_ERROR; // Always allow jumping to the first (even when there is no order).
|
||||
if (new_order.GetConditionVariable() >= OCV_END) return CMD_ERROR;
|
||||
if (new_order.GetConditionVariable() >= OrderConditionVariable::End) return CMD_ERROR;
|
||||
if (v->HasUnbunchingOrder()) return CommandCost(STR_ERROR_UNBUNCHING_NO_CONDITIONAL);
|
||||
|
||||
OrderConditionComparator occ = new_order.GetConditionComparator();
|
||||
if (occ >= OCC_END) return CMD_ERROR;
|
||||
if (occ >= OrderConditionComparator::End) return CMD_ERROR;
|
||||
switch (new_order.GetConditionVariable()) {
|
||||
case OCV_REQUIRES_SERVICE:
|
||||
if (occ != OCC_IS_TRUE && occ != OCC_IS_FALSE) return CMD_ERROR;
|
||||
case OrderConditionVariable::RequiresService:
|
||||
if (occ != OrderConditionComparator::IsTrue && occ != OrderConditionComparator::IsFalse) return CMD_ERROR;
|
||||
break;
|
||||
|
||||
case OCV_UNCONDITIONALLY:
|
||||
if (occ != OCC_EQUALS) return CMD_ERROR;
|
||||
case OrderConditionVariable::Unconditionally:
|
||||
if (occ != OrderConditionComparator::Equal) return CMD_ERROR;
|
||||
if (new_order.GetConditionValue() != 0) return CMD_ERROR;
|
||||
break;
|
||||
|
||||
case OCV_LOAD_PERCENTAGE:
|
||||
case OCV_RELIABILITY:
|
||||
case OrderConditionVariable::LoadPercentage:
|
||||
case OrderConditionVariable::Reliability:
|
||||
if (new_order.GetConditionValue() > 100) return CMD_ERROR;
|
||||
[[fallthrough]];
|
||||
|
||||
default:
|
||||
if (occ == OCC_IS_TRUE || occ == OCC_IS_FALSE) return CMD_ERROR;
|
||||
if (occ == OrderConditionComparator::IsTrue || occ == OrderConditionComparator::IsFalse) return CMD_ERROR;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@@ -945,7 +952,7 @@ static void CancelLoadingDueToDeletedOrder(Vehicle *v)
|
||||
assert(v->current_order.IsType(OT_LOADING));
|
||||
/* NON-stop flag is misused to see if a train is in a station that is
|
||||
* on its order list or not */
|
||||
v->current_order.SetNonStopType(ONSF_STOP_EVERYWHERE);
|
||||
v->current_order.SetNonStopType({});
|
||||
/* When full loading, "cancel" that order so the vehicle doesn't
|
||||
* stay indefinitely at this station anymore. */
|
||||
if (v->current_order.GetLoadType() & OLFB_FULL_LOAD) v->current_order.SetLoadType(OLF_LOAD_IF_POSSIBLE);
|
||||
@@ -1195,19 +1202,25 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
switch (mof) {
|
||||
default: NOT_REACHED();
|
||||
|
||||
case MOF_NON_STOP:
|
||||
case MOF_NON_STOP: {
|
||||
if (!v->IsGroundVehicle()) return CMD_ERROR;
|
||||
if (data >= ONSF_END) return CMD_ERROR;
|
||||
if (data == order->GetNonStopType()) return CMD_ERROR;
|
||||
|
||||
OrderNonStopFlags nonstop_flags = static_cast<OrderNonStopFlags>(data);
|
||||
if (nonstop_flags == order->GetNonStopType()) return CMD_ERROR;
|
||||
|
||||
/* Test for invalid flags. */
|
||||
nonstop_flags.Reset({OrderNonStopFlag::NoIntermediate, OrderNonStopFlag::NoDestination});
|
||||
if (nonstop_flags.Any()) return CMD_ERROR;
|
||||
break;
|
||||
}
|
||||
|
||||
case MOF_STOP_LOCATION:
|
||||
if (v->type != VEH_TRAIN) return CMD_ERROR;
|
||||
if (data >= OSL_END) return CMD_ERROR;
|
||||
if (data >= to_underlying(OrderStopLocation::End)) return CMD_ERROR;
|
||||
break;
|
||||
|
||||
case MOF_UNLOAD:
|
||||
if (order->GetNonStopType() & ONSF_NO_STOP_AT_DESTINATION_STATION) return CMD_ERROR;
|
||||
if (order->GetNonStopType().Test(OrderNonStopFlag::NoDestination)) return CMD_ERROR;
|
||||
if ((data & ~(OUFB_UNLOAD | OUFB_TRANSFER | OUFB_NO_UNLOAD)) != 0) return CMD_ERROR;
|
||||
/* Unload and no-unload are mutual exclusive and so are transfer and no unload. */
|
||||
if (data != 0 && ((data & (OUFB_UNLOAD | OUFB_TRANSFER)) != 0) == ((data & OUFB_NO_UNLOAD) != 0)) return CMD_ERROR;
|
||||
@@ -1215,52 +1228,58 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
break;
|
||||
|
||||
case MOF_LOAD:
|
||||
if (order->GetNonStopType() & ONSF_NO_STOP_AT_DESTINATION_STATION) return CMD_ERROR;
|
||||
if (order->GetNonStopType().Test(OrderNonStopFlag::NoDestination)) return CMD_ERROR;
|
||||
if (data > OLFB_NO_LOAD || data == 1) return CMD_ERROR;
|
||||
if (data == order->GetLoadType()) return CMD_ERROR;
|
||||
if ((data & (OLFB_FULL_LOAD | OLF_FULL_LOAD_ANY)) && v->HasUnbunchingOrder()) return CommandCost(STR_ERROR_UNBUNCHING_NO_FULL_LOAD);
|
||||
break;
|
||||
|
||||
case MOF_DEPOT_ACTION:
|
||||
if (data >= DA_END) return CMD_ERROR;
|
||||
case MOF_DEPOT_ACTION: {
|
||||
OrderDepotAction depot_action = static_cast<OrderDepotAction>(data);
|
||||
if (depot_action >= OrderDepotAction::End) return CMD_ERROR;
|
||||
/* Check if we are allowed to add unbunching. We are always allowed to remove it. */
|
||||
if (data == DA_UNBUNCH) {
|
||||
if (depot_action == OrderDepotAction::Unbunch) {
|
||||
/* Only one unbunching order is allowed in a vehicle's orders. If this order already has an unbunching action, no error is needed. */
|
||||
if (v->HasUnbunchingOrder() && !(order->GetDepotActionType() & ODATFB_UNBUNCH)) return CommandCost(STR_ERROR_UNBUNCHING_ONLY_ONE_ALLOWED);
|
||||
if (v->HasUnbunchingOrder() && !order->GetDepotActionType().Test(OrderDepotActionFlag::Unbunch)) return CommandCost(STR_ERROR_UNBUNCHING_ONLY_ONE_ALLOWED);
|
||||
/* We don't allow unbunching if the vehicle has a conditional order. */
|
||||
if (v->HasConditionalOrder()) return CommandCost(STR_ERROR_UNBUNCHING_NO_UNBUNCHING_CONDITIONAL);
|
||||
/* We don't allow unbunching if the vehicle has a full load order. */
|
||||
if (v->HasFullLoadOrder()) return CommandCost(STR_ERROR_UNBUNCHING_NO_UNBUNCHING_FULL_LOAD);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case MOF_COND_VARIABLE:
|
||||
if (data >= OCV_END) return CMD_ERROR;
|
||||
case MOF_COND_VARIABLE: {
|
||||
OrderConditionVariable cond_variable = static_cast<OrderConditionVariable>(data);
|
||||
if (cond_variable >= OrderConditionVariable::End) return CMD_ERROR;
|
||||
break;
|
||||
}
|
||||
|
||||
case MOF_COND_COMPARATOR:
|
||||
if (data >= OCC_END) return CMD_ERROR;
|
||||
case MOF_COND_COMPARATOR: {
|
||||
OrderConditionComparator cond_comparator = static_cast<OrderConditionComparator>(data);
|
||||
if (cond_comparator >= OrderConditionComparator::End) return CMD_ERROR;
|
||||
switch (order->GetConditionVariable()) {
|
||||
case OCV_UNCONDITIONALLY: return CMD_ERROR;
|
||||
case OrderConditionVariable::Unconditionally: return CMD_ERROR;
|
||||
|
||||
case OCV_REQUIRES_SERVICE:
|
||||
if (data != OCC_IS_TRUE && data != OCC_IS_FALSE) return CMD_ERROR;
|
||||
case OrderConditionVariable::RequiresService:
|
||||
if (cond_comparator != OrderConditionComparator::IsTrue && cond_comparator != OrderConditionComparator::IsFalse) return CMD_ERROR;
|
||||
break;
|
||||
|
||||
default:
|
||||
if (data == OCC_IS_TRUE || data == OCC_IS_FALSE) return CMD_ERROR;
|
||||
if (cond_comparator == OrderConditionComparator::IsTrue || cond_comparator == OrderConditionComparator::IsFalse) return CMD_ERROR;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case MOF_COND_VALUE:
|
||||
switch (order->GetConditionVariable()) {
|
||||
case OCV_UNCONDITIONALLY:
|
||||
case OCV_REQUIRES_SERVICE:
|
||||
case OrderConditionVariable::Unconditionally:
|
||||
case OrderConditionVariable::RequiresService:
|
||||
return CMD_ERROR;
|
||||
|
||||
case OCV_LOAD_PERCENTAGE:
|
||||
case OCV_RELIABILITY:
|
||||
case OrderConditionVariable::LoadPercentage:
|
||||
case OrderConditionVariable::Reliability:
|
||||
if (data > 100) return CMD_ERROR;
|
||||
break;
|
||||
|
||||
@@ -1278,8 +1297,8 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
if (flags.Test(DoCommandFlag::Execute)) {
|
||||
switch (mof) {
|
||||
case MOF_NON_STOP:
|
||||
order->SetNonStopType((OrderNonStopFlags)data);
|
||||
if (data & ONSF_NO_STOP_AT_DESTINATION_STATION) {
|
||||
order->SetNonStopType(static_cast<OrderNonStopFlags>(data));
|
||||
if (order->GetNonStopType().Test(OrderNonStopFlag::NoDestination)) {
|
||||
order->SetRefit(CARGO_NO_REFIT);
|
||||
order->SetLoadType(OLF_LOAD_IF_POSSIBLE);
|
||||
order->SetUnloadType(OUF_UNLOAD_IF_POSSIBLE);
|
||||
@@ -1287,7 +1306,7 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
break;
|
||||
|
||||
case MOF_STOP_LOCATION:
|
||||
order->SetStopLocation((OrderStopLocation)data);
|
||||
order->SetStopLocation(static_cast<OrderStopLocation>(data));
|
||||
break;
|
||||
|
||||
case MOF_UNLOAD:
|
||||
@@ -1300,31 +1319,27 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
break;
|
||||
|
||||
case MOF_DEPOT_ACTION: {
|
||||
switch (data) {
|
||||
case DA_ALWAYS_GO:
|
||||
order->SetDepotOrderType((OrderDepotTypeFlags)(order->GetDepotOrderType() & ~ODTFB_SERVICE));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_HALT));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_UNBUNCH));
|
||||
switch (static_cast<OrderDepotAction>(data)) {
|
||||
case OrderDepotAction::AlwaysGo:
|
||||
order->SetDepotOrderType(order->GetDepotOrderType().Reset(OrderDepotTypeFlag::Service));
|
||||
order->SetDepotActionType(order->GetDepotActionType().Reset({OrderDepotActionFlag::Halt, OrderDepotActionFlag::Unbunch}));
|
||||
break;
|
||||
|
||||
case DA_SERVICE:
|
||||
order->SetDepotOrderType((OrderDepotTypeFlags)(order->GetDepotOrderType() | ODTFB_SERVICE));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_HALT));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_UNBUNCH));
|
||||
case OrderDepotAction::Service:
|
||||
order->SetDepotOrderType(order->GetDepotOrderType().Set(OrderDepotTypeFlag::Service));
|
||||
order->SetDepotActionType(order->GetDepotActionType().Reset({OrderDepotActionFlag::Halt, OrderDepotActionFlag::Unbunch}));
|
||||
order->SetRefit(CARGO_NO_REFIT);
|
||||
break;
|
||||
|
||||
case DA_STOP:
|
||||
order->SetDepotOrderType((OrderDepotTypeFlags)(order->GetDepotOrderType() & ~ODTFB_SERVICE));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() | ODATFB_HALT));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_UNBUNCH));
|
||||
case OrderDepotAction::Stop:
|
||||
order->SetDepotOrderType(order->GetDepotOrderType().Reset(OrderDepotTypeFlag::Service));
|
||||
order->SetDepotActionType(order->GetDepotActionType().Set(OrderDepotActionFlag::Halt).Reset(OrderDepotActionFlag::Unbunch));
|
||||
order->SetRefit(CARGO_NO_REFIT);
|
||||
break;
|
||||
|
||||
case DA_UNBUNCH:
|
||||
order->SetDepotOrderType((OrderDepotTypeFlags)(order->GetDepotOrderType() & ~ODTFB_SERVICE));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_HALT));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() | ODATFB_UNBUNCH));
|
||||
case OrderDepotAction::Unbunch:
|
||||
order->SetDepotOrderType(order->GetDepotOrderType().Reset(OrderDepotTypeFlag::Service));
|
||||
order->SetDepotActionType(order->GetDepotActionType().Reset(OrderDepotActionFlag::Halt).Set(OrderDepotActionFlag::Unbunch));
|
||||
break;
|
||||
|
||||
default:
|
||||
@@ -1338,23 +1353,23 @@ CommandCost CmdModifyOrder(DoCommandFlags flags, VehicleID veh, VehicleOrderID s
|
||||
|
||||
OrderConditionComparator occ = order->GetConditionComparator();
|
||||
switch (order->GetConditionVariable()) {
|
||||
case OCV_UNCONDITIONALLY:
|
||||
order->SetConditionComparator(OCC_EQUALS);
|
||||
case OrderConditionVariable::Unconditionally:
|
||||
order->SetConditionComparator(OrderConditionComparator::Equal);
|
||||
order->SetConditionValue(0);
|
||||
break;
|
||||
|
||||
case OCV_REQUIRES_SERVICE:
|
||||
if (occ != OCC_IS_TRUE && occ != OCC_IS_FALSE) order->SetConditionComparator(OCC_IS_TRUE);
|
||||
case OrderConditionVariable::RequiresService:
|
||||
if (occ != OrderConditionComparator::IsTrue && occ != OrderConditionComparator::IsFalse) order->SetConditionComparator(OrderConditionComparator::IsTrue);
|
||||
order->SetConditionValue(0);
|
||||
break;
|
||||
|
||||
case OCV_LOAD_PERCENTAGE:
|
||||
case OCV_RELIABILITY:
|
||||
case OrderConditionVariable::LoadPercentage:
|
||||
case OrderConditionVariable::Reliability:
|
||||
if (order->GetConditionValue() > 100) order->SetConditionValue(100);
|
||||
[[fallthrough]];
|
||||
|
||||
default:
|
||||
if (occ == OCC_IS_TRUE || occ == OCC_IS_FALSE) order->SetConditionComparator(OCC_EQUALS);
|
||||
if (occ == OrderConditionComparator::IsTrue || occ == OrderConditionComparator::IsFalse) order->SetConditionComparator(OrderConditionComparator::Equal);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@@ -1605,8 +1620,8 @@ CommandCost CmdOrderRefit(DoCommandFlags flags, VehicleID veh, VehicleOrderID or
|
||||
|
||||
/* Make the depot order an 'always go' order. */
|
||||
if (cargo != CARGO_NO_REFIT && order->IsType(OT_GOTO_DEPOT)) {
|
||||
order->SetDepotOrderType((OrderDepotTypeFlags)(order->GetDepotOrderType() & ~ODTFB_SERVICE));
|
||||
order->SetDepotActionType((OrderDepotActionFlags)(order->GetDepotActionType() & ~ODATFB_HALT));
|
||||
order->SetDepotOrderType(order->GetDepotOrderType().Reset(OrderDepotTypeFlag::Service));
|
||||
order->SetDepotActionType(order->GetDepotActionType().Reset(OrderDepotActionFlag::Halt));
|
||||
}
|
||||
|
||||
for (Vehicle *u = v->FirstShared(); u != nullptr; u = u->NextShared()) {
|
||||
@@ -1614,7 +1629,7 @@ CommandCost CmdOrderRefit(DoCommandFlags flags, VehicleID veh, VehicleOrderID or
|
||||
InvalidateVehicleOrder(u, VIWD_MODIFY_ORDERS);
|
||||
|
||||
/* If the vehicle already got the current depot set as current order, then update current order as well */
|
||||
if (u->cur_real_order_index == order_number && (u->current_order.GetDepotOrderType() & ODTFB_PART_OF_ORDERS)) {
|
||||
if (u->cur_real_order_index == order_number && u->current_order.GetDepotOrderType().Test(OrderDepotTypeFlag::PartOfOrders)) {
|
||||
u->current_order.SetRefit(cargo);
|
||||
}
|
||||
}
|
||||
@@ -1725,7 +1740,7 @@ void RemoveOrderFromAllVehicles(OrderType type, DestinationID destination, bool
|
||||
next_id = id + 1;
|
||||
Order *order = v->orders->GetOrderAt(id);
|
||||
OrderType ot = order->GetType();
|
||||
if (ot == OT_GOTO_DEPOT && (order->GetDepotActionType() & ODATFB_NEAREST_DEPOT) != 0) continue;
|
||||
if (ot == OT_GOTO_DEPOT && order->GetDepotActionType().Test(OrderDepotActionFlag::NearestDepot)) continue;
|
||||
if (ot == OT_GOTO_DEPOT && hangar && v->type != VEH_AIRCRAFT) continue; // Not an aircraft? Can't have a hangar order.
|
||||
if (ot == OT_IMPLICIT || (v->type == VEH_AIRCRAFT && ot == OT_GOTO_DEPOT && !hangar)) ot = OT_GOTO_STATION;
|
||||
if (ot == type && order->GetDestination() == destination) {
|
||||
@@ -1844,14 +1859,14 @@ static bool CheckForValidOrders(const Vehicle *v)
|
||||
static bool OrderConditionCompare(OrderConditionComparator occ, int variable, int value)
|
||||
{
|
||||
switch (occ) {
|
||||
case OCC_EQUALS: return variable == value;
|
||||
case OCC_NOT_EQUALS: return variable != value;
|
||||
case OCC_LESS_THAN: return variable < value;
|
||||
case OCC_LESS_EQUALS: return variable <= value;
|
||||
case OCC_MORE_THAN: return variable > value;
|
||||
case OCC_MORE_EQUALS: return variable >= value;
|
||||
case OCC_IS_TRUE: return variable != 0;
|
||||
case OCC_IS_FALSE: return variable == 0;
|
||||
case OrderConditionComparator::Equal: return variable == value;
|
||||
case OrderConditionComparator::NotEqual: return variable != value;
|
||||
case OrderConditionComparator::LessThan: return variable < value;
|
||||
case OrderConditionComparator::LessThanOrEqual: return variable <= value;
|
||||
case OrderConditionComparator::MoreThan: return variable > value;
|
||||
case OrderConditionComparator::MoreThanOrEqual: return variable >= value;
|
||||
case OrderConditionComparator::IsTrue: return variable != 0;
|
||||
case OrderConditionComparator::IsFalse: return variable == 0;
|
||||
default: NOT_REACHED();
|
||||
}
|
||||
}
|
||||
@@ -1876,14 +1891,14 @@ VehicleOrderID ProcessConditionalOrder(const Order *order, const Vehicle *v)
|
||||
uint16_t value = order->GetConditionValue();
|
||||
|
||||
switch (order->GetConditionVariable()) {
|
||||
case OCV_LOAD_PERCENTAGE: skip_order = OrderConditionCompare(occ, CalcPercentVehicleFilled(v, nullptr), value); break;
|
||||
case OCV_RELIABILITY: skip_order = OrderConditionCompare(occ, ToPercent16(v->reliability), value); break;
|
||||
case OCV_MAX_RELIABILITY: skip_order = OrderConditionCompare(occ, ToPercent16(v->GetEngine()->reliability), value); break;
|
||||
case OCV_MAX_SPEED: skip_order = OrderConditionCompare(occ, v->GetDisplayMaxSpeed() * 10 / 16, value); break;
|
||||
case OCV_AGE: skip_order = OrderConditionCompare(occ, TimerGameCalendar::DateToYear(v->age), value); break;
|
||||
case OCV_REQUIRES_SERVICE: skip_order = OrderConditionCompare(occ, v->NeedsServicing(), value); break;
|
||||
case OCV_UNCONDITIONALLY: skip_order = true; break;
|
||||
case OCV_REMAINING_LIFETIME: skip_order = OrderConditionCompare(occ, std::max(TimerGameCalendar::DateToYear(v->max_age - v->age + CalendarTime::DAYS_IN_LEAP_YEAR - 1), TimerGameCalendar::Year(0)), value); break;
|
||||
case OrderConditionVariable::LoadPercentage: skip_order = OrderConditionCompare(occ, CalcPercentVehicleFilled(v, nullptr), value); break;
|
||||
case OrderConditionVariable::Reliability: skip_order = OrderConditionCompare(occ, ToPercent16(v->reliability), value); break;
|
||||
case OrderConditionVariable::MaxReliability: skip_order = OrderConditionCompare(occ, ToPercent16(v->GetEngine()->reliability), value); break;
|
||||
case OrderConditionVariable::MaxSpeed: skip_order = OrderConditionCompare(occ, v->GetDisplayMaxSpeed() * 10 / 16, value); break;
|
||||
case OrderConditionVariable::Age: skip_order = OrderConditionCompare(occ, TimerGameCalendar::DateToYear(v->age), value); break;
|
||||
case OrderConditionVariable::RequiresService: skip_order = OrderConditionCompare(occ, v->NeedsServicing(), value); break;
|
||||
case OrderConditionVariable::Unconditionally: skip_order = true; break;
|
||||
case OrderConditionVariable::RemainingLifetime: skip_order = OrderConditionCompare(occ, std::max(TimerGameCalendar::DateToYear(v->max_age - v->age + CalendarTime::DAYS_IN_LEAP_YEAR - 1), TimerGameCalendar::Year(0)), value); break;
|
||||
default: NOT_REACHED();
|
||||
}
|
||||
|
||||
@@ -1911,14 +1926,14 @@ bool UpdateOrderDest(Vehicle *v, const Order *order, int conditional_depth, bool
|
||||
return true;
|
||||
|
||||
case OT_GOTO_DEPOT:
|
||||
if ((order->GetDepotOrderType() & ODTFB_SERVICE) && !v->NeedsServicing()) {
|
||||
if (order->GetDepotOrderType().Test(OrderDepotTypeFlag::Service) && !v->NeedsServicing()) {
|
||||
assert(!pbs_look_ahead);
|
||||
UpdateVehicleTimetable(v, true);
|
||||
v->IncrementRealOrderIndex();
|
||||
break;
|
||||
}
|
||||
|
||||
if (v->current_order.GetDepotActionType() & ODATFB_NEAREST_DEPOT) {
|
||||
if (v->current_order.GetDepotActionType().Test(OrderDepotActionFlag::NearestDepot)) {
|
||||
/* If the vehicle can't find its destination, delay its next search.
|
||||
* In case many vehicles are in this state, use the vehicle index to spread out pathfinder calls. */
|
||||
if (v->dest_tile == 0 && TimerGameEconomy::date_fract != (v->index % Ticks::DAY_TICKS)) break;
|
||||
@@ -2031,7 +2046,7 @@ bool ProcessOrders(Vehicle *v)
|
||||
switch (v->current_order.GetType()) {
|
||||
case OT_GOTO_DEPOT:
|
||||
/* Let a depot order in the orderlist interrupt. */
|
||||
if (!(v->current_order.GetDepotOrderType() & ODTFB_PART_OF_ORDERS)) return false;
|
||||
if (!v->current_order.GetDepotOrderType().Test(OrderDepotTypeFlag::PartOfOrders)) return false;
|
||||
break;
|
||||
|
||||
case OT_LOADING:
|
||||
@@ -2054,7 +2069,7 @@ bool ProcessOrders(Vehicle *v)
|
||||
bool may_reverse = v->current_order.IsType(OT_NOTHING);
|
||||
|
||||
/* Check if we've reached a 'via' destination. */
|
||||
if (((v->current_order.IsType(OT_GOTO_STATION) && (v->current_order.GetNonStopType() & ONSF_NO_STOP_AT_DESTINATION_STATION)) || v->current_order.IsType(OT_GOTO_WAYPOINT)) &&
|
||||
if (((v->current_order.IsType(OT_GOTO_STATION) && v->current_order.GetNonStopType().Test(OrderNonStopFlag::NoDestination)) || v->current_order.IsType(OT_GOTO_WAYPOINT)) &&
|
||||
IsTileType(v->tile, MP_STATION) &&
|
||||
v->current_order.GetDestination() == GetStationIndex(v->tile)) {
|
||||
v->DeleteUnreachedImplicitOrders();
|
||||
@@ -2128,16 +2143,16 @@ bool Order::ShouldStopAtStation(const Vehicle *v, StationID station) const
|
||||
{
|
||||
bool is_dest_station = this->IsType(OT_GOTO_STATION) && this->dest == station;
|
||||
|
||||
return (!this->IsType(OT_GOTO_DEPOT) || (this->GetDepotOrderType() & ODTFB_PART_OF_ORDERS) != 0) &&
|
||||
return (!this->IsType(OT_GOTO_DEPOT) || this->GetDepotOrderType().Test(OrderDepotTypeFlag::PartOfOrders)) &&
|
||||
v->last_station_visited != station && // Do stop only when we've not just been there
|
||||
/* Finally do stop when there is no non-stop flag set for this type of station. */
|
||||
!(this->GetNonStopType() & (is_dest_station ? ONSF_NO_STOP_AT_DESTINATION_STATION : ONSF_NO_STOP_AT_INTERMEDIATE_STATIONS));
|
||||
!this->GetNonStopType().Test(is_dest_station ? OrderNonStopFlag::NoDestination : OrderNonStopFlag::NoIntermediate);
|
||||
}
|
||||
|
||||
bool Order::CanLoadOrUnload() const
|
||||
{
|
||||
return (this->IsType(OT_GOTO_STATION) || this->IsType(OT_IMPLICIT)) &&
|
||||
(this->GetNonStopType() & ONSF_NO_STOP_AT_DESTINATION_STATION) == 0 &&
|
||||
!this->GetNonStopType().Test(OrderNonStopFlag::NoDestination) &&
|
||||
((this->GetLoadType() & OLFB_NO_LOAD) == 0 ||
|
||||
(this->GetUnloadType() & OUFB_NO_UNLOAD) == 0);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user