OpenTTD Source  20241120-master-g6d3adc6169
vehiclelist.cpp
Go to the documentation of this file.
1 /*
2  * This file is part of OpenTTD.
3  * 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.
4  * 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.
5  * 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/>.
6  */
7 
10 #include "stdafx.h"
11 #include "train.h"
12 #include "vehicle_func.h"
13 #include "vehiclelist.h"
14 #include "vehiclelist_func.h"
15 #include "group.h"
16 
17 #include "safeguards.h"
18 
24 {
25  uint8_t c = this->company == OWNER_NONE ? 0xF : (uint8_t)this->company;
26  assert(c < (1 << 4));
27  assert(this->vtype < (1 << 2));
28  assert(this->index < (1 << 20));
29  assert(this->type < VLT_END);
30  static_assert(VLT_END <= (1 << 3));
31 
32  return c << 28 | this->type << 23 | this->vtype << 26 | this->index;
33 }
34 
41 {
42  uint8_t c = GB(data, 28, 4);
43  this->company = c == 0xF ? OWNER_NONE : (CompanyID)c;
44  this->type = (VehicleListType)GB(data, 23, 3);
45  this->vtype = (VehicleType)GB(data, 26, 2);
46  this->index = GB(data, 0, 20);
47 
48  return this->type < VLT_END;
49 }
50 
56 {
57  VehicleListIdentifier result;
58  [[maybe_unused]] bool ret = result.UnpackIfValid(data);
59  assert(ret);
60  return result;
61 }
62 
65 {
70 };
71 
78 static Vehicle *BuildDepotVehicleListProc(Vehicle *v, void *data)
79 {
80  auto bdvld = static_cast<BuildDepotVehicleListData *>(data);
81  if (v->type != bdvld->type || !v->IsInDepot()) return nullptr;
82 
83  if (bdvld->type == VEH_TRAIN) {
84  const Train *t = Train::From(v);
85  if (t->IsArticulatedPart() || t->IsRearDualheaded()) return nullptr;
86  if (bdvld->wagons != nullptr && t->First()->IsFreeWagon()) {
87  if (bdvld->individual_wagons || t->IsFreeWagon()) bdvld->wagons->push_back(t);
88  return nullptr;
89  }
90  }
91 
92  if (v->IsPrimaryVehicle()) bdvld->engines->push_back(v);
93  return nullptr;
94 };
95 
104 void BuildDepotVehicleList(VehicleType type, TileIndex tile, VehicleList *engines, VehicleList *wagons, bool individual_wagons)
105 {
106  engines->clear();
107  if (wagons != nullptr && wagons != engines) wagons->clear();
108 
109  BuildDepotVehicleListData bdvld{engines, wagons, type, individual_wagons};
111 }
112 
120 {
121  list->clear();
122 
123  switch (vli.type) {
124  case VL_STATION_LIST:
126  [&vli](const Vehicle *v) { return v->type == vli.vtype; },
127  [&vli](const Order *order) { return (order->IsType(OT_GOTO_STATION) || order->IsType(OT_GOTO_WAYPOINT) || order->IsType(OT_IMPLICIT)) && order->GetDestination() == vli.index; },
128  [&list](const Vehicle *v) { list->push_back(v); }
129  );
130  break;
131 
132  case VL_SHARED_ORDERS: {
133  /* Add all vehicles from this vehicle's shared order list */
134  const Vehicle *v = Vehicle::GetIfValid(vli.index);
135  if (v == nullptr || v->type != vli.vtype || !v->IsPrimaryVehicle()) return false;
136 
137  for (; v != nullptr; v = v->NextShared()) {
138  list->push_back(v);
139  }
140  break;
141  }
142 
143  case VL_GROUP_LIST:
144  if (vli.index != ALL_GROUP) {
145  for (const Vehicle *v : Vehicle::Iterate()) {
146  if (v->type == vli.vtype && v->IsPrimaryVehicle() &&
147  v->owner == vli.company && GroupIsInGroup(v->group_id, vli.index)) {
148  list->push_back(v);
149  }
150  }
151  break;
152  }
153  [[fallthrough]];
154 
155  case VL_STANDARD:
156  for (const Vehicle *v : Vehicle::Iterate()) {
157  if (v->type == vli.vtype && v->owner == vli.company && v->IsPrimaryVehicle()) {
158  list->push_back(v);
159  }
160  }
161  break;
162 
163  case VL_DEPOT_LIST:
165  [&vli](const Vehicle *v) { return v->type == vli.vtype; },
166  [&vli](const Order *order) { return order->IsType(OT_GOTO_DEPOT) && !(order->GetDepotActionType() & ODATFB_NEAREST_DEPOT) && order->GetDestination() == vli.index; },
167  [&list](const Vehicle *v) { list->push_back(v); }
168  );
169  break;
170 
171  default: return false;
172  }
173 
174  return true;
175 }
constexpr static debug_inline uint GB(const T x, const uint8_t s, const uint8_t n)
Fetch n bits from x, started at bit s.
Owner
Enum for all companies/owners.
Definition: company_type.h:18
@ OWNER_NONE
The tile has no ownership.
Definition: company_type.h:25
Base class for groups and group functions.
bool GroupIsInGroup(GroupID search, GroupID group)
Test if GroupID group is a descendant of (or is) GroupID search.
Definition: group_cmd.cpp:874
static const GroupID ALL_GROUP
All vehicles are in this group.
Definition: group_type.h:16
@ ODATFB_NEAREST_DEPOT
Send the vehicle to the nearest depot.
Definition: order_type.h:105
A number of safeguards to prevent using unsafe methods.
Definition of base types and functions in a cross-platform compatible way.
VehicleType type
Type of vehicle.
Definition: vehicle_type.h:51
Data for building a depot vehicle list.
Definition: vehiclelist.cpp:65
VehicleList * engines
Pointer to list to add vehicles to.
Definition: vehiclelist.cpp:66
VehicleType type
Type of vehicle.
Definition: vehiclelist.cpp:68
bool individual_wagons
If true add every wagon to wagons which is not attached to an engine. If false only add the first wag...
Definition: vehiclelist.cpp:69
VehicleList * wagons
Pointer to list to add wagons to (can be nullptr).
Definition: vehiclelist.cpp:67
bool IsRearDualheaded() const
Tell if we are dealing with the rear end of a multiheaded engine.
bool IsFreeWagon() const
Check if the vehicle is a free wagon (got no engine in front of it).
static Titem * GetIfValid(size_t index)
Returns Titem with given index.
Definition: pool_type.hpp:350
static Pool::IterateWrapper< Titem > Iterate(size_t from=0)
Returns an iterable ensemble of all valid Titem.
Definition: pool_type.hpp:388
static T * From(Vehicle *v)
Converts a Vehicle to SpecializedVehicle with type checking.
T * First() const
Get the first vehicle in the chain.
'Train' is either a loco or a wagon.
Definition: train.h:89
The information about a vehicle list.
Definition: vehiclelist.h:28
VehicleListType type
The type of vehicle list.
Definition: vehiclelist.h:29
CompanyID company
The company associated with this list.
Definition: vehiclelist.h:31
uint32_t Pack() const
Pack a VehicleListIdentifier in a single uint32.
Definition: vehiclelist.cpp:23
VehicleType vtype
The vehicle type associated with this list.
Definition: vehiclelist.h:30
static VehicleListIdentifier UnPack(uint32_t data)
Decode a packed vehicle list identifier into a new one.
Definition: vehiclelist.cpp:55
uint32_t index
A vehicle list type specific index.
Definition: vehiclelist.h:32
bool UnpackIfValid(uint32_t data)
Unpack a VehicleListIdentifier from a single uint32.
Definition: vehiclelist.cpp:40
Vehicle data structure.
Definition: vehicle_base.h:244
GroupID group_id
Index of group Pool array.
Definition: vehicle_base.h:366
bool IsArticulatedPart() const
Check if the vehicle is an articulated part of an engine.
Definition: vehicle_base.h:954
virtual bool IsPrimaryVehicle() const
Whether this is the primary vehicle in the chain.
Definition: vehicle_base.h:477
Vehicle * NextShared() const
Get the next vehicle of the shared vehicle chain.
Definition: vehicle_base.h:714
virtual bool IsInDepot() const
Check whether the vehicle is in the depot.
Definition: vehicle_base.h:548
Owner owner
Which company owns the vehicle?
Definition: vehicle_base.h:309
Base for the train class.
void FindVehicleOnPos(TileIndex tile, void *data, VehicleFromPosProc *proc)
Find a vehicle from a specific location.
Definition: vehicle.cpp:505
Functions related to vehicles.
VehicleType
Available vehicle types.
Definition: vehicle_type.h:21
@ VEH_TRAIN
Train vehicle type.
Definition: vehicle_type.h:24
bool GenerateVehicleSortList(VehicleList *list, const VehicleListIdentifier &vli)
Generate a list of vehicles based on window type.
static Vehicle * BuildDepotVehicleListProc(Vehicle *v, void *data)
Add vehicles to a depot vehicle list.
Definition: vehiclelist.cpp:78
void BuildDepotVehicleList(VehicleType type, TileIndex tile, VehicleList *engines, VehicleList *wagons, bool individual_wagons)
Generate a list of vehicles inside a depot.
Functions and type for generating vehicle lists.
std::vector< const Vehicle * > VehicleList
A list of vehicles.
Definition: vehiclelist.h:54
VehicleListType
Vehicle List type flags.
Definition: vehiclelist.h:18
Functions and type for generating vehicle lists.
void FindVehiclesWithOrder(VehiclePredicate veh_pred, OrderPredicate ord_pred, VehicleFunc veh_func)
Find vehicles matching an order.