SUMO - Simulation of Urban MObility
GNEJunction.cpp
Go to the documentation of this file.
1 /****************************************************************************/
7 // A class for visualizing and editing junctions in netedit (adapted from
8 // GUIJunctionWrapper)
9 /****************************************************************************/
10 // SUMO, Simulation of Urban MObility; see http://sumo.dlr.de/
11 // Copyright (C) 2001-2017 DLR (http://www.dlr.de/) and contributors
12 /****************************************************************************/
13 //
14 // This file is part of SUMO.
15 // SUMO is free software: you can redistribute it and/or modify
16 // it under the terms of the GNU General Public License as published by
17 // the Free Software Foundation, either version 3 of the License, or
18 // (at your option) any later version.
19 //
20 /****************************************************************************/
21 
22 
23 // ===========================================================================
24 // included modules
25 // ===========================================================================
26 #ifdef _MSC_VER
27 #include <windows_config.h>
28 #else
29 #include <config.h>
30 #endif
31 
32 #include <string>
33 #include <utility>
36 #include <utils/geom/Position.h>
43 #include <utils/gui/div/GLHelper.h>
48 #include <netbuild/NBOwnTLDef.h>
50 #include <netbuild/NBAlgorithms.h>
52 
53 #include "GNENet.h"
54 #include "GNEEdge.h"
55 #include "GNECrossing.h"
56 #include "GNEUndoList.h"
57 #include "GNEViewNet.h"
58 #include "GNEChange_Attribute.h"
59 #include "GNEChange_Connection.h"
60 #include "GNEChange_TLS.h"
61 #include "GNEConnection.h"
62 #include "GNEJunction.h"
63 
64 const double GNEJunction::BUBBLE_RADIUS(4);
65 
66 // ===========================================================================
67 // method definitions
68 // ===========================================================================
69 GNEJunction::GNEJunction(NBNode& nbn, GNENet* net, bool loaded) :
71  myNBNode(nbn),
72  myAmCreateEdgeSource(false),
73  myLogicStatus(loaded ? LOADED : GUESSED),
74  myAmResponsible(false),
75  myHasValidLogic(loaded),
76  myAmTLSSelected(false) {
78 }
79 
80 
82  // delete all GNECrossing
83  for (std::vector<GNECrossing*>::const_iterator it = myGNECrossings.begin(); it != myGNECrossings.end(); it++) {
84  (*it)->decRef();
85  if ((*it)->unreferenced()) {
86  // show extra information for tests
87  if (OptionsCont::getOptions().getBool("gui-testing-debug")) {
88  WRITE_WARNING("Deleting unreferenced " + toString((*it)->getTag()) + " '" + (*it)->getID() + "' in GNEJunction destructor");
89  }
90  delete *it;
91  }
92  }
93 
94  if (myAmResponsible) {
95  // show extra information for tests
96  if (OptionsCont::getOptions().getBool("gui-testing-debug")) {
97  WRITE_WARNING("Deleting NBNode of '" + getID() + "' in GNEJunction destructor");
98  }
99  delete &myNBNode;
100  }
101 }
102 
103 
104 void
106  // calculate boundary using EXTENT as size
107  const double EXTENT = 2;
108  myBoundary = Boundary(myNBNode.getPosition().x() - EXTENT, myNBNode.getPosition().y() - EXTENT,
109  myNBNode.getPosition().x() + EXTENT, myNBNode.getPosition().y() + EXTENT);
110  // if junctio own a extra shape, add it to boundary
111  if (myNBNode.getShape().size() > 0) {
113  }
115  // rebuild GNECrossings
117 }
118 
119 
120 void
122  // rebuild GNECrossings only if create crossings and walkingAreas in net is enabled
124  // build new NBNode::Crossings and walking areas
126  // create a vector to keep retrieved and created crossings
127  std::vector<GNECrossing*> retrievedCrossings;
128  // iterate over NBNode::Crossings of GNEJunction
129  for (auto c : myNBNode.getCrossingsIncludingInvalid()) {
130  // retrieve existent GNECrossing, or create it
131  GNECrossing* retrievedGNECrossing = retrieveGNECrossing(c);
132  retrievedCrossings.push_back(retrievedGNECrossing);
133  // check if previously this GNECrossings exists, and if true, remove it from myGNECrossings
134  std::vector<GNECrossing*>::iterator retrievedExists = std::find(myGNECrossings.begin(), myGNECrossings.end(), retrievedGNECrossing);
135  if (retrievedExists != myGNECrossings.end()) {
136  myGNECrossings.erase(retrievedExists);
137  // update geometry of retrieved crossing
138  retrievedGNECrossing->updateGeometry();
139  } else {
140  // include reference to created GNECrossing
141  retrievedGNECrossing->incRef();
142  }
143  }
144  // delete non retrieved GNECrossings
145  for (std::vector<GNECrossing*>::const_iterator it = myGNECrossings.begin(); it != myGNECrossings.end(); it++) {
146  (*it)->decRef();
147  if ((*it)->unreferenced()) {
148  // show extra information for tests
149  if (OptionsCont::getOptions().getBool("gui-testing-debug")) {
150  WRITE_WARNING("Deleting unreferenced " + toString((*it)->getTag()) + " '" + (*it)->getID() + "' in rebuildGNECrossings()");
151  }
152  delete *it;
153  }
154  }
155  // copy retrieved (existent and created) GNECrossigns to myGNECrossings
156  myGNECrossings = retrievedCrossings;
157  }
158 }
159 
160 
161 
162 
165  GUIGLObjectPopupMenu* ret = new GUIGLObjectPopupMenu(app, parent, *this);
166  buildPopupHeader(ret, app);
170  buildPositionCopyEntry(ret, false);
171  //if (parent.getVisualisationSettings()->editMode != GNE_MODE_CONNECT) {
172  // // XXX if joinable
173  // new FXMenuCommand(ret, "Join adjacent edges", 0, &parent, MID_GNE_JOIN_EDGES);
174  //}
175  FXMenuCommand* mcCustomShape = new FXMenuCommand(ret, "Set custom shape", 0, &parent, MID_GNE_JUNCTION_EDIT_SHAPE);
176  FXMenuCommand* mcReplace = new FXMenuCommand(ret, "Replace by geometry node", 0, &parent, MID_GNE_JUNCTION_REPLACE);
177  const int editMode = parent.getVisualisationSettings()->editMode;
178  const bool wrongMode = (editMode == GNE_MODE_CONNECT || editMode == GNE_MODE_TLS || editMode == GNE_MODE_CREATE_EDGE);
179  if (wrongMode) {
180  mcCustomShape->handle(&parent, FXSEL(SEL_COMMAND, FXWindow::ID_DISABLE), 0);
181  }
182  // checkIsRemovable requiers turnarounds to be computed. This is ugly
183  if (myNBNode.getIncomingEdges().size() == 2 && myNBNode.getOutgoingEdges().size() == 2) {
185  }
186  std::string reason = "wrong edit mode";
187  if (wrongMode || !myNBNode.checkIsRemovableReporting(reason)) {
188  mcReplace->setText(mcReplace->getText() + " (" + reason.c_str() + ")");
189  mcReplace->handle(&parent, FXSEL(SEL_COMMAND, FXWindow::ID_DISABLE), 0);
190  }
191  // let the GNEViewNet store the popup position
192  (dynamic_cast<GNEViewNet&>(parent)).markPopupPosition();
193  return ret;
194 }
195 
196 
199  return 0;
200 }
201 
202 
203 Boundary
205  Boundary b = myBoundary;
206  b.grow(20);
207  return b;
208 }
209 
210 
211 void
213  // declare variables
214  GLfloat color[4];
215  double exaggeration = gSelected.isSelected(getType(), getGlID()) ? s.selectionScale : 1;
216  exaggeration *= s.junctionSize.getExaggeration(s);
217  // push name
218  glPushName(getGlID());
219  if (s.scale * exaggeration * myMaxSize < 1.) {
220  // draw something simple so that selection still works
222  } else {
223  // node shape has been computed and is valid for drawing
224  const bool drawShape = myNBNode.getShape().size() > 0 && s.drawJunctionShape;
225  const bool drawBubble = (!drawShape || myNBNode.getShape().area() < 4) && s.drawJunctionShape; // magic threshold
226 
227  if (drawShape) {
228  setColor(s, false);
229  // recognize full transparency and simply don't draw
230  glGetFloatv(GL_CURRENT_COLOR, color);
231  if (color[3] != 0) {
232  glPushMatrix();
233  glTranslated(0, 0, getType());
234  PositionVector shape = myNBNode.getShape();
235  shape.closePolygon();
236  if (exaggeration > 1) {
237  shape.scaleRelative(exaggeration);
238  }
239  if (s.scale * exaggeration * myMaxSize < 40.) {
240  GLHelper::drawFilledPoly(shape, true);
241  } else {
243  }
244  glPopMatrix();
245  }
246  // Check if a buuble must be drawed over junction
248  setColor(s, true);
249  // recognize full transparency and simply don't draw
250  glGetFloatv(GL_CURRENT_COLOR, color);
251  if (color[3] != 0) {
252  glPushMatrix();
253  Position pos = myNBNode.getPosition();
254  glTranslated(pos.x(), pos.y(), getType() + 0.05);
255  GLHelper::drawFilledCircle(BUBBLE_RADIUS * exaggeration, 32);
256  glPopMatrix();
257  }
258  }
259  }
260  if (drawBubble) {
261  setColor(s, true);
262  // recognize full transparency and simply don't draw
263  glGetFloatv(GL_CURRENT_COLOR, color);
264  if (color[3] != 0) {
265  glPushMatrix();
266  Position pos = myNBNode.getPosition();
267  glTranslated(pos.x(), pos.y(), getType() - 0.05);
268  // resolution of drawn circle depending of the zoom (To improve smothness)
269  if (s.scale >= 10) {
270  GLHelper::drawFilledCircle(BUBBLE_RADIUS * exaggeration, 32);
271  } else if (s.scale >= 2) {
272  GLHelper::drawFilledCircle(BUBBLE_RADIUS * exaggeration, 16);
273  } else if (s.scale >= 1) {
274  GLHelper::drawFilledCircle(BUBBLE_RADIUS * exaggeration, 8);
275  } else {
276  GLHelper::drawFilledCircle(BUBBLE_RADIUS * exaggeration, 4);
277  }
278  glPopMatrix();
279  }
280  }
281 
283  glPushMatrix();
284  Position pos = myNBNode.getPosition();
285  glTranslated(pos.x(), pos.y(), getType() + 0.1);
286  glColor3d(1, 1, 1);
287  const double halfWidth = 32 / s.scale;
288  const double halfHeight = 64 / s.scale;
289  GUITexturesHelper::drawTexturedBox(GUITextureSubSys::getTexture(GNETEXTURE_TLS), -halfWidth, -halfHeight, halfWidth, halfHeight);
290  glPopMatrix();
291  }
292  // draw crossings
293  if (s.editMode != GNE_MODE_TLS) {
294  for (std::vector<GNECrossing*>::const_iterator it = myGNECrossings.begin(); it != myGNECrossings.end(); it++) {
295  (*it)->drawGL(s);
296  }
297  }
298  // (optional) draw name @todo expose this setting
300  }
301  glPopName();
302 }
303 
304 Boundary
306  return myBoundary;
307 }
308 
309 
310 NBNode*
312  return &myNBNode;
313 }
314 
315 
316 Position
318  return myNBNode.getPosition();
319 }
320 
321 
322 std::vector<GNEJunction*>
324  // use set to avoid duplicates junctions
325  std::set<GNEJunction*> junctions;
326  for (std::vector<GNEEdge*>::const_iterator i = myGNEIncomingEdges.begin(); i != myGNEIncomingEdges.end(); i++) {
327  junctions.insert((*i)->getGNEJunctionSource());
328  }
329  for (std::vector<GNEEdge*>::const_iterator i = myGNEOutgoingEdges.begin(); i != myGNEOutgoingEdges.end(); i++) {
330  junctions.insert((*i)->getGNEJunctionDestiny());
331  }
332  return std::vector<GNEJunction*>(junctions.begin(), junctions.end());
333 }
334 
335 
336 void
338  // Check if incoming edge was already inserted
339  std::vector<GNEEdge*>::iterator i = std::find(myGNEIncomingEdges.begin(), myGNEIncomingEdges.end(), edge);
340  if (i != myGNEIncomingEdges.end()) {
341  throw InvalidArgument("Incoming " + toString(SUMO_TAG_EDGE) + " with ID '" + edge->getID() + "' was already inserted into " + toString(getTag()) + " with ID " + getID() + "'");
342  } else {
343  // Add edge into containers
344  myGNEIncomingEdges.push_back(edge);
345  myGNEEdges.push_back(edge);
346  }
347 }
348 
349 
350 
351 void
353  // Check if outgoing edge was already inserted
354  std::vector<GNEEdge*>::iterator i = std::find(myGNEOutgoingEdges.begin(), myGNEOutgoingEdges.end(), edge);
355  if (i != myGNEOutgoingEdges.end()) {
356  throw InvalidArgument("Outgoing " + toString(SUMO_TAG_EDGE) + " with ID '" + edge->getID() + "' was already inserted into " + toString(getTag()) + " with ID " + getID() + "'");
357  } else {
358  // Add edge into containers
359  myGNEOutgoingEdges.push_back(edge);
360  myGNEEdges.push_back(edge);
361  }
362 }
363 
364 
365 void
367  // Check if incoming edge was already inserted
368  std::vector<GNEEdge*>::iterator i = std::find(myGNEIncomingEdges.begin(), myGNEIncomingEdges.end(), edge);
369  if (i == myGNEIncomingEdges.end()) {
370  throw InvalidArgument("Incoming " + toString(SUMO_TAG_EDGE) + " with ID '" + edge->getID() + "' doesn't found into " + toString(getTag()) + " with ID " + getID() + "'");
371  } else {
372  // remove edge from containers
373  myGNEIncomingEdges.erase(i);
374  myGNEEdges.erase(std::find(myGNEEdges.begin(), myGNEEdges.end(), edge));
375  }
376 }
377 
378 
379 void
381  // Check if outgoing edge was already inserted
382  std::vector<GNEEdge*>::iterator i = std::find(myGNEOutgoingEdges.begin(), myGNEOutgoingEdges.end(), edge);
383  if (i == myGNEOutgoingEdges.end()) {
384  throw InvalidArgument("Outgoing " + toString(SUMO_TAG_EDGE) + " with ID '" + edge->getID() + "' doesn't found into " + toString(getTag()) + " with ID " + getID() + "'");
385  } else {
386  // remove edge from containers
387  myGNEOutgoingEdges.erase(i);
388  myGNEEdges.erase(std::find(myGNEEdges.begin(), myGNEEdges.end(), edge));
389  }
390 }
391 
392 
393 const std::vector<GNEEdge*>&
395  return myGNEEdges;
396 }
397 
398 
399 const std::vector<GNEEdge*>&
401  return myGNEIncomingEdges;
402 }
403 
404 
405 const std::vector<GNEEdge*>&
407  return myGNEOutgoingEdges;
408 }
409 
410 const std::vector<GNECrossing*>&
412  return myGNECrossings;
413 }
414 
415 void
417  myAmCreateEdgeSource = true;
418 }
419 
420 
421 void
423  myAmCreateEdgeSource = false;
424 }
425 
426 
427 void
428 GNEJunction::selectTLS(bool selected) {
429  myAmTLSSelected = selected;
430 }
431 
432 
433 void
435  std::set<GNEJunction*> neighborsJunctions;
436  // obtain all neighbors junctions
437  for (std::vector<GNEEdge*>::const_iterator i = myGNEIncomingEdges.begin(); i != myGNEIncomingEdges.end(); i++) {
438  neighborsJunctions.insert((*i)->getGNEJunctionSource());
439  }
440  for (std::vector<GNEEdge*>::const_iterator i = myGNEOutgoingEdges.begin(); i != myGNEOutgoingEdges.end(); i++) {
441  neighborsJunctions.insert((*i)->getGNEJunctionDestiny());
442  }
443  // recompute all neighbors junctions
444  //for(std::set<GNEJunction*>::iterator i = neighborsJunctions.begin(); i != neighborsJunctions.end(); i++) {
445  // myNet->getNetBuilder()->computeSingleNode((*i)->getNBNode(), OptionsCont::getOptions());
446  //}
447 }
448 
449 
450 void
452  const Position orig = myNBNode.getPosition();
454  const EdgeVector& incident = getNBNode()->getEdges();
455  for (EdgeVector::const_iterator it = incident.begin(); it != incident.end(); it++) {
456  GNEEdge* edge = myNet->retrieveEdge((*it)->getID());
457  edge->updateJunctionPosition(this, orig);
458  }
459  // recompute neighbors junctions
461  // recompute junction
462  //myNet->getNetBuilder()->computeSingleNode(&myNBNode, OptionsCont::getOptions());
463  // Update shapes without include connections, because the aren't showed in Move mode
465 }
466 
467 
468 void
470  pos2D.setz(myNBNode.getPosition().z());
471  moveJunctionGeometry(pos2D);
472 }
473 
474 void
477  undoList->p_begin("position of " + toString(getTag()));
478  undoList->p_add(new GNEChange_Attribute(this, SUMO_ATTR_POSITION, toString(myNBNode.getPosition()), true, toString(oldPos)));
479  undoList->p_end();
480  } else {
481  // tried to set an invalid position, revert back to the previous one
482  moveJunctionGeometry(oldPos);
483  }
484 }
485 
486 
487 void
489  // First declare three sets with all affected GNEJunctions, GNEEdges and GNEConnections
490  std::set<GNEJunction*> affectedJunctions;
491  std::set<GNEEdge*> affectedEdges;
492  // Iterate over GNEEdges
493  for (std::vector<GNEEdge*>::const_iterator i = myGNEEdges.begin(); i != myGNEEdges.end(); i++) {
494  // Add source and destiny junctions
495  affectedJunctions.insert((*i)->getGNEJunctionSource());
496  affectedJunctions.insert((*i)->getGNEJunctionDestiny());
497  // Obtain neighbors of Junction source
498  for (std::vector<GNEEdge*>::const_iterator j = (*i)->getGNEJunctionSource()->getGNEEdges().begin(); j != (*i)->getGNEJunctionSource()->getGNEEdges().end(); j++) {
499  affectedEdges.insert(*j);
500  }
501  // Obtain neighbors of Junction destiny
502  for (std::vector<GNEEdge*>::const_iterator j = (*i)->getGNEJunctionDestiny()->getGNEEdges().begin(); j != (*i)->getGNEJunctionDestiny()->getGNEEdges().end(); j++) {
503  affectedEdges.insert(*j);
504  }
505  }
506  // Iterate over affected Junctions
507  for (std::set<GNEJunction*>::iterator i = affectedJunctions.begin(); i != affectedJunctions.end(); i++) {
508  // Update geometry of Junction
509  (*i)->updateGeometry();
510  }
511  // Iterate over affected Edges
512  for (std::set<GNEEdge*>::iterator i = affectedEdges.begin(); i != affectedEdges.end(); i++) {
513  // Update edge geometry
514  (*i)->updateGeometry();
515  }
516  // Finally update geometry of this junction
517  updateGeometry();
518  // Update view to show the new shapes
519  if (myNet->getViewNet()) {
520  myNet->getViewNet()->update();
521  }
522 }
523 
524 
525 void
527  if (!myNBNode.hasCustomShape()) {
528  myNBNode.myPoly.clear();
530  }
531 }
532 
533 
534 void
535 GNEJunction::setLogicValid(bool valid, GNEUndoList* undoList, const std::string& status) {
536  myHasValidLogic = valid;
537  if (!valid) {
538  assert(undoList != 0);
539  assert(undoList->hasCommandGroup());
541  EdgeVector incoming = myNBNode.getIncomingEdges();
542  for (EdgeVector::iterator it = incoming.begin(); it != incoming.end(); it++) {
543  NBEdge* srcNBE = *it;
544  NBEdge* turnEdge = srcNBE->getTurnDestination();
545  GNEEdge* srcEdge = myNet->retrieveEdge(srcNBE->getID());
546  // Make a copy of connections
547  std::vector<NBEdge::Connection> connections = srcNBE->getConnections();
548  // delete in reverse so that undoing will add connections in the original order
549  for (std::vector<NBEdge::Connection>::reverse_iterator con_it = connections.rbegin(); con_it != connections.rend(); con_it++) {
550  bool hasTurn = con_it->toEdge == turnEdge;
551  undoList->add(new GNEChange_Connection(srcEdge, *con_it, false, false), true);
552  // needs to come after GNEChange_Connection
553  // XXX bug: this code path will not be used on a redo!
554  if (hasTurn) {
555  myNet->addExplicitTurnaround(srcNBE->getID());
556  }
557  }
558  undoList->add(new GNEChange_Attribute(srcEdge, GNE_ATTR_MODIFICATION_STATUS, status), true);
559  }
560  undoList->add(new GNEChange_Attribute(this, GNE_ATTR_MODIFICATION_STATUS, status), true);
561  invalidateTLS(undoList);
562  } else {
563  // logic valed, then rebuild GNECrossings to adapt it to the new logic
565  }
566 }
567 
568 
569 void
571  EdgeVector incoming = myNBNode.getIncomingEdges();
572  for (EdgeVector::iterator it = incoming.begin(); it != incoming.end(); it++) {
573  NBEdge* srcNBE = *it;
574  GNEEdge* srcEdge = myNet->retrieveEdge(srcNBE->getID());
575  undoList->add(new GNEChange_Attribute(srcEdge, GNE_ATTR_MODIFICATION_STATUS, MODIFIED), true);
576  }
577 }
578 
579 
580 void
581 GNEJunction::invalidateTLS(GNEUndoList* undoList, const NBConnection& deletedConnection) {
582  assert(undoList->hasCommandGroup());
583  // NBLoadedSUMOTLDef becomes invalid, replace with NBOwnTLDef which will be dynamically recomputed
584  const std::set<NBTrafficLightDefinition*> tls = myNBNode.getControllingTLS(); // make a copy!
585  for (std::set<NBTrafficLightDefinition*>::iterator it = tls.begin(); it != tls.end(); it++) {
586  NBLoadedSUMOTLDef* tlDef = dynamic_cast<NBLoadedSUMOTLDef*>(*it);
587  if (tlDef != 0) {
588  NBTrafficLightDefinition* replacementDef = 0;
589  std::string newID = tlDef->getID(); // + "_reguessed"; // changes due to reguessing will be visible in diff
590  if (deletedConnection != NBConnection::InvalidConnection) {
591  // create replacement before deleting the original because deletion will mess up saving original nodes
592  NBLoadedSUMOTLDef* repl = new NBLoadedSUMOTLDef(tlDef, tlDef->getLogic());
593  repl->removeConnection(deletedConnection);
594  replacementDef = repl;
595  } else {
596  replacementDef = new NBOwnTLDef(newID, tlDef->getOffset(), tlDef->getType());
597  replacementDef->setProgramID(tlDef->getProgramID());
598  }
599  undoList->add(new GNEChange_TLS(this, tlDef, false), true);
600  undoList->add(new GNEChange_TLS(this, replacementDef, true, false, newID), true);
601  // the removed traffic light may have controlled more than one junction. These too have become invalid now
602  const std::vector<NBNode*> coNodes = tlDef->getNodes(); // make a copy!
603  for (std::vector<NBNode*>::const_iterator it_node = coNodes.begin(); it_node != coNodes.end(); it_node++) {
604  GNEJunction* sharing = myNet->retrieveJunction((*it_node)->getID());
605  undoList->add(new GNEChange_TLS(sharing, tlDef, false), true);
606  undoList->add(new GNEChange_TLS(sharing, replacementDef, true, false, newID), true);
607  }
608  }
609  }
610 }
611 
612 void
614  // obtain a copy of GNECrossing of junctions
615  auto copyOfGNECrossings = myGNECrossings;
616  // iterate over copy of GNECrossings
617  for (auto c : copyOfGNECrossings) {
618  // obtain the set of edges vinculated with the crossing (due it works as ID)
619  EdgeSet edgeSet(c->getNBCrossing()->edges.begin(), c->getNBCrossing()->edges.end());
620  // If this edge is part of the set of edges of crossing
621  if (edgeSet.count(edge->getNBEdge()) == 1) {
622  // delete crossing if this is their last edge
623  if ((c->getNBCrossing()->edges.size() == 1) && (c->getNBCrossing()->edges.front() == edge->getNBEdge())) {
624  myNet->deleteCrossing(c, undoList);
625  } else {
626  // remove this edge of the edge's attribute of crossing (note: This can invalidate the crossing)
627  std::vector<std::string> edges = GNEAttributeCarrier::parse<std::vector<std::string>>(c->getAttribute(SUMO_ATTR_EDGES));
628  edges.erase(std::find(edges.begin(), edges.end(), edge->getID()));
629  c->setAttribute(SUMO_ATTR_EDGES, joinToString(edges, " "), undoList);
630  }
631  }
632  }
633 }
634 
635 
636 bool
638  return myHasValidLogic;
639 }
640 
641 
643 GNEJunction::retrieveGNECrossing(NBNode::Crossing* crossing, bool createIfNoExist) {
644  for (std::vector<GNECrossing*>::iterator i = myGNECrossings.begin(); i != myGNECrossings.end(); ++i) {
645  if ((*i)->getNBCrossing() == crossing) {
646  return *i;
647  }
648  }
649  if (createIfNoExist) {
650  // create new GNECrossing
651  GNECrossing* createdGNECrossing = new GNECrossing(this, crossing);
652  // show extra information for tests
653  if (OptionsCont::getOptions().getBool("gui-testing-debug")) {
654  WRITE_WARNING("Created " + toString(createdGNECrossing->getTag()) + " '" + createdGNECrossing->getID() + "' in retrieveGNECrossing()");
655  }
656  return createdGNECrossing;
657  } else {
658  return NULL;
659  }
660 }
661 
662 
663 std::string
665  switch (key) {
666  case SUMO_ATTR_ID:
667  return getMicrosimID();
668  case SUMO_ATTR_POSITION:
669  return toString(myNBNode.getPosition());
670  case SUMO_ATTR_TYPE:
671  return toString(myNBNode.getType());
673  return myLogicStatus;
674  case SUMO_ATTR_SHAPE:
675  return toString(myNBNode.getShape());
676  case SUMO_ATTR_RADIUS:
677  return toString(myNBNode.getRadius());
678  case SUMO_ATTR_TLTYPE:
679  // @todo this causes problems if the node were to have multiple programs of different type (plausible)
680  return myNBNode.isTLControlled() ? toString((*myNBNode.getControllingTLS().begin())->getType()) : "";
681  case SUMO_ATTR_TLID:
682  return myNBNode.isTLControlled() ? toString((*myNBNode.getControllingTLS().begin())->getID()) : "";
684  return myNBNode.getKeepClear() ? "true" : "false";
685  default:
686  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
687  }
688 }
689 
690 
691 void
692 GNEJunction::setAttribute(SumoXMLAttr key, const std::string& value, GNEUndoList* undoList) {
693  if (value == getAttribute(key)) {
694  return; //avoid needless changes, later logic relies on the fact that attributes have changed
695  }
696  switch (key) {
697  case SUMO_ATTR_ID:
698  case SUMO_ATTR_POSITION:
700  case SUMO_ATTR_SHAPE:
701  case SUMO_ATTR_RADIUS:
702  case SUMO_ATTR_TLTYPE:
704  undoList->add(new GNEChange_Attribute(this, key, value), true);
705  break;
706  case SUMO_ATTR_TYPE: {
707  undoList->p_begin("change " + toString(getTag()) + " type");
709  if (getNBNode()->isTLControlled() &&
710  // if switching changing from or to traffic_light_right_on_red we need to remove the old plan
713  ) {
714  const std::set<NBTrafficLightDefinition*> tls = myNBNode.getControllingTLS();
715  for (std::set<NBTrafficLightDefinition*>::iterator it = tls.begin(); it != tls.end(); it++) {
716  undoList->add(new GNEChange_TLS(this, *it, false), true);
717  }
718  }
719  if (!getNBNode()->isTLControlled()) {
720  // create new traffic light
721  undoList->add(new GNEChange_TLS(this, 0, true), true);
722  }
723  } else if (getNBNode()->isTLControlled()) {
724  // delete old traffic light
725  // make a copy because we will modify the original
726  const std::set<NBTrafficLightDefinition*> tls = myNBNode.getControllingTLS();
727  for (std::set<NBTrafficLightDefinition*>::iterator it = tls.begin(); it != tls.end(); it++) {
728  undoList->add(new GNEChange_TLS(this, *it, false, OptionsCont::getOptions().getBool("gui-testing-debug")), true);
729  }
730  }
731  // must be the final step, otherwise we do not know which traffic lights to remove via GNEChange_TLS
732  undoList->add(new GNEChange_Attribute(this, key, value), true);
733  undoList->p_end();
734  break;
735  }
736  case SUMO_ATTR_TLID: {
737  undoList->p_begin("change " + toString(SUMO_TAG_TRAFFIC_LIGHT) + " id");
738  // junction is already controlled, remove from previous tls
739  const std::set<NBTrafficLightDefinition*> tls = myNBNode.getControllingTLS();
740  for (std::set<NBTrafficLightDefinition*>::iterator it = tls.begin(); it != tls.end(); it++) {
741  undoList->add(new GNEChange_TLS(this, *it, false), true);
742  }
744  const std::map<std::string, NBTrafficLightDefinition*> programs = tlCont.getPrograms(value);
745  if (programs.size() > 0) {
746  // add to existing tls definitions
747  for (std::map<std::string, NBTrafficLightDefinition*>::const_iterator it = programs.begin(); it != programs.end(); it++) {
748  NBTrafficLightDefinition* oldTLS = it->second;
749  if (dynamic_cast<NBOwnTLDef*>(oldTLS) != 0) {
750  undoList->add(new GNEChange_TLS(this, oldTLS, true), true);
751  } else {
752  // delete and re-create the definition because the loaded phases are now invalid
753  const std::vector<NBNode*> nodes = oldTLS->getNodes();
754  for (std::vector<NBNode*>::const_iterator it_node = nodes.begin(); it_node != nodes.end(); ++it_node) {
755  GNEJunction* oldJunction = myNet->retrieveJunction((*it_node)->getID());
756  undoList->add(new GNEChange_TLS(oldJunction, oldTLS, false), true);
757  }
758  undoList->add(new GNEChange_TLS(this, 0, true, false, value), true);
760  // re-add existing nodes
761  for (std::vector<NBNode*>::const_iterator it_node = nodes.begin(); it_node != nodes.end(); ++it_node) {
762  GNEJunction* oldJunction = myNet->retrieveJunction((*it_node)->getID());
763  undoList->add(new GNEChange_TLS(oldJunction, newTLS, true), true);
764  }
765  }
766  }
767  } else {
768  // create new traffic light
769  undoList->add(new GNEChange_TLS(this, 0, true, false, value), true);
770  }
771  undoList->p_end();
772  break;
773  }
774  default:
775  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
776  }
777 }
778 
779 
780 bool
781 GNEJunction::isValid(SumoXMLAttr key, const std::string& value) {
782  switch (key) {
783  case SUMO_ATTR_ID:
784  return isValidID(value) && (myNet->retrieveJunction(value, false) == 0);
785  case SUMO_ATTR_TYPE:
787  case SUMO_ATTR_POSITION: {
788  bool ok;
789  return GeomConvHelper::parseShapeReporting(value, "user-supplied position", 0, ok, false).size() == 1;
790  }
791  case SUMO_ATTR_SHAPE: {
792  bool ok = true;
793  PositionVector shape = GeomConvHelper::parseShapeReporting(value, "user-supplied position", 0, ok, true);
794  return ok;
795  }
796  case SUMO_ATTR_RADIUS:
797  return canParse<double>(value);
798  case SUMO_ATTR_TLTYPE:
800  case SUMO_ATTR_TLID:
801  return myNBNode.isTLControlled() && (value != "");
803  return canParse<bool>(value);
804  default:
805  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
806  }
807 }
808 
809 
810 void
812  myAmResponsible = newVal;
813 }
814 
815 // ===========================================================================
816 // private
817 // ===========================================================================
818 
819 void
820 GNEJunction::setAttribute(SumoXMLAttr key, const std::string& value) {
821  switch (key) {
822  case SUMO_ATTR_ID: {
823  myNet->renameJunction(this, value);
824  break;
825  }
826  case SUMO_ATTR_TYPE: {
828  break;
829  }
830  case SUMO_ATTR_POSITION: {
831  // set new position in NBNode
832  bool ok;
833  moveJunctionGeometry(GeomConvHelper::parseShapeReporting(value, "netedit-given", 0, ok, false)[0]);
834  // recompute neighbors junctions
836  // update geometry
837  updateGeometry();
838  // Refresh element to avoid grabbing problems
839  myNet->refreshElement(this);
840  break;
841  }
843  if (myLogicStatus == GUESSED && value != GUESSED) {
844  // clear guessed connections. previous connections will be restored
846  // Clear GNEConnections of incoming edges
847  for (std::vector<GNEEdge*>::iterator i = myGNEIncomingEdges.begin(); i != myGNEIncomingEdges.end(); i++) {
848  (*i)->clearGNEConnections();
849  }
850  }
851  myLogicStatus = value;
852  break;
853  case SUMO_ATTR_SHAPE: {
854  bool ok;
855  const PositionVector shape = GeomConvHelper::parseShapeReporting(value, "netedit-given", 0, ok, true);
856  myNBNode.setCustomShape(shape);
857  // Refresh element to avoid grabbing problems
858  myNet->refreshElement(this);
859  break;
860  }
861  case SUMO_ATTR_RADIUS: {
862  myNBNode.setRadius(parse<double>(value));
863  break;
864  }
865  case SUMO_ATTR_TLTYPE: {
866  const std::set<NBTrafficLightDefinition*> tls = myNBNode.getControllingTLS();
867  for (std::set<NBTrafficLightDefinition*>::iterator it = tls.begin(); it != tls.end(); it++) {
868  (*it)->setType(SUMOXMLDefinitions::TrafficLightTypes.get(value));
869  }
870  break;
871  }
872  case SUMO_ATTR_KEEP_CLEAR: {
873  myNBNode.setKeepClear(value == "true");
874  break;
875  }
876  default:
877  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
878  }
879 }
880 
881 
882 double
884  switch (s.junctionColorer.getActive()) {
885  case 0:
886  if (bubble) {
887  return 1;
888  } else {
889  return 0;
890  }
891  case 1:
892  return gSelected.isSelected(getType(), getGlID()) ? 1 : 0;
893  case 2:
894  switch (myNBNode.getType()) {
896  return 0;
898  return 1;
899  case NODETYPE_PRIORITY:
900  return 2;
902  return 3;
904  return 4;
906  return 5;
907  case NODETYPE_DISTRICT:
908  return 6;
909  case NODETYPE_NOJUNCTION:
910  return 7;
911  case NODETYPE_DEAD_END:
913  return 8;
914  case NODETYPE_UNKNOWN:
915  case NODETYPE_INTERNAL:
916  assert(false);
917  return 8;
919  return 9;
920  case NODETYPE_ZIPPER:
921  return 10;
923  return 11;
925  return 12;
926  }
927  default:
928  assert(false);
929  return 0;
930  }
931 }
932 
933 
934 void
935 GNEJunction::setColor(const GUIVisualizationSettings& s, bool bubble) const {
937  // override with special colors (unless the color scheme is based on selection)
940  }
941  if (myAmCreateEdgeSource) {
942  glColor3d(0, 1, 0);
943  }
944 }
945 
946 void
949  tlCont.insert(tlDef, forceInsert); // may return false for tlDef which controls multiple junctions
950  tlDef->addNode(&myNBNode);
951 }
952 
953 
954 void
957  if (tlDef->getNodes().size() == 1) {
958  tlCont.extract(tlDef);
959  }
961 }
962 
963 /****************************************************************************/
GUIVisualizationSizeSettings junctionSize
static void drawTexturedBox(int which, double size)
Draws a named texture as a box with the given size.
bool myAmResponsible
whether we are responsible for deleting myNBNode
Definition: GNEJunction.h:265
GUIVisualizationTextSettings junctionName
void removeConnection(const NBConnection &conn, bool reconstruct=true)
removes the given connection from the traffic light if recontruct=true, reconstructs the logic and in...
bool myHasValidLogic
whether this junctions logic is valid
Definition: GNEJunction.h:268
void setResponsible(bool newVal)
set responsibility for deleting internal strctures
void moveJunctionGeometry2D(Position pos2D)
reposition the node as above but keep the old z value
double z() const
Returns the z-position.
Definition: Position.h:73
void drawName(const Position &pos, const double scale, const GUIVisualizationTextSettings &settings, const double angle=0) const
draw name of item
double myMaxSize
The maximum size (in either x-, or y-dimension) for determining whether to draw or not...
Definition: GNEJunction.h:252
const EdgeVector & getIncomingEdges() const
Returns this node&#39;s incoming edges (The edges which yield in this node)
Definition: NBNode.h:243
std::string myLogicStatus
modification status of the junction logic (all connections across this junction)
Definition: GNEJunction.h:262
Boundary getCenteringBoundary() const
Returns the boundary to which the view shall be centered in order to show the object.
bool getKeepClear() const
Returns the keepClear flag.
Definition: NBNode.h:270
void setAttribute(SumoXMLAttr key, const std::string &value, GNEUndoList *undoList)
void addIncomingGNEEdge(GNEEdge *edge)
add incoming GNEEdge
static StringBijection< SumoXMLNodeType > NodeTypes
node types
GNEEdge * retrieveEdge(const std::string &id, bool failHard=true)
get edge by id
Definition: GNENet.cpp:899
double scale
information about a lane&#39;s width (temporary, used for a single view)
double getColorValue(const GUIVisualizationSettings &s, bool bubble) const
determines color value
turn junction into geometry node
Definition: GUIAppEnum.h:648
Whether vehicles must keep the junction clear.
GNENet * myNet
the net to inform about updates
virtual void addNode(NBNode *node)
Adds a node to the traffic light logic.
void invalidateShape()
void removeIncomingGNEEdge(GNEEdge *edge)
remove incoming GNEEdge
void buildNameCopyPopupEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds entries which allow to copy the name / typed name into the clipboard.
begin/end of the description of a junction
PositionVector myPoly
the (outer) shape of the junction
Definition: NBNode.h:747
void refreshElement(GUIGlObject *o)
refreshes boundary information for o and update
Definition: GNENet.cpp:990
void markAsCreateEdgeSource()
marks as first junction in createEdge-mode
bool hasString(const std::string &str) const
void removeEdgeFromCrossings(GNEEdge *edge, GNEUndoList *undoList)
removes the given edge from all pedestrian crossings
A loaded (complete) traffic light logic.
bool myAmCreateEdgeSource
whether this junction is the first junction for a newly creatededge
Definition: GNEJunction.h:259
static GUIGlID getTexture(GUITexture which)
returns a texture previously defined in the enum GUITexture
static const NBConnection InvalidConnection
Definition: NBConnection.h:127
A container for traffic light definitions and built programs.
std::vector< GNEEdge * > myGNEIncomingEdges
vector with the incomings GNEEdges vinculated with this junction
Definition: GNEJunction.h:246
void reinit(const Position &position, SumoXMLNodeType type, bool updateEdgeGeometries=false)
Resets initial values.
Definition: NBNode.cpp:264
bool isTLControlled() const
Returns whether this node is controlled by any tls.
Definition: NBNode.h:291
bool isValid(SumoXMLAttr key, const std::string &value)
TrafficLightType getType() const
get the algorithm type (static etc..)
void setLogicValid(bool valid, GNEUndoList *undoList=0, const std::string &status=GUESSED)
double x() const
Returns the x-position.
Definition: Position.h:63
friend class GNEChange_TLS
Declare friend class.
Definition: GNEJunction.h:57
Stores the information about how to visualize structures.
bool getBool(const std::string &name) const
Returns the boolean-value of the named option (only for Option_Bool)
const std::string & getProgramID() const
Returns the ProgramID.
The representation of a single edge during network building.
Definition: NBEdge.h:71
mode for editing tls
Definition: GNEViewNet.h:63
NBNode * getNBNode() const
Return net build node.
The base class for traffic light logic definitions.
void buildCenterPopupEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds an entry which allows to center to the object.
link,node: the traffic light id responsible for this link
T MAX2(T a, T b)
Definition: StdDefs.h:74
Position getPositionInView() const
Return current position.
bool isSelected(GUIGlObjectType type, GUIGlID id)
Returns the information whether the object with the given type and id is selected.
A NBNetBuilder extended by visualisation and editing capabilities.
Definition: GNENet.h:92
static void drawFilledPoly(const PositionVector &v, bool close)
Draws a filled polygon described by the list of points.
Definition: GLHelper.cpp:72
int editMode
the current NETEDIT mode (temporary)
void p_begin(const std::string &description)
Begin undo command sub-group. This begins a new group of commands that are treated as a single comman...
Definition: GNEUndoList.cpp:85
bool hasCustomShape() const
return whether the shape was set by the user
Definition: NBNode.h:491
void addExplicitTurnaround(std::string id)
add edge id to the list of explicit turnarounds
Definition: GNENet.cpp:1540
SumoXMLAttr
Numbers representing SUMO-XML - attributes.
void selectTLS(bool selected)
notify the junction of being selected in tls-mode. (used to control drawing)
bool myAmTLSSelected
whether this junction is selected in tls-mode
Definition: GNEJunction.h:271
const std::vector< GNEEdge * > & getGNEEdges() const
Returns all GNEEdges vinculated with this Junction.
void removeTrafficLight(NBTrafficLightDefinition *tlDef)
Removes the given traffic light from this node.
Definition: NBNode.cpp:322
void setCustomShape(const PositionVector &shape)
set the junction shape
Definition: NBNode.cpp:1732
void extract(NBTrafficLightDefinition *definition)
Extracts a traffic light definition from myDefinitions but keeps it in myExtracted for eventual * del...
static void drawFilledCircle(double width, int steps=8)
Draws a filled circle around (0,0)
Definition: GLHelper.cpp:339
void updateShapesAndGeometries()
update shapes of all elements associated to the junction
void removeTrafficLight(NBTrafficLightDefinition *tlDef)
removes a traffic light
void buildPositionCopyEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds an entry which allows to copy the cursor position if geo projection is used, also builds an entry for copying the geo-position.
GUIGlID getGlID() const
Returns the numerical id of the object.
void drawGL(const GUIVisualizationSettings &s) const
Draws the object.
A class that stores a 2D geometrical boundary.
Definition: Boundary.h:48
#define WRITE_WARNING(msg)
Definition: MsgHandler.h:200
static OptionsCont & getOptions()
Retrieves the options.
Definition: OptionsCont.cpp:65
void setColor(const GUIVisualizationSettings &s, bool bubble) const
sets junction color depending on circumstances
whether a feature has been loaded,guessed,modified or approved
SUMOTime getOffset()
Returns the offset.
void updateGeometry()
update pre-computed geometry information
Definition: GNECrossing.cpp:71
void renameJunction(GNEJunction *junction, const std::string &newID)
updates the map and reserves new id
Definition: GNENet.cpp:1531
static void drawFilledPolyTesselated(const PositionVector &v, bool close)
Draws a filled polygon described by the list of points.
Definition: GLHelper.cpp:91
virtual const std::string & getMicrosimID() const
Returns the id of the object as known to microsim.
void removeOutgoingGNEEdge(GNEEdge *edge)
remove outgoing GNEEdge
void p_add(GNEChange_Attribute *cmd)
special method, avoid empty changes, always execute
const EdgeVector & getOutgoingEdges() const
Returns this node&#39;s outgoing edges (The edges which start at this node)
Definition: NBNode.h:248
const std::string & getID() const
Returns the id.
Definition: Named.h:66
edit junction shape
Definition: GUIAppEnum.h:646
static bool isValidID(const std::string &value)
true if value is a valid sumo ID
static const std::string MODIFIED
feature has been manually modified (implies approval)
GUIGlObjectType getType() const
Returns the type of the object as coded in GUIGlObjectType.
void setRadius(double radius)
set the turning radius
Definition: NBNode.h:481
std::vector< GNEJunction * > getJunctionNeighbours() const
return GNEJunction neighbours
void invalidateIncomingConnections()
invalidate incoming connections
Definition: NBNode.cpp:1339
double area() const
Returns the area (0 for non-closed)
const Position & getPosition() const
Definition: NBNode.h:235
The turning radius at an intersection in m.
double getWidth() const
Returns the width of the boudary (x-axis)
Definition: Boundary.cpp:162
double getExaggeration(const GUIVisualizationSettings &s, double factor=20) const
return the drawing size including exaggeration and constantSize values
std::set< NBEdge * > EdgeSet
container for unique edges
Definition: NBCont.h:51
const std::set< NBTrafficLightDefinition * > & getControllingTLS() const
Returns the traffic lights that were assigned to this node (The set of tls that control this node) ...
Definition: NBNode.h:296
the edges of a route
std::string toString(const T &t, std::streamsize accuracy=gPrecision)
Definition: ToString.h:56
static void setColor(const RGBColor &c)
Sets the gl-color to this value.
Definition: GLHelper.cpp:438
This object is responsible for drawing a shape and for supplying a a popup menu. Messages are routete...
Definition: GNECrossing.h:52
void moveJunctionGeometry(Position pos)
reposition the node at pos and informs the edges
static StringBijection< TrafficLightType > TrafficLightTypes
traffic light types
double getHeight() const
Returns the height of the boundary (y-axis)
Definition: Boundary.cpp:168
const std::vector< GNECrossing * > & getGNECrossings() const
Returns GNECrossings.
void p_end()
End undo command sub-group. If the sub-group is still empty, it will be deleted; otherwise, the sub-group will be added as a new command into parent group. A matching begin() must have been called previously.
Definition: GNEUndoList.cpp:92
A point in 2D or 3D with translation and scaling methods.
Definition: Position.h:46
GNEJunction * retrieveJunction(const std::string &id, bool failHard=true)
get junction by id
Definition: GNENet.cpp:886
A list of positions.
bool isLogicValid()
whether this junction has a valid logic
void buildCrossingsAndWalkingAreas()
build crossings, and walkingareas. Also removes invalid loaded crossings if wished ...
Definition: NBNode.cpp:2025
friend class GNEChange_Attribute
declare friend class
double y() const
Returns the y-position.
Definition: Position.h:68
SumoXMLNodeType getType() const
Returns the type of this node.
Definition: NBNode.h:260
const std::map< std::string, NBTrafficLightDefinition * > & getPrograms(const std::string &id) const
Returns all programs for the given tl-id.
void commitGeometryMoving(const Position &oldPos, GNEUndoList *undoList)
registers completed movement with the undoList
const T getColor(const double value) const
const EdgeVector & getEdges() const
Returns all edges which participate in this node (Edges that start or end at this node) ...
Definition: NBNode.h:253
NBTrafficLightLogic * getLogic()
Returns the internal logic.
node: the type of traffic light
edge: the shape in xml-definition
Boundary & grow(double by)
extends the boundary by the given amount
Definition: Boundary.cpp:302
GUIColorer junctionColorer
The junction colorer.
void deleteCrossing(GNECrossing *crossing, GNEUndoList *undoList)
remove crossing
Definition: GNENet.cpp:498
void addOutgoingGNEEdge(GNEEdge *edge)
add outgoing GNEEdge
std::vector< GNEEdge * > myGNEEdges
vector with the GNEEdges vinculated with this junction
Definition: GNEJunction.h:243
void unMarkAsCreateEdgeSource()
removes mark as first junction in createEdge-mode
void setProgramID(const std::string &programID)
Sets the programID.
const std::string getID() const
function to support debugging
void incRef(const std::string &debugMsg="")
Increarse reference.
bool checkIsRemovableReporting(std::string &reason) const
check if node is removable and return reason if not
Definition: NBNode.cpp:1640
const PositionVector & getShape() const
retrieve the junction shape
Definition: NBNode.cpp:1726
NBNode & myNBNode
A reference to the represented junction.
Definition: GNEJunction.h:240
GUIGLObjectPopupMenu * getPopUpMenu(GUIMainWindow &app, GUISUMOAbstractView &parent)
Returns an own popup-menu.
const std::vector< NBNode * > & getNodes() const
Returns the list of controlled nodes.
void setKeepClear(bool keepClear)
set the keepClear flag
Definition: NBNode.h:486
void invalidateTLS(GNEUndoList *undoList, const NBConnection &deletedConnection=NBConnection::InvalidConnection)
static void computeTurnDirectionsForNode(NBNode *node, bool warn)
Computes turnaround destinations for all incoming edges of the given nodes (if any) ...
begin/end of the description of an edge
A road/street connecting two junctions (netedit-version)
Definition: GNEEdge.h:58
static const double BUBBLE_RADIUS
Definition: GNEJunction.h:62
double selectionScale
the current selection scaling in NETEDIT (temporary)
bool hasCommandGroup() const
Check if undoList has command group.
~GNEJunction()
Destructor.
Definition: GNEJunction.cpp:81
bool haveNetworkCrossings()
notify about style of loaded network (Without Crossings)
Definition: NBNetBuilder.h:198
void updateGeometry()
Update the boundary of the junction.
Boundary getBoundary() const
Returns the boundary of the junction.
Boundary myBoundary
The represented junction&#39;s boundary.
Definition: GNEJunction.h:255
std::vector< NBEdge * > EdgeVector
container for (sorted) edges
Definition: NBCont.h:41
std::vector< GNECrossing * > myGNECrossings
the built crossing objects
Definition: GNEJunction.h:274
void recomputeNeighborsJunctions()
recompute neighbors junctions
void scaleRelative(double factor)
enlarges/shrinks the polygon by a factor based at the centroid
void rebuildGNECrossings()
rebuilds crossing objects for this junction
void updateJunctionPosition(GNEJunction *junction, const Position &origPos)
update edge geometry after junction move
Definition: GNEEdge.cpp:293
The popup menu of a globject.
std::vector< GNEEdge * > myGNEOutgoingEdges
vector with the outgoings GNEEdges vinculated with this junction
Definition: GNEJunction.h:249
double getRadius() const
Returns the turning radius of this node.
Definition: NBNode.h:265
void buildSelectionPopupEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds an entry which allows to (de)select the object.
Represents a single node (junction) during network building.
Definition: NBNode.h:75
T get(const std::string &str) const
GUIParameterTableWindow * getParameterWindow(GUIMainWindow &app, GUISUMOAbstractView &parent)
Returns an own parameter window.
A definition of a pedestrian crossing.
Definition: NBNode.h:135
GNEJunction(NBNode &nbn, GNENet *net, bool loaded=false)
Constructor.
Definition: GNEJunction.cpp:69
SumoXMLTag getTag() const
get XML Tag assigned to this object
bool insert(NBTrafficLightDefinition *logic, bool forceInsert=false)
Adds a logic definition to the dictionary.
GUIVisualizationSettings * getVisualisationSettings() const
get visualitation settings
static const std::string GUESSED
feature has been reguessed (may still be unchanged be we can&#39;t tell (yet)
bool drawJunctionShape
whether the shape of the junction should be drawn
static const RGBColor selectionColor
Definition: GNENet.h:103
const std::vector< GNEEdge * > & getGNEIncomingEdges() const
Returns incoming GNEEdges.
mode for connecting lanes
Definition: GNEViewNet.h:61
mode for creating new edges
Definition: GNEViewNet.h:51
static void drawBoxLine(const Position &beg, double rot, double visLength, double width, double offset=0)
Draws a thick line.
Definition: GLHelper.cpp:126
std::string getAttribute(SumoXMLAttr key) const
This functions has to be implemented in allGNEAttributeCarrier.
GNECrossing * retrieveGNECrossing(NBNode::Crossing *crossing, bool createIfNoExist=true)
get GNECrossing if exist, and if not create it if create is enabled
NBEdge * getNBEdge()
returns the internal NBEdge
Definition: GNEEdge.cpp:306
void add(double x, double y, double z=0)
Makes the boundary include the given coordinate.
Definition: Boundary.cpp:86
A traffic light logics which must be computed (only nodes/edges are given)
Definition: NBOwnTLDef.h:54
bool showJunctionAsBubbles() const
return true if junction must be showed as bubbles
Definition: GNEViewNet.cpp:340
void closePolygon()
ensures that the last position equals the first
Boundary getBoxBoundary() const
Returns a boundary enclosing this list of lines.
GUISelectedStorage gSelected
A global holder of selected objects.
const std::vector< Connection > & getConnections() const
Returns the connections.
Definition: NBEdge.h:835
const std::vector< Crossing * > & getCrossingsIncludingInvalid() const
Definition: NBNode.h:620
A window containing a gl-object&#39;s parameter.
NBEdge * getTurnDestination(bool possibleDestination=false) const
Definition: NBEdge.cpp:2737
NBTrafficLightLogicCont & getTLLogicCont()
returns the tllcont of the underlying netbuilder
Definition: GNENet.cpp:1525
GNEViewNet * getViewNet() const
get view net
Definition: GNENet.cpp:1519
static bool isTrafficLight(SumoXMLNodeType type)
return whether the given type is a traffic light
Definition: NBNode.cpp:2742
static PositionVector parseShapeReporting(const std::string &shpdef, const std::string &objecttype, const char *objectid, bool &ok, bool allowEmpty, bool report=true)
Builds a PositionVector from a string representation, reporting occured errors.
std::string joinToString(const std::vector< T > &v, const T_BETWEEN &between, std::streamsize accuracy=gPrecision)
Definition: ToString.h:237
void requireRecompute()
inform the net about the need for recomputation
Definition: GNENet.cpp:1232
void addTrafficLight(NBTrafficLightDefinition *tlDef, bool forceInsert)
adds a traffic light
const std::vector< GNEEdge * > & getGNEOutgoingEdges() const
Returns incoming GNEEdges.
void buildPopupHeader(GUIGLObjectPopupMenu *ret, GUIMainWindow &app, bool addSeparator=true)
Builds the header.
void markAsModified(GNEUndoList *undoList)
prevent re-guessing connections at this junction
void setz(double z)
set position z
Definition: Position.h:88
a junction
NBNetBuilder * getNetBuilder() const
get net builder
Definition: GNENet.cpp:1274