Eclipse SUMO - Simulation of Urban MObility
MSDevice_FCDReplay.cpp
Go to the documentation of this file.
1 /****************************************************************************/
2 // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3 // Copyright (C) 2013-2024 German Aerospace Center (DLR) and others.
4 // This program and the accompanying materials are made available under the
5 // terms of the Eclipse Public License 2.0 which is available at
6 // https://www.eclipse.org/legal/epl-2.0/
7 // This Source Code may also be made available under the following Secondary
8 // Licenses when the conditions for such availability set forth in the Eclipse
9 // Public License 2.0 are satisfied: GNU General Public License, version 2
10 // or later which is available at
11 // https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html
12 // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
13 /****************************************************************************/
18 // A device which replays recorded floating car data
19 /****************************************************************************/
20 #include <config.h>
21 
23 #include <utils/geom/Position.h>
26 #include <utils/xml/XMLSubSys.h>
27 #include <libsumo/Vehicle.h>
28 #include <microsim/MSNet.h>
29 #include <microsim/MSEdge.h>
30 #include <microsim/MSLane.h>
31 #include <microsim/MSRoute.h>
39 #include "MSDevice_FCDReplay.h"
40 
41 
42 // ===========================================================================
43 // static member initializations
44 // ===========================================================================
47 
48 
49 // ===========================================================================
50 // method definitions
51 // ===========================================================================
52 // ---------------------------------------------------------------------------
53 // static initialisation methods
54 // ---------------------------------------------------------------------------
55 void
57  oc.addOptionSubTopic("FCD Replay Device");
58  insertDefaultAssignmentOptions("fcd-replay", "FCD Replay Device", oc);
59 
60  oc.doRegister("device.fcd-replay.file", new Option_FileName());
61  oc.addDescription("device.fcd-replay.file", "FCD Replay Device", TL("FCD file to read"));
62 }
63 
64 
65 void
66 MSDevice_FCDReplay::buildVehicleDevices(SUMOVehicle& v, std::vector<MSVehicleDevice*>& into) {
68  if (equippedByDefaultAssignmentOptions(oc, "fcd-replay", v, oc.isSet("device.fcd-replay.file"))) {
69  MSDevice_FCDReplay* device = new MSDevice_FCDReplay(v, "fcdReplay_" + v.getID());
70  into.push_back(device);
71  }
72 }
73 
74 
75 void
77  myHandler.reset();
79  if (oc.isSet("device.fcd-replay.file")) {
80  const std::string& filename = oc.getString("device.fcd-replay.file");
82  if (!myParser->parseFirst(filename)) {
83  throw ProcessError(TLF("Can not read XML-file '%'.", filename));
84  }
85  const SUMOTime inc = parseNext(SIMSTEP);
87  if (inc > 0) {
89  SIMSTEP + inc);
90  }
91  }
92 }
93 
94 
97  SUMOTime inc = string2time(OptionsCont::getOptions().getString("route-steps"));
98  // make sure that we have always at least inc time steps buffered, so at time 200 we will parse 400 to 600
99  const SUMOTime start = myHandler.getTime();
100  while (myHandler.getTime() < t + 2 * inc) {
101  if (!myParser->parseNext()) {
102  inc = 0;
103  break;
104  }
105  }
107  return inc;
108 }
109 
110 
111 // ---------------------------------------------------------------------------
112 // MSDevice_FCDReplay-methods
113 // ---------------------------------------------------------------------------
114 MSDevice_FCDReplay::MSDevice_FCDReplay(SUMOVehicle& holder, const std::string& id) :
115  MSVehicleDevice(holder, id) {
116 }
117 
118 
120 }
121 
122 
123 void
125  if (myTrajectory == nullptr || myTrajectoryIndex == (int)myTrajectory->size()) {
126  // removal happens via the usual MSVehicle::hasArrived mechanism
127  // TODO we may need to set an arrivalPos
128  return;
129  }
130  MSVehicle* v = dynamic_cast<MSVehicle*>(&myHolder);
132  if (v == nullptr || te.time > currentTime) {
133  return;
134  }
135  const std::string& edgeID = SUMOXMLDefinitions::getEdgeIDFromLane(te.edgeOrLane);
136  const int laneIdx = SUMOXMLDefinitions::getIndexFromLane(te.edgeOrLane);
137  libsumo::Vehicle::moveToXY(myHolder.getID(), edgeID, laneIdx, te.pos.x(), te.pos.y(), te.angle, 7);
138  libsumo::Vehicle::setSpeed(myHolder.getID(), te.speed);
139  // libsumo::Vehicle::changeLane(myHolder.getID(), laneIdx, TS);
141 }
142 
143 
144 SUMOTime
147  for (MSVehicleControl::constVehIt i = c.loadedVehBegin(); i != c.loadedVehEnd(); ++i) {
148  MSDevice_FCDReplay* device = static_cast<MSDevice_FCDReplay*>(i->second->getDevice(typeid(MSDevice_FCDReplay)));
149  if (device != nullptr && i->second->hasDeparted()) {
150  device->move(currentTime);
151  }
152  }
153  return DELTA_T;
154 }
155 
156 
157 // ---------------------------------------------------------------------------
158 // MSDevice_FCDReplay::FCDHandler-methods
159 // ---------------------------------------------------------------------------
160 void
162  bool ok = true;
163  switch (element) {
164  case SUMO_TAG_TIMESTEP:
165  myTime = attrs.getSUMOTimeReporting(SUMO_ATTR_TIME, "", ok);
166  myPositions.clear();
167  return;
168  case SUMO_TAG_VEHICLE:
169  case SUMO_TAG_PERSON: {
170  if (myTime >= SIMSTEP) {
171  const bool isPerson = element == SUMO_TAG_PERSON;
172  const std::string id = attrs.getString(SUMO_ATTR_ID);
173  const Position xy = Position(attrs.getOpt<double>(SUMO_ATTR_X, id.c_str(), ok, INVALID_DOUBLE),
174  attrs.getOpt<double>(SUMO_ATTR_Y, id.c_str(), ok, INVALID_DOUBLE));
175  const std::string type = attrs.getOpt<std::string>(SUMO_ATTR_TYPE, id.c_str(), ok, "");
176  const std::string edgeOrLane = attrs.getOpt<std::string>(isPerson ? SUMO_ATTR_EDGE : SUMO_ATTR_LANE, id.c_str(), ok, "");
177  const double speed = attrs.getOpt<double>(SUMO_ATTR_SPEED, id.c_str(), ok, INVALID_DOUBLE);
178  const double pos = attrs.getOpt<double>(SUMO_ATTR_POSITION, id.c_str(), ok, INVALID_DOUBLE);
179  const double angle = attrs.getOpt<double>(SUMO_ATTR_ANGLE, id.c_str(), ok, INVALID_DOUBLE);
180  std::string vehicle = attrs.getOpt<std::string>(SUMO_ATTR_VEHICLE, id.c_str(), ok, "");
181  if (isPerson) {
182  if (vehicle == "") {
183  const auto& veh = myPositions.find(xy);
184  if (veh != myPositions.end()) {
185  vehicle = veh->second;
186  }
187  }
188  } else {
189  myPositions[xy] = id;
190  }
191  myTrajectories[id].push_back({myTime, xy, edgeOrLane, pos, speed, angle});
192  const MSEdge* const edge = MSEdge::dictionary(isPerson ? edgeOrLane : SUMOXMLDefinitions::getEdgeIDFromLane(edgeOrLane));
193  if (edge != nullptr) { // TODO maybe warn for unknown edge?
194  if (myRoutes.count(id) == 0) {
195  myRoutes[id] = std::make_tuple(myTime, type, isPerson, ConstMSEdgeVector{edge}, std::vector<StageStart>());
196  } else {
197  ConstMSEdgeVector& route = std::get<3>(myRoutes[id]);
198  if (!edge->isInternal() && edge != route.back()) {
199  route.push_back(edge);
200  }
201  }
202  std::vector<StageStart>& vehicleUsage = std::get<4>(myRoutes[id]);
203  if ((vehicleUsage.empty() && vehicle != "") || (!vehicleUsage.empty() && vehicle != vehicleUsage.back().vehicle)) {
204  vehicleUsage.push_back({vehicle, (int)myTrajectories[id].size() - 1, (int)std::get<3>(myRoutes[id]).size() - 1});
205  }
206  }
207  }
208  return;
209  }
210  default:
211  break;
212  }
213 }
214 
215 
216 void
218  myTime = 0;
219  myTrajectories.clear();
220  myRoutes.clear();
221 }
222 
223 
226  const std::vector<StageStart>& stages, const Trajectory& t) {
228  plan->push_back(new MSStageWaiting(route.front(), nullptr, 0, params.depart, params.departPos, "awaiting departure", true));
229  int prevRouteOffset = 0;
230  const MSEdge* start = route.front();
231  std::string prevVeh;
232  for (const auto& stageStart : stages) {
233  if (stageStart.vehicle != prevVeh) {
234  if (stageStart.trajectoryOffset != 0) {
235  const MSEdge* prevEdge = MSEdge::dictionary(t[stageStart.trajectoryOffset - 1].edgeOrLane);
236  if (prevVeh == "") {
237  MSStoppingPlace* finalStop = nullptr;
238  if (prevRouteOffset < (int)route.size() - 1 && (route[prevRouteOffset]->getPermissions() & SVC_PEDESTRIAN) == 0) {
239  prevRouteOffset++; // skip the access
240  }
241  int offset = stageStart.routeOffset;
242  if (offset < (int)route.size() - 1 && (route[offset]->getPermissions() & SVC_PEDESTRIAN) == SVC_PEDESTRIAN) {
243  offset++; // a bus stop or two consecutive walks so include the edge in both
244  } else {
245  // may have an access, let's find the stop
246  const std::string& stop = MSNet::getInstance()->getStoppingPlaceID(route[offset]->getLanes()[0], t[stageStart.trajectoryOffset].lanePos, SUMO_TAG_BUS_STOP);
247  if (stop != "") {
249  }
250  }
251  ConstMSEdgeVector subRoute = ConstMSEdgeVector(route.begin() + prevRouteOffset, route.begin() + offset);
252  plan->push_back(new MSStageWalking(params.id, subRoute, finalStop, -1, params.departSpeed, params.departPos, 0, 0));
253  } else {
254  plan->push_back(new MSStageDriving(start, prevEdge, nullptr, -1, 0, {prevVeh}));
255  }
256  start = MSEdge::dictionary(t[stageStart.trajectoryOffset].edgeOrLane);
257  prevVeh = stageStart.vehicle;
258  prevRouteOffset = stageStart.routeOffset;
259  }
260  }
261  }
262  // final stage
263  if (prevVeh == "") {
264  if (prevRouteOffset < (int)route.size() - 1 && (route[prevRouteOffset]->getPermissions() & SVC_PEDESTRIAN) == 0) {
265  prevRouteOffset++;
266  }
267  int offset = (int)route.size() - 1;
268  if ((route[offset]->getPermissions() & SVC_PEDESTRIAN) == SVC_PEDESTRIAN) {
269  offset++;
270  }
271  if (prevRouteOffset < offset) {
272  // otherwise we may be still in a vehicle or in access, skip the stage for now
273  ConstMSEdgeVector subRoute = ConstMSEdgeVector(route.begin() + prevRouteOffset, route.begin() + offset);
274  plan->push_back(new MSStageWalking(params.id, subRoute, nullptr, -1, params.departSpeed, params.departPos, 0, 0));
275  }
276  } else {
277  plan->push_back(new MSStageDriving(start, route.back(), nullptr, -1, 0, {prevVeh}));
278  }
279  return plan;
280 }
281 
282 
285  ConstMSEdgeVector checkedRoute;
286  for (const MSEdge* const e : edges) {
287  if (checkedRoute.empty() || checkedRoute.back()->isConnectedTo(*e, vehicle->getVehicleType().getVehicleClass())) {
288  checkedRoute.push_back(e);
289  } else {
290  const MSEdge* fromEdge = checkedRoute.back();
291  checkedRoute.pop_back();
292  if (!MSNet::getInstance()->getRouterTT(0).compute(fromEdge, e, vehicle, myTime, checkedRoute)) {
293  // TODO maybe warn about disconnected route
294  checkedRoute.push_back(fromEdge);
295  checkedRoute.push_back(e);
296  }
297  // TODO check whether we introduced a big detour
298  }
299  }
300  return checkedRoute;
301 }
302 
303 
304 void
306  for (const auto& desc : myRoutes) {
307  const std::string& id = desc.first;
308  const bool isPerson = std::get<2>(desc.second);
309  Trajectory& t = myTrajectories[id];
310  if (t.front().time >= intervalStart) {
311  // new vehicle or person
313  params->id = id;
314  params->depart = std::get<0>(desc.second);
315  params->departPos = t.front().lanePos;
316  params->departSpeed = t.front().speed;
317  // params->arrivalPos = t.back().lanePos;
318  std::string vType = std::get<1>(desc.second);
319  if (vType == "") {
320  vType = isPerson ? DEFAULT_PEDTYPE_ID : DEFAULT_VTYPE_ID;
321  }
322  MSVehicleType* vehicleType = MSNet::getInstance()->getVehicleControl().getVType(vType);
323  if (vehicleType == nullptr) {
324  throw ProcessError("Unknown vType '" + vType + "'.");
325  }
326  if (isPerson) {
327  MSTransportable::MSTransportablePlan* plan = makePlan(*params, std::get<3>(desc.second), std::get<4>(desc.second), t);
328  // plan completed, now build the person
329  MSTransportable* person = MSNet::getInstance()->getPersonControl().buildPerson(params, vehicleType, plan, nullptr);
331  if (!MSNet::getInstance()->getPersonControl().add(person)) {
332  throw ProcessError("Duplicate person '" + id + "'.");
333  }
335  if (device == nullptr) { // Person did not get a replay device
336  // TODO delete person
337  continue;
338  }
339  device->setTrajectory(&t);
340  } else {
341  const std::string dummyRouteID = "DUMMY_ROUTE_" + id;
342  const std::vector<SUMOVehicleParameter::Stop> stops;
343  const ConstMSEdgeVector& routeEdges = std::get<3>(desc.second);
344  ConstMSRoutePtr route = std::make_shared<MSRoute>(dummyRouteID, routeEdges, true, nullptr, stops);
345  if (!MSRoute::dictionary(dummyRouteID, route)) {
346  throw ProcessError("Could not add route '" + dummyRouteID + "'.");
347  }
349  params->departLane = SUMOXMLDefinitions::getIndexFromLane(t.front().edgeOrLane);
350  SUMOVehicle* vehicle = MSNet::getInstance()->getVehicleControl().buildVehicle(params, route, vehicleType, false);
351  if (!MSNet::getInstance()->getVehicleControl().addVehicle(id, vehicle)) {
352  throw ProcessError("Duplicate vehicle '" + id + "'.");
353  }
355  MSDevice_FCDReplay* device = static_cast<MSDevice_FCDReplay*>(vehicle->getDevice(typeid(MSDevice_FCDReplay)));
356  if (device == nullptr) { // Vehicle did not get a replay device
358  continue;
359  }
360  device->setTrajectory(&t);
361  static_cast<MSVehicle*>(vehicle)->getInfluencer().setSpeedMode(0);
362 
363  // repair the route, cannot do this on parsing because a vehicle is needed
364  ConstMSEdgeVector checkedRoute = checkRoute(routeEdges, vehicle);
365  if (checkedRoute.size() != routeEdges.size()) {
366  vehicle->replaceRouteEdges(checkedRoute, -1, 0, "FCDReplay", true);
367  }
368  }
369  } else if (t.back().time >= intervalStart) {
370  // new data for existing person / vehicle
371  if (isPerson) {
373  // TODO optimize: no need to regenerate the whole plan
374  MSTransportable::MSTransportablePlan* plan = makePlan(person->getParameter(), std::get<3>(desc.second), std::get<4>(desc.second), t);
375  const int stageIndex = person->getNumRemainingStages() - 1;
376  MSStage* const final = person->getNextStage(stageIndex);
377  bool append = false;
378  for (MSStage* stage : *plan) {
379  if (stage->getStageType() == final->getStageType() && stage->getFromEdge() == final->getFromEdge()) {
380  // TODO: circular plans?
381  append = true;
382  }
383  if (append) {
384  person->appendStage(stage);
385  }
386  }
387  person->removeStage(stageIndex);
388  } else {
390  const ConstMSEdgeVector& routeEdges = std::get<3>(desc.second);
391  ConstMSEdgeVector checkedRoute = checkRoute(routeEdges, vehicle);
392  if ((int)checkedRoute.size() != vehicle->getRoute().size()) {
393  vehicle->replaceRouteEdges(checkedRoute, -1, 0, "FCDReplay", true);
394  }
395  }
396  }
397  }
398 }
399 
400 
401 /****************************************************************************/
long long int SUMOTime
Definition: GUI.h:35
std::vector< const MSEdge * > ConstMSEdgeVector
Definition: MSEdge.h:74
#define TL(string)
Definition: MsgHandler.h:315
#define TLF(string,...)
Definition: MsgHandler.h:317
std::shared_ptr< const MSRoute > ConstMSRoutePtr
Definition: Route.h:31
SUMOTime DELTA_T
Definition: SUMOTime.cpp:38
SUMOTime string2time(const std::string &r)
convert string to SUMOTime
Definition: SUMOTime.cpp:46
#define SIMSTEP
Definition: SUMOTime.h:61
const std::string DEFAULT_PEDTYPE_ID
const std::string DEFAULT_VTYPE_ID
@ SVC_IGNORING
vehicles ignoring classes
@ SVC_PEDESTRIAN
pedestrian
@ GIVEN
The lane is given.
@ SUMO_TAG_TIMESTEP
@ SUMO_TAG_BUS_STOP
A bus stop.
@ SUMO_TAG_VEHICLE
description of a vehicle
@ SUMO_TAG_PERSON
@ SUMO_ATTR_LANE
@ SUMO_ATTR_SPEED
@ SUMO_ATTR_Y
@ SUMO_ATTR_EDGE
@ SUMO_ATTR_X
@ SUMO_ATTR_ANGLE
@ SUMO_ATTR_VEHICLE
@ SUMO_ATTR_TYPE
@ SUMO_ATTR_ID
@ SUMO_ATTR_POSITION
@ SUMO_ATTR_TIME
trigger: the time of the step
const double INVALID_DOUBLE
invalid double
Definition: StdDefs.h:64
void updateTrafficObjects(const SUMOTime intervalStart)
ConstMSEdgeVector checkRoute(const ConstMSEdgeVector &edges, const SUMOVehicle *const vehicle)
MSTransportable::MSTransportablePlan * makePlan(const SUMOVehicleParameter &params, const ConstMSEdgeVector &route, const std::vector< StageStart > &stages, const Trajectory &t)
void myStartElement(int element, const SUMOSAXAttributes &attrs)
Called on the opening of a tag.
SUMOTime execute(SUMOTime currentTime)
Executes the command.
A device which replays a vehicle trajectory from an fcd file.
~MSDevice_FCDReplay()
Destructor.
static FCDHandler myHandler
static void init()
Static intialization.
std::vector< TrajectoryEntry > Trajectory
static SUMOTime parseNext(SUMOTime t)
static void buildVehicleDevices(SUMOVehicle &v, std::vector< MSVehicleDevice * > &into)
Build devices for the given vehicle, if needed.
MSDevice_FCDReplay(SUMOVehicle &holder, const std::string &id)
Constructor.
void move(SUMOTime currentTime)
static SUMOSAXReader * myParser
void setTrajectory(Trajectory *const t)
static void insertOptions(OptionsCont &oc)
Inserts MSDevice_FCDReplay-options.
static void insertDefaultAssignmentOptions(const std::string &deviceName, const std::string &optionsTopic, OptionsCont &oc, const bool isPerson=false)
Adds common command options that allow to assign devices to vehicles.
Definition: MSDevice.cpp:155
static bool equippedByDefaultAssignmentOptions(const OptionsCont &oc, const std::string &deviceName, DEVICEHOLDER &v, bool outputOptionSet, const bool isPerson=false)
Determines whether a vehicle should get a certain device.
Definition: MSDevice.h:203
A road/street connecting two junctions.
Definition: MSEdge.h:77
bool isInternal() const
return whether this edge is an internal edge
Definition: MSEdge.h:265
static bool dictionary(const std::string &id, MSEdge *edge)
Inserts edge into the static dictionary Returns true if the key id isn't already in the dictionary....
Definition: MSEdge.cpp:983
virtual void addEvent(Command *operation, SUMOTime execTimeStep=-1)
Adds an Event.
void add(SUMOVehicle *veh)
Adds a single vehicle for departure.
static MSNet * getInstance()
Returns the pointer to the unique instance of MSNet (singleton).
Definition: MSNet.cpp:182
MSVehicleControl & getVehicleControl()
Returns the vehicle control.
Definition: MSNet.h:378
std::string getStoppingPlaceID(const MSLane *lane, const double pos, const SumoXMLTag category) const
Returns the stop of the given category close to the given position.
Definition: MSNet.cpp:1373
MSStoppingPlace * getStoppingPlace(const std::string &id, const SumoXMLTag category) const
Returns the named stopping place of the given category.
Definition: MSNet.cpp:1364
MSInsertionControl & getInsertionControl()
Returns the insertion control.
Definition: MSNet.h:431
MSEventControl * getBeginOfTimestepEvents()
Returns the event control for events executed at the begin of a time step.
Definition: MSNet.h:471
virtual MSTransportableControl & getPersonControl()
Returns the person control.
Definition: MSNet.cpp:1173
int size() const
Returns the number of edges to pass.
Definition: MSRoute.cpp:85
static bool dictionary(const std::string &id, ConstMSRoutePtr route)
Adds a route to the dictionary.
Definition: MSRoute.cpp:109
A lane area vehicles can halt at.
virtual MSTransportable * buildPerson(const SUMOVehicleParameter *pars, MSVehicleType *vtype, MSTransportable::MSTransportablePlan *plan, SumoRNG *rng) const
Builds a new person.
MSTransportable * get(const std::string &id) const
Returns the named transportable, if existing.
A device which collects info on the vehicle trip (mainly on departure and arrival)
void setTrajectory(MSDevice_FCDReplay::Trajectory *const t)
MSStage * getNextStage(int offset) const
Return the next (or previous) stage denoted by the offset.
int getNumRemainingStages() const
Return the number of remaining stages (including the current)
const SUMOVehicleParameter & getParameter() const
Returns the vehicle's parameter (including departure definition)
void removeStage(int next, bool stayInSim=true)
removes the nth next stage
void appendStage(MSStage *stage, int next=-1)
Appends the given stage to the current plan.
MSVehicleType & getSingularType()
Replaces the current vehicle type with a new one used by this vehicle only.
std::vector< MSStage * > MSTransportablePlan
the structure holding the plan of a transportable
MSDevice * getDevice(const std::type_info &type) const
Returns a device of the given type if it exists or nullptr if not.
The class responsible for building and deletion of vehicles.
virtual SUMOVehicle * buildVehicle(SUMOVehicleParameter *defs, ConstMSRoutePtr route, MSVehicleType *type, const bool ignoreStopErrors, const bool fromRouteFile=true, bool addRouteStops=true)
Builds a vehicle, increases the number of built vehicles.
std::map< std::string, SUMOVehicle * >::const_iterator constVehIt
Definition of the internal vehicles map iterator.
SUMOVehicle * getVehicle(const std::string &id) const
Returns the vehicle with the given id.
MSVehicleType * getVType(const std::string &id=DEFAULT_VTYPE_ID, SumoRNG *rng=nullptr, bool readOnly=false)
Returns the named vehicle type or a sample from the named distribution.
virtual void deleteVehicle(SUMOVehicle *v, bool discard=false, bool wasKept=false)
Deletes the vehicle.
constVehIt loadedVehBegin() const
Returns the begin of the internal vehicle map.
constVehIt loadedVehEnd() const
Returns the end of the internal vehicle map.
Abstract in-vehicle device.
SUMOVehicle & myHolder
The vehicle that stores the device.
Representation of a vehicle in the micro simulation.
Definition: MSVehicle.h:77
The car-following model and parameter.
Definition: MSVehicleType.h:63
SUMOVehicleClass getVehicleClass() const
Get this vehicle type's vehicle class.
void setVClass(SUMOVehicleClass vclass)
Set a new value for this type's vehicle class.
const std::string & getID() const
Returns the id.
Definition: Named.h:74
A storage for options typed value containers)
Definition: OptionsCont.h:89
void addDescription(const std::string &name, const std::string &subtopic, const std::string &description)
Adds a description for an option.
bool isSet(const std::string &name, bool failOnNonExistant=true) const
Returns the information whether the named option is set.
std::string getString(const std::string &name) const
Returns the string-value of the named option (only for Option_String)
void doRegister(const std::string &name, Option *o)
Adds an option under the given name.
Definition: OptionsCont.cpp:76
void addOptionSubTopic(const std::string &topic)
Adds an option subtopic.
static OptionsCont & getOptions()
Retrieves the options.
Definition: OptionsCont.cpp:60
A point in 2D or 3D with translation and scaling methods.
Definition: Position.h:37
double x() const
Returns the x-position.
Definition: Position.h:55
double y() const
Returns the y-position.
Definition: Position.h:60
Encapsulated SAX-Attributes.
virtual std::string getString(int id, bool *isPresent=nullptr) const =0
Returns the string-value of the named (by its enum-value) attribute.
T getOpt(int attr, const char *objectid, bool &ok, T defaultValue=T(), bool report=true) const
Tries to read given attribute assuming it is an int.
SUMOTime getSUMOTimeReporting(int attr, const char *objectid, bool &ok, bool report=true) const
Tries to read given attribute assuming it is a SUMOTime.
SAX-reader encapsulation containing binary reader.
Definition: SUMOSAXReader.h:53
bool parseFirst(std::string systemID)
Start parsing the given file using parseFirst of myXMLReader.
bool parseNext()
Continue a progressive parse started by parseFirst.
virtual MSDevice * getDevice(const std::type_info &type) const =0
Returns a device of the given type if it exists or nullptr if not.
virtual const MSVehicleType & getVehicleType() const =0
Returns the object's "vehicle" type.
Representation of a vehicle.
Definition: SUMOVehicle.h:60
virtual bool replaceRouteEdges(ConstMSEdgeVector &edges, double cost, double savings, const std::string &info, bool onInit=false, bool check=false, bool removeStops=true, std::string *msgReturn=nullptr)=0
Replaces the current route by the given edges.
virtual const MSRoute & getRoute() const =0
Returns the current route.
Structure representing possible vehicle parameter.
int departLane
(optional) The lane the vehicle shall depart from (index in edge)
double departSpeed
(optional) The initial speed of the vehicle
DepartLaneDefinition departLaneProcedure
Information how the vehicle shall choose the lane to depart from.
double departPos
(optional) The position the vehicle shall depart from
std::string id
The vehicle's id.
static std::string getEdgeIDFromLane(const std::string laneID)
return edge id when given the lane ID
static int getIndexFromLane(const std::string laneID)
return lane index when given the lane ID
A wrapper for a Command function.
Definition: StaticCommand.h:38
static SUMOSAXReader * getSAXReader(SUMOSAXHandler &handler, const bool isNet=false, const bool isRoute=false)
Builds a reader and assigns the handler to it.
Definition: XMLSubSys.cpp:132
SUMOTime time
double angle
std::string edgeOrLane
Position pos
double speed