void GUIEdge::addRerouter() { MSEdgeVector edges; edges.push_back(this); GUITriggeredRerouter* rr = new GUITriggeredRerouter(getID() + "_dynamic_rerouter", edges, 1, "", false, GUINet::getGUIInstance()->getVisualisationSpeedUp()); MSTriggeredRerouter::RerouteInterval ri; ri.begin = MSNet::getInstance()->getCurrentTimeStep(); ri.end = SUMOTime_MAX; ri.edgeProbs.add(1, &MSTriggeredRerouter::mySpecialDest_keepDestination); rr->myIntervals.push_back(ri); // trigger rerouting for vehicles already on this edge const std::vector<MSLane*>& lanes = getLanes(); for (std::vector<MSLane*>::const_iterator i = lanes.begin(); i != lanes.end(); ++i) { const MSLane::VehCont& vehicles = (*i)->getVehiclesSecure(); for (MSLane::VehCont::const_iterator v = vehicles.begin(); v != vehicles.end(); ++v) { if ((*v)->getLane() == (*i)) { rr->notifyEnter(**v, MSMoveReminder::NOTIFICATION_JUNCTION); } // else: this is the shadow during a continuous lane change } (*i)->releaseVehicles(); } }
/* ------------------------------------------------------------------------- * MSPerson::MSPersonStage_Walking - methods * ----------------------------------------------------------------------- */ MSPerson::MSPersonStage_Walking::MSPersonStage_Walking(MSEdgeVector route, SUMOTime walkingTime, SUMOReal speed) : MSPersonStage(*route.back()), myWalkingTime(walkingTime) { if (speed > 0) { SUMOReal time = 0; for (MSEdgeVector::const_iterator it = route.begin(); it != route.end(); ++it) { time += ((*it)->getLanes())[0]->getLength() * speed; } myWalkingTime = MAX2(walkingTime, (SUMOTime)(time * 1000.)); } }
/* ------------------------------------------------------------------------- * GUITriggeredRerouter - methods * ----------------------------------------------------------------------- */ GUITriggeredRerouter::GUITriggeredRerouter( const std::string& id, const MSEdgeVector& edges, SUMOReal prob, const std::string& aXMLFilename, bool off, SUMORTree& rtree) : MSTriggeredRerouter(id, edges, prob, aXMLFilename, off), GUIGlObject_AbstractAdd("rerouter", GLO_TRIGGER, id) { // add visualisation objects for edges which trigger the rerouter for (MSEdgeVector::const_iterator it = edges.begin(); it != edges.end(); ++it) { myEdgeVisualizations.push_back(new GUITriggeredRerouterEdge(dynamic_cast<GUIEdge*>(*it), this, false)); rtree.addAdditionalGLObject(myEdgeVisualizations.back()); myBoundary.add(myEdgeVisualizations.back()->getCenteringBoundary()); } }
bool TraCIServerAPI_Route::processSet(TraCIServer& server, tcpip::Storage& inputStorage, tcpip::Storage& outputStorage) { std::string warning = ""; // additional description for response // variable int variable = inputStorage.readUnsignedByte(); if (variable != ADD) { server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_ERR, "Change Route State: unsupported variable specified", outputStorage); return false; } // id std::string id = inputStorage.readString(); // process int valueDataType = inputStorage.readUnsignedByte(); switch (variable) { case ADD: { if (valueDataType != TYPE_STRINGLIST) { server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_ERR, "A string list is needed for adding a new route.", outputStorage); return false; } //read itemNo int numEdges = inputStorage.readInt(); MSEdgeVector edges; while (numEdges--) { std::string edgeID = inputStorage.readString(); MSEdge* edge = MSEdge::dictionary(edgeID); if (edge == 0) { server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_ERR, "Unknown edge '" + edgeID + "' in route.", outputStorage); return false; } edges.push_back(edge); } const std::vector<SUMOVehicleParameter::Stop> stops; if (!MSRoute::dictionary(id, new MSRoute(id, edges, 1, 0, stops))) { server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_ERR, "Could not add route.", outputStorage); return false; } } break; default: break; } server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_OK, warning, outputStorage); return true; }
bool TraCIServerAPI_Route::processSet(TraCIServer& server, tcpip::Storage& inputStorage, tcpip::Storage& outputStorage) { std::string warning = ""; // additional description for response // variable int variable = inputStorage.readUnsignedByte(); if (variable != ADD) { return server.writeErrorStatusCmd(CMD_SET_ROUTE_VARIABLE, "Change Route State: unsupported variable specified", outputStorage); } // id std::string id = inputStorage.readString(); // process switch (variable) { case ADD: { std::vector<std::string> edgeIDs; if (!server.readTypeCheckingStringList(inputStorage, edgeIDs)) { return server.writeErrorStatusCmd(CMD_SET_ROUTE_VARIABLE, "A string list is needed for adding a new route.", outputStorage); } //read itemNo MSEdgeVector edges; for (std::vector<std::string>::const_iterator i = edgeIDs.begin(); i != edgeIDs.end(); ++i) { MSEdge* edge = MSEdge::dictionary(*i); if (edge == 0) { return server.writeErrorStatusCmd(CMD_SET_ROUTE_VARIABLE, "Unknown edge '" + *i + "' in route.", outputStorage); } edges.push_back(edge); } const std::vector<SUMOVehicleParameter::Stop> stops; if (!MSRoute::dictionary(id, new MSRoute(id, edges, 1, 0, stops))) { return server.writeErrorStatusCmd(CMD_SET_ROUTE_VARIABLE, "Could not add route.", outputStorage); } } break; default: break; } server.writeStatusCmd(CMD_SET_ROUTE_VARIABLE, RTYPE_OK, warning, outputStorage); return true; }
bool MSRailSignal::hasLinkConflict(int index) const { #ifdef DEBUG_SIGNALSTATE_PRIORITY //if (DEBUG_COND) std::cout << SIMTIME << " railSignal=" << getID() << " index=" << index << " hasLinkConflict...\n"; #endif MSLink* currentLink = myLinks[index][0]; double foeMaxSpeed = -1; double foeMinDist = std::numeric_limits<double>::max(); SUMOTime foeMinETA = std::numeric_limits<SUMOTime>::max(); long long foeMinNumericalID = std::numeric_limits<long long>::max(); // tie braker // check for vehicles that enter the (unconditional) conflict area and // resolve conflict according to priority std::vector<int> checkRouteConflict; const auto& cLinks = myConflictLinks[index]; for (int clIndex = 0; clIndex < (int)cLinks.size(); ++clIndex) { if (myRouteConflictLanes[index][clIndex].size() > 0) { // record links where the conditional conflict area may be occupied checkRouteConflict.push_back(clIndex); } const MSLink* link = cLinks[clIndex]; if (link->getApproaching().size() > 0) { const MSTrafficLightLogic* foeTLL = link->getTLLogic(); assert(foeTLL != nullptr); const MSRailSignal* foeRS = dynamic_cast<const MSRailSignal*>(foeTLL); if (foeRS != nullptr) { if (foeRS->conflictLaneOccupied(link->getTLIndex())) { #ifdef DEBUG_SIGNALSTATE_PRIORITY if (DEBUG_COND) std::cout << SIMTIME << " railSignal=" << getID() << " index=" << index << " foeLink " << link->getViaLaneOrLane()->getID() << " (ignored)\n"; #endif continue; } } else if (link->getState() == LINKSTATE_TL_RED) { // ignore foe vehicles waiting at a regular traffic light continue; } } for (auto apprIt : link->getApproaching()) { MSLink::ApproachingVehicleInformation info = apprIt.second; foeMaxSpeed = MAX2(apprIt.first->getSpeed(), foeMaxSpeed); foeMinDist = MIN2(info.dist, foeMinDist); if (info.willPass) { foeMinETA = MIN2(info.arrivalTime, foeMinETA); } foeMinNumericalID = MIN2(foeMinNumericalID, apprIt.first->getNumericalID()); } } SUMOVehicle* closest = nullptr; if (foeMaxSpeed >= 0 || checkRouteConflict.size() > 0) { // check against vehicles approaching this link double maxSpeed = -1; double minDist = std::numeric_limits<double>::max(); SUMOTime minETA = std::numeric_limits<SUMOTime>::max(); long long minNumericalID = std::numeric_limits<long long>::max(); // tie braker for (auto apprIt : currentLink->getApproaching()) { MSLink::ApproachingVehicleInformation info = apprIt.second; maxSpeed = MAX2(apprIt.first->getSpeed(), maxSpeed); if (info.dist < minDist) { minDist = info.dist; closest = const_cast<SUMOVehicle*>(apprIt.first); } if (info.willPass) { minETA = MIN2(info.arrivalTime, minETA); } minNumericalID = MIN2(minNumericalID, apprIt.first->getNumericalID()); } #ifdef DEBUG_SIGNALSTATE_PRIORITY if (DEBUG_COND) std::cout << SIMTIME << " railSignal=" << getID() << " index=" << index << " fms=" << foeMaxSpeed << " ms=" << maxSpeed << " fmd=" << foeMinDist << " md=" << minDist << " fmE=" << foeMinETA << " mE=" << minETA << " fmI=" << foeMinNumericalID << " mI=" << minNumericalID << "\n"; #endif if (foeMinETA < minETA) { return true; } else if (foeMinETA == minETA) { if (foeMaxSpeed > maxSpeed) { return true; } else if (foeMaxSpeed == maxSpeed) { if (foeMinDist < minDist) { return true; } else if (foeMinDist == minDist) { if (foeMinNumericalID < minNumericalID) { return true; } } } } #ifdef DEBUG_SIGNALSTATE_PRIORITY //if (DEBUG_COND) std::cout << SIMTIME << " railSignal=" << getID() << " index=" << index << " closestVeh=" << Named::getIDSecure(closest) << " routeFoes " << toString(routeFoes) << "\n"; #endif if (closest != nullptr) { for (int clIndex : checkRouteConflict) { const MSEdge& firstBidi = myRouteConflictLanes[index][clIndex].front()->getEdge(); const MSEdge* first = firstBidi.getBidiEdge(); assert(first != nullptr); if (std::find(closest->getCurrentRouteEdge(), closest->getRoute().end(), first) != closest->getRoute().end()) { // vehicle wants to drive passt this conflict link //const ConstMSEdgeVector& route = closest->getRoute().getEdges(); for (const MSLane* cLane : myRouteConflictLanes[index][clIndex]) { if (cLane->getVehicleNumberWithPartials() > 0) { if (DEBUG_COND) std::cout << SIMTIME << " railSignal=" << getID() << " index=" << index << " closestVeh=" << closest->getID() << " route edge " << cLane->getEdge().getID() << " blocked\n"; // trigger rerouting MSDevice_Routing* rDev = static_cast<MSDevice_Routing*>(closest->getDevice(typeid(MSDevice_Routing))); if (rDev != nullptr) { SUMOTime now = MSNet::getInstance()->getCurrentTimeStep(); if (myLastRerouteAttempt[index].first != closest // reroute each vehicle only once if no // periodic routing is allowed, otherwise // with the specified period || (rDev->getPeriod() > 0 && myLastRerouteAttempt[index].second + rDev->getPeriod() <= now)) { MSEdgeVector routeFoes; routeFoes.push_back(const_cast<MSEdge*>(first)); SUMOAbstractRouter<MSEdge, SUMOVehicle>& router = MSRoutingEngine::getRouterTT(routeFoes); myLastRerouteAttempt[index] = std::make_pair(closest, now); try { closest->reroute(now, "railSignal:" + getID(), router, false, false, true); // silent } catch (ProcessError& error) { #ifdef DEBUG_SIGNALSTATE_PRIORITY if (DEBUG_COND) { std::cout << " rerouting failed: " << error.what() << "\n"; } #endif } } } return true; } } } } } } return false; }