SUMO - Simulation of Urban MObility
GNELane.cpp
Go to the documentation of this file.
1 /****************************************************************************/
7 // A class for visualizing Lane geometry (adapted from GNELaneWrapper)
8 /****************************************************************************/
9 // SUMO, Simulation of Urban MObility; see http://sumo.dlr.de/
10 // Copyright (C) 2001-2017 DLR (http://www.dlr.de/) and contributors
11 /****************************************************************************/
12 //
13 // This file is part of SUMO.
14 // SUMO is free software: you can redistribute it and/or modify
15 // it under the terms of the GNU General Public License as published by
16 // the Free Software Foundation, either version 3 of the License, or
17 // (at your option) any later version.
18 //
19 /****************************************************************************/
20 
21 
22 // ===========================================================================
23 // included modules
24 // ===========================================================================
25 #ifdef _MSC_VER
26 #include <windows_config.h>
27 #else
28 #include <config.h>
29 #endif
30 
31 #include <string>
32 #include <iostream>
33 #include <utility>
39 #include <utils/common/ToString.h>
40 #include <utils/geom/GeomHelper.h>
47 #include <utils/gui/div/GLHelper.h>
51 
52 #include "GNELane.h"
53 #include "GNEEdge.h"
54 #include "GNEJunction.h"
55 #include "GNETLSEditorFrame.h"
56 #include "GNEInternalLane.h"
57 #include "GNEUndoList.h"
58 #include "GNENet.h"
59 #include "GNEChange_Attribute.h"
60 #include "GNEViewNet.h"
61 #include "GNEViewParent.h"
62 #include "GNEConnection.h"
63 
64 // ===========================================================================
65 // FOX callback mapping
66 // ===========================================================================
67 
68 // Object implementation
69 FXIMPLEMENT(GNELane, FXDelegator, 0, 0)
70 
71 // ===========================================================================
72 // method definitions
73 // ===========================================================================
74 
75 GNELane::GNELane(GNEEdge& edge, const int index) :
76  GNENetElement(edge.getNet(), edge.getNBEdge()->getLaneID(index), GLO_LANE, SUMO_TAG_LANE, ICON_LANE),
77  myParentEdge(edge),
78  myIndex(index),
79  mySpecialColor(0),
80  myTLSEditor(0) {
81 }
82 
84  GNENetElement(NULL, "dummyConstructorGNELane", GLO_LANE, SUMO_TAG_LANE, ICON_LOCATEEDGE),
85  myParentEdge(*static_cast<GNEEdge*>(0)),
86  myIndex(-1),
87  mySpecialColor(0),
88  myTLSEditor(0) {
89 }
90 
91 
93 }
94 
95 
96 void
98  const std::vector<NBEdge::Connection>& cons = myParentEdge.getNBEdge()->getConnectionsFromLane(myIndex);
99  int noLinks = (int)cons.size();
100  if (noLinks == 0) {
101  return;
102  }
103  // draw all links
104  glPushMatrix();
105  glTranslated(0, 0, GLO_LANE + 0.1);
106  double w = myParentEdge.getNBEdge()->getLaneWidth(myIndex) / (double) noLinks;
107  double x1 = myParentEdge.getNBEdge()->getLaneWidth(myIndex) / 2;
108  const bool lefthand = OptionsCont::getOptions().getBool("lefthand");
109  for (int i = noLinks; --i >= 0;) {
110  double x2 = x1 - (double)(w / 2.);
112  cons[lefthand ? noLinks - 1 - i : i]);
114  x1 -= w;
115  }
116  glPopMatrix();
117 }
118 
119 
120 void
122  const std::vector<NBEdge::Connection>& cons = myParentEdge.getNBEdge()->getConnectionsFromLane(myIndex);
123  int noLinks = (int)cons.size();
124  if (noLinks == 0) {
125  return;
126  }
127  // draw all links
128  glPushMatrix();
129  glTranslated(0, 0, GLO_LANE + 0.1);
130  double w = myParentEdge.getNBEdge()->getLaneWidth(myIndex) / (double) noLinks;
131  double x1 = myParentEdge.getNBEdge()->getLaneWidth(myIndex) / 2;
132  const bool lefthand = OptionsCont::getOptions().getBool("lefthand");
133  for (int i = noLinks; --i >= 0;) {
134  double x2 = x1 - (double)(w / 2.);
135  int linkNo = cons[lefthand ? noLinks - 1 - i : i].tlLinkNo;
137  x1 -= w;
138  }
139  glPopMatrix();
140 }
141 
142 
143 void
145 }
146 
147 
148 void
150  const Position& end = getShape().back();
151  const Position& f = getShape()[-2];
152  double rot = (double) atan2((end.x() - f.x()), (f.y() - end.y())) * (double) 180.0 / (double) PI;
153  glPushMatrix();
154  glPushName(0);
155  glTranslated(0, 0, GLO_JUNCTION + .1); // must draw on top of junction shape
156  glColor3d(1, 1, 1);
157  glTranslated(end.x(), end.y(), 0);
158  glRotated(rot, 0, 0, 1);
159 
160  // draw all links
161  const std::vector<NBEdge::Connection>& edgeCons = myParentEdge.getNBEdge()->myConnections;
162  NBNode* dest = myParentEdge.getNBEdge()->myTo;
163  for (std::vector<NBEdge::Connection>::const_iterator i = edgeCons.begin(); i != edgeCons.end(); ++i) {
164  if ((*i).fromLane == myIndex) {
165  LinkDirection dir = dest->getDirection(myParentEdge.getNBEdge(), i->toEdge, OptionsCont::getOptions().getBool("lefthand"));
166  switch (dir) {
167  case LINKDIR_STRAIGHT:
168  GLHelper::drawBoxLine(Position(0, 4), 0, 2, .05);
169  GLHelper::drawTriangleAtEnd(Position(0, 4), Position(0, 1), (double) 1, (double) .25);
170  break;
171  case LINKDIR_LEFT:
172  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
173  GLHelper::drawBoxLine(Position(0, 2.5), 90, 1, .05);
174  GLHelper::drawTriangleAtEnd(Position(0, 2.5), Position(1.5, 2.5), (double) 1, (double) .25);
175  break;
176  case LINKDIR_RIGHT:
177  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
178  GLHelper::drawBoxLine(Position(0, 2.5), -90, 1, .05);
179  GLHelper::drawTriangleAtEnd(Position(0, 2.5), Position(-1.5, 2.5), (double) 1, (double) .25);
180  break;
181  case LINKDIR_TURN:
182  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
183  GLHelper::drawBoxLine(Position(0, 2.5), 90, .5, .05);
184  GLHelper::drawBoxLine(Position(0.5, 2.5), 180, 1, .05);
185  GLHelper::drawTriangleAtEnd(Position(0.5, 2.5), Position(0.5, 4), (double) 1, (double) .25);
186  break;
188  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
189  GLHelper::drawBoxLine(Position(0, 2.5), -90, 1, .05);
190  GLHelper::drawBoxLine(Position(-0.5, 2.5), -180, 1, .05);
191  GLHelper::drawTriangleAtEnd(Position(-0.5, 2.5), Position(-0.5, 4), (double) 1, (double) .25);
192  break;
193  case LINKDIR_PARTLEFT:
194  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
195  GLHelper::drawBoxLine(Position(0, 2.5), 45, .7, .05);
196  GLHelper::drawTriangleAtEnd(Position(0, 2.5), Position(1.2, 1.3), (double) 1, (double) .25);
197  break;
198  case LINKDIR_PARTRIGHT:
199  GLHelper::drawBoxLine(Position(0, 4), 0, 1.5, .05);
200  GLHelper::drawBoxLine(Position(0, 2.5), -45, .7, .05);
201  GLHelper::drawTriangleAtEnd(Position(0, 2.5), Position(-1.2, 1.3), (double) 1, (double) .25);
202  break;
203  case LINKDIR_NODIR:
204  GLHelper::drawBoxLine(Position(1, 5.8), 245, 2, .05);
205  GLHelper::drawBoxLine(Position(-1, 5.8), 115, 2, .05);
206  glTranslated(0, 5, 0);
207  GLHelper::drawOutlineCircle(0.9, 0.8, 32);
208  glTranslated(0, -5, 0);
209  break;
210  }
211  }
212  }
213  glPopName();
214  glPopMatrix();
215 }
216 
217 
218 void
220  glPushMatrix();
221  glPushName(0);
222  glTranslated(0, 0, GLO_JUNCTION + .1); // must draw on top of junction shape
223  std::vector<NBEdge::Connection> connections = myParentEdge.getNBEdge()->getConnectionsFromLane(myIndex);
224  NBNode* node = myParentEdge.getNBEdge()->getToNode();
225  const Position& startPos = getShape()[-1];
226  for (std::vector<NBEdge::Connection>::iterator it = connections.begin(); it != connections.end(); it++) {
227  const LinkState state = node->getLinkState(
228  myParentEdge.getNBEdge(), it->toEdge, it->fromLane, it->toLane, it->mayDefinitelyPass, it->tlID);
229  switch (state) {
231  glColor3d(1, 1, 0);
232  break;
234  glColor3d(0, 1, 1);
235  break;
236  case LINKSTATE_MAJOR:
237  glColor3d(1, 1, 1);
238  break;
239  case LINKSTATE_MINOR:
240  glColor3d(.4, .4, .4);
241  break;
242  case LINKSTATE_STOP:
243  glColor3d(.7, .4, .4);
244  break;
245  case LINKSTATE_EQUAL:
246  glColor3d(.7, .7, .7);
247  break;
249  glColor3d(.7, .7, 1);
250  case LINKSTATE_ZIPPER:
251  glColor3d(.75, .5, 0.25);
252  break;
253  default:
254  throw ProcessError("Unexpected LinkState '" + toString(state) + "'");
255  }
256  const Position& endPos = it->toEdge->getLaneShape(it->toLane)[0];
257  glBegin(GL_LINES);
258  glVertex2d(startPos.x(), startPos.y());
259  glVertex2d(endPos.x(), endPos.y());
260  glEnd();
261  GLHelper::drawTriangleAtEnd(startPos, endPos, (double) 1.5, (double) .2);
262  }
263  glPopName();
264  glPopMatrix();
265 }
266 
267 
268 void
270  // Push draw matrix 1
271  glPushMatrix();
272  // Push name
273  glPushName(getGlID());
274  // Traslate to fromt
275  glTranslated(0, 0, getType());
276  // Check if edge parent or this lane is selected
277  const bool selectedEdge = gSelected.isSelected(myParentEdge.getType(), myParentEdge.getGlID());
278  const bool selected = gSelected.isSelected(getType(), getGlID());
279  // Set color
280  if (mySpecialColor != 0) {
281  // If special color is enabled, set it
283  } else if (selected && s.laneColorer.getActive() != 1) {
284  // override with special colors (unless the color scheme is based on selection)
286  } else if (selectedEdge && s.laneColorer.getActive() != 1) {
287  // override with special colors (unless the color scheme is based on selection)
289  } else {
290  // Get normal lane color
291  const GUIColorer& c = s.laneColorer;
292  if (!setFunctionalColor(c.getActive()) && !setMultiColor(c)) {
294  }
295  }
296 
297  // start drawing lane checking whether it is not too small
298  const double selectionScale = selected || selectedEdge ? s.selectionScale : 1;
299  double exaggeration = selectionScale * s.laneWidthExaggeration; // * s.laneScaler.getScheme().getColor(getScaleValue(s.laneScaler.getActive()));
300  // XXX apply usefull scale values
301  //exaggeration *= s.laneScaler.getScheme().getColor(getScaleValue(s.laneScaler.getActive()));
302 
303  // recognize full transparency and simply don't draw
304  GLfloat color[4];
305  glGetFloatv(GL_CURRENT_COLOR, color);
306  if (color[3] == 0 || s.scale * exaggeration < s.laneMinSize) {
307  // Pop draw matrix 1
308  glPopMatrix();
309  } else if (s.scale * exaggeration < 1.) {
310  // draw as lines, depending of myShapeColors
311  if (myShapeColors.size() > 0) {
313  } else {
315  }
316  // Pop draw matrix 1
317  glPopMatrix();
318  } else {
319  if (drawAsRailway(s)) {
320  // draw as railway
321  const double halfRailWidth = 0.725 * exaggeration;
322  // Draw box depending of myShapeColors
323  if (myShapeColors.size() > 0) {
325  } else {
327  }
328  // Save current color
329  RGBColor current = GLHelper::getColor();
330  // Set white color
331  glColor3d(1, 1, 1);
332  // Traslate matrix 1
333  glTranslated(0, 0, .1);
334  // Draw Box
336  // Set current color back
337  GLHelper::setColor(current);
338  // Draw crossties
339  drawCrossties(0.3 * exaggeration, 1 * exaggeration, 1 * exaggeration);
340  } else {
341  // Draw as a normal lane, and reduce width to make sure that a selected edge can still be seen
342  const double halfWidth = exaggeration * (myParentEdge.getNBEdge()->getLaneWidth(myIndex) / 2 - (selectedEdge ? .3 : 0));
343  if (myShapeColors.size() > 0) {
345  } else {
347  }
348  }
349  // Pop draw matrix 1
350  glPopMatrix();
351  // if exaggeration is 1, draw drawMarkings
352  if (exaggeration == 1) {
353  drawMarkings(selectedEdge, exaggeration);
354  }
355  // draw ROWs only if target junction has a valid logic)
357  drawArrows();
358  }
359  // Draw direction indicators if the correspondient option is enabled
360  if (s.showLaneDirection) {
362  }
363  if (s.drawLinkJunctionIndex.show) {
364  drawLinkNo(s);
365  }
366  if (s.drawLinkTLIndex.show) {
367  drawTLSLinkNo(s);
368  }
369  // If there are texture of restricted lanes to draw, and draw lane icons is enabled in options
370  if ((OptionsCont::getOptions().getBool("disable-laneIcons") == false) && myLaneRestrictedTexturePositions.size() > 0) {
371  // Declare default width of icon (3)
372  double iconWidth = 1;
373  // Obtain width of icon, if width of lane is different
375  iconWidth = myParentEdge.getNBEdge()->getLaneStruct(myIndex).width / 3;
376  }
377  // Draw list of icons
378  for (int i = 0; i < (int)myLaneRestrictedTexturePositions.size(); i++) {
379  // Push draw matrix 2
380  glPushMatrix();
381  // Set white color
382  glColor3d(1, 1, 1);
383  // Traslate matrix 2
384  glTranslated(myLaneRestrictedTexturePositions.at(i).x(), myLaneRestrictedTexturePositions.at(i).y(), getType() + 0.1);
385  // Rotate matrix 2
386  glRotated(myLaneRestrictedTextureRotations.at(i), 0, 0, -1);
387  glRotated(90, 0, 0, 1);
388  // draw texture box depending of type of restriction
391  } else if (isRestricted(SVC_BICYCLE)) {
393  } else if (isRestricted(SVC_BUS)) {
395  }
396  // Pop draw matrix 2
397  glPopMatrix();
398  }
399  }
400  }
401  // Pop Name
402  glPopName();
403 }
404 
405 
406 void
407 GNELane::drawMarkings(const bool& selectedEdge, double scale) const {
408  glPushMatrix();
409  glTranslated(0, 0, GLO_EDGE);
410 
411  const double halfWidth = myParentEdge.getNBEdge()->getLaneWidth(myIndex) * 0.5;
412  // optionally draw inverse markings
414  double mw = (halfWidth + SUMO_const_laneOffset + .01) * scale;
415  int e = (int) getShape().size() - 1;
416  for (int i = 0; i < e; ++i) {
417  glPushMatrix();
418  glTranslated(getShape()[i].x(), getShape()[i].y(), 0.1);
419  glRotated(myShapeRotations[i], 0, 0, 1);
420  for (double t = 0; t < myShapeLengths[i]; t += 6) {
421  const double length = MIN2((double)3, myShapeLengths[i] - t);
422  glBegin(GL_QUADS);
423  glVertex2d(-mw, -t);
424  glVertex2d(-mw, -t - length);
425  glVertex2d(halfWidth * 0.5 * scale, -t - length);
426  glVertex2d(halfWidth * 0.5 * scale, -t);
427  glEnd();
428  }
429  glPopMatrix();
430  }
431  }
432 
433  // draw white boundings (and white markings) depending on selection
434  if (selectedEdge) {
435  glTranslated(0, 0, 0.2); // draw selection on top of regular markings
437  } else {
438  glColor3d(1, 1, 1);
439  }
440 
442  getShape(),
444  getShapeLengths(),
445  (halfWidth + SUMO_const_laneOffset) * scale);
446  glPopMatrix();
447 
448 }
449 
450 
453  GUIGLObjectPopupMenu* ret = new GUIGLObjectPopupMenu(app, parent, *this);
454  buildPopupHeader(ret, app);
456  new FXMenuCommand(ret, ("Copy " + toString(SUMO_TAG_EDGE) + " name to clipboard").c_str(), 0, ret, MID_COPY_EDGE_NAME);
459  buildPositionCopyEntry(ret, false);
460  const int editMode = parent.getVisualisationSettings()->editMode;
461  myTLSEditor = 0;
462  if (editMode != GNE_MODE_CONNECT && editMode != GNE_MODE_TLS && editMode != GNE_MODE_CREATE_EDGE) {
463  // Get icons
464  FXIcon* pedestrianIcon = GUIIconSubSys::getIcon(ICON_LANEPEDESTRIAN);
465  FXIcon* bikeIcon = GUIIconSubSys::getIcon(ICON_LANEBIKE);
466  FXIcon* busIcon = GUIIconSubSys::getIcon(ICON_LANEBUS);
467  // Create basic commands
468  new FXMenuCommand(ret, ("Split " + toString(SUMO_TAG_EDGE) + " here").c_str(), 0, &parent, MID_GNE_SPLIT_EDGE);
469  new FXMenuCommand(ret, ("Split " + toString(SUMO_TAG_EDGE) + "s in both direction here").c_str(), 0, &parent, MID_GNE_SPLIT_EDGE_BIDI);
470  new FXMenuCommand(ret, ("Reverse " + toString(SUMO_TAG_EDGE)).c_str(), 0, &parent, MID_GNE_REVERSE_EDGE);
471  new FXMenuCommand(ret, "Add reverse direction", 0, &parent, MID_GNE_ADD_REVERSE_EDGE);
472  new FXMenuCommand(ret, "Set geometry endpoint here", 0, &parent, MID_GNE_SET_EDGE_ENDPOINT);
473  new FXMenuCommand(ret, "Restore geometry endpoint", 0, &parent, MID_GNE_RESET_EDGE_ENDPOINT);
475  new FXMenuCommand(ret, ("Straighten selected " + toString(SUMO_TAG_EDGE) + "s").c_str(), 0, &parent, MID_GNE_STRAIGHTEN);
476  } else {
477  new FXMenuCommand(ret, ("Straighten " + toString(SUMO_TAG_EDGE)).c_str(), 0, &parent, MID_GNE_STRAIGHTEN);
478  }
480  new FXMenuCommand(ret, ("Duplicate selected" + toString(SUMO_TAG_LANE) + "s").c_str(), 0, &parent, MID_GNE_DUPLICATE_LANE);
481  // Create panel for lane operations
482  FXMenuPane* addSpecialLanes = new FXMenuPane(ret);
483  ret->insertMenuPaneChild(addSpecialLanes);
484  FXMenuPane* removeSpecialLanes = new FXMenuPane(ret);
485  ret->insertMenuPaneChild(removeSpecialLanes);
486  FXMenuPane* transformSlanes = new FXMenuPane(ret);
487  ret->insertMenuPaneChild(transformSlanes);
488  // Create menu comands for all add special lanes
489  new FXMenuCommand(addSpecialLanes, "Sidewalks", pedestrianIcon, &parent, MID_GNE_ADD_LANE_SIDEWALK);
490  new FXMenuCommand(addSpecialLanes, "Bikelanes", bikeIcon, &parent, MID_GNE_ADD_LANE_BIKE);
491  new FXMenuCommand(addSpecialLanes, "Buslanes", busIcon, &parent, MID_GNE_ADD_LANE_BUS);
492  // Create menu comands for all remove special lanes and disable it
493  new FXMenuCommand(removeSpecialLanes, "Sidewalks", pedestrianIcon, &parent, MID_GNE_REMOVE_LANE_SIDEWALK);
494  new FXMenuCommand(removeSpecialLanes, "Bikelanes", bikeIcon, &parent, MID_GNE_REMOVE_LANE_BIKE);
495  new FXMenuCommand(removeSpecialLanes, "Buslanes", busIcon, &parent, MID_GNE_REMOVE_LANE_BUS);
496  // Create menu comands for all trasform special lanes and disable it
497  new FXMenuCommand(transformSlanes, "Sidewalks", pedestrianIcon, &parent, MID_GNE_TRANSFORM_LANE_SIDEWALK);
498  new FXMenuCommand(transformSlanes, "Bikelanes", bikeIcon, &parent, MID_GNE_TRANSFORM_LANE_BIKE);
499  new FXMenuCommand(transformSlanes, "Buslanes", busIcon, &parent, MID_GNE_TRANSFORM_LANE_BUS);
500  new FXMenuCommand(transformSlanes, "revert transformations", 0, &parent, MID_GNE_REVERT_TRANSFORMATION);
501  // add menuCascade for lane operations
502  new FXMenuCascade(ret, ("add special" + toString(SUMO_TAG_LANE) + "s").c_str(), 0, addSpecialLanes);
503  new FXMenuCascade(ret, ("remove special" + toString(SUMO_TAG_LANE) + "s").c_str(), 0, removeSpecialLanes);
504  new FXMenuCascade(ret, ("transform to special" + toString(SUMO_TAG_LANE) + "s").c_str(), 0, transformSlanes);
505  } else {
506  new FXMenuCommand(ret, ("Duplicate" + toString(SUMO_TAG_LANE)).c_str(), 0, &parent, MID_GNE_DUPLICATE_LANE);
507  // Declare flags
508  bool edgeHasSidewalk = myParentEdge.hasRestrictedLane(SVC_PEDESTRIAN);
509  bool edgeHasBikelane = myParentEdge.hasRestrictedLane(SVC_BICYCLE);
510  bool edgeHasBuslane = myParentEdge.hasRestrictedLane(SVC_BUS);
511  // Create panel for lane operations and insert it in ret
512  FXMenuPane* addSpecialLanes = new FXMenuPane(ret);
513  ret->insertMenuPaneChild(addSpecialLanes);
514  FXMenuPane* removeSpecialLanes = new FXMenuPane(ret);
515  ret->insertMenuPaneChild(removeSpecialLanes);
516  FXMenuPane* transformSlanes = new FXMenuPane(ret);
517  ret->insertMenuPaneChild(transformSlanes);
518  // Create menu comands for all add special lanes
519  FXMenuCommand* addSidewalk = new FXMenuCommand(addSpecialLanes, "Sidewalk", pedestrianIcon, &parent, MID_GNE_ADD_LANE_SIDEWALK);
520  FXMenuCommand* addBikelane = new FXMenuCommand(addSpecialLanes, "Bikelane", bikeIcon, &parent, MID_GNE_ADD_LANE_BIKE);
521  FXMenuCommand* addBuslane = new FXMenuCommand(addSpecialLanes, "Buslane", busIcon, &parent, MID_GNE_ADD_LANE_BUS);
522  // Create menu comands for all remove special lanes and disable it
523  FXMenuCommand* removeSidewalk = new FXMenuCommand(removeSpecialLanes, "Sidewalk", pedestrianIcon, &parent, MID_GNE_REMOVE_LANE_SIDEWALK);
524  removeSidewalk->disable();
525  FXMenuCommand* removeBikelane = new FXMenuCommand(removeSpecialLanes, "Bikelane", bikeIcon, &parent, MID_GNE_REMOVE_LANE_BIKE);
526  removeBikelane->disable();
527  FXMenuCommand* removeBuslane = new FXMenuCommand(removeSpecialLanes, "Buslane", busIcon, &parent, MID_GNE_REMOVE_LANE_BUS);
528  removeBuslane->disable();
529  // Create menu comands for all trasform special lanes and disable it
530  FXMenuCommand* transformLaneToSidewalk = new FXMenuCommand(transformSlanes, "Sidewalk", pedestrianIcon, &parent, MID_GNE_TRANSFORM_LANE_SIDEWALK);
531  FXMenuCommand* transformLaneToBikelane = new FXMenuCommand(transformSlanes, "Bikelane", bikeIcon, &parent, MID_GNE_TRANSFORM_LANE_BIKE);
532  FXMenuCommand* transformLaneToBuslane = new FXMenuCommand(transformSlanes, "Buslane", busIcon, &parent, MID_GNE_TRANSFORM_LANE_BUS);
533  FXMenuCommand* revertTransformation = new FXMenuCommand(transformSlanes, "revert transformation", 0, &parent, MID_GNE_REVERT_TRANSFORMATION);
534  // add menuCascade for lane operations
535  FXMenuCascade* cascadeAddSpecialLane = new FXMenuCascade(ret, ("add special" + toString(SUMO_TAG_LANE)).c_str(), 0, addSpecialLanes);
536  FXMenuCascade* cascadeRemoveSpecialLane = new FXMenuCascade(ret, ("remove special" + toString(SUMO_TAG_LANE)).c_str(), 0, removeSpecialLanes);
537  new FXMenuCascade(ret, ("transform to special" + toString(SUMO_TAG_LANE)).c_str(), 0, transformSlanes);
538  // Enable and disable options depending of current transform of the lane
539  if (edgeHasSidewalk) {
540  transformLaneToSidewalk->disable();
541  addSidewalk->disable();
542  removeSidewalk->enable();
543  }
544  if (edgeHasBikelane) {
545  transformLaneToBikelane->disable();
546  addBikelane->disable();
547  removeBikelane->enable();
548  }
549  if (edgeHasBuslane) {
550  transformLaneToBuslane->disable();
551  addBuslane->disable();
552  removeBuslane->enable();
553  }
554  // Check if cascade menus must be disabled
555  if (edgeHasSidewalk && edgeHasBikelane && edgeHasBuslane) {
556  cascadeAddSpecialLane->disable();
557  }
558  if (!edgeHasSidewalk && !edgeHasBikelane && !edgeHasBuslane) {
559  cascadeRemoveSpecialLane->disable();
560  }
561  // Enable or disable revert transformation
563  revertTransformation->enable();
564  } else {
565  revertTransformation->disable();
566  }
567  }
568  } else if (editMode == GNE_MODE_TLS) {
569  myTLSEditor = static_cast<GNEViewNet&>(parent).getViewParent()->getTLSEditorFrame();
571  new FXMenuCommand(ret, "Select state for all links from this edge:", 0, 0, 0);
572  const std::vector<std::string> names = GNEInternalLane::LinkStateNames.getStrings();
573  for (std::vector<std::string>::const_iterator it = names.begin(); it != names.end(); it++) {
574  FXuint state = GNEInternalLane::LinkStateNames.get(*it);
575  FXMenuRadio* mc = new FXMenuRadio(ret, (*it).c_str(), this, FXDataTarget::ID_OPTION + state);
576  mc->setSelBackColor(MFXUtils::getFXColor(GNEInternalLane::colorForLinksState(state)));
578  }
579  }
580  } else {
581  FXMenuCommand* mc = new FXMenuCommand(ret, "Additional options available in 'Inspect Mode'", 0, 0, 0);
582  mc->handle(&parent, FXSEL(SEL_COMMAND, FXWindow::ID_DISABLE), 0);
583  }
584  // buildShowParamsPopupEntry(ret, false);
585  new FXMenuSeparator(ret);
586  const double pos = getShape().nearest_offset_to_point2D(parent.getPositionInformation());
587  const double height = getShape().positionAtOffset2D(getShape().nearest_offset_to_point2D(parent.getPositionInformation())).z();
588  new FXMenuCommand(ret, ("Shape pos: " + toString(pos)).c_str(), 0, 0, 0);
589  new FXMenuCommand(ret, ("Length pos: " + toString(getPositionRelativeToShapeLength(pos))).c_str(), 0, 0, 0);
590  new FXMenuCommand(ret, ("Height: " + toString(height)).c_str(), 0, 0, 0);
591  // new FXMenuSeparator(ret);
592  // buildPositionCopyEntry(ret, false);
593 
594  // let the GNEViewNet store the popup position
595  (dynamic_cast<GNEViewNet&>(parent)).markPopupPosition();
596  return ret;
597 }
598 
599 
603  new GUIParameterTableWindow(app, *this, 2);
604  // add items
605  ret->mkItem("length [m]", false, myParentEdge.getNBEdge()->getLength());
606  // close building
607  ret->closeBuilding();
608  return ret;
609 }
610 
611 
612 Boundary
615  b.grow(10);
616  return b;
617 }
618 
619 
620 const PositionVector&
623 }
624 
625 
626 const std::vector<double>&
628  return myShapeRotations;
629 }
630 
631 
632 const std::vector<double>&
634  return myShapeLengths;
635 }
636 
637 
638 Boundary
641 }
642 
643 
644 void
646  // Clear containers
647  myShapeRotations.clear();
648  myShapeLengths.clear();
651  //double length = myParentEdge.getLength(); // @todo see ticket #448
652  // may be different from length
653 
654  // Obtain lane and shape rotations
655  int segments = (int) getShape().size() - 1;
656  if (segments >= 0) {
657  myShapeRotations.reserve(segments);
658  myShapeLengths.reserve(segments);
659  for (int i = 0; i < segments; ++i) {
660  const Position& f = getShape()[i];
661  const Position& s = getShape()[i + 1];
662  myShapeLengths.push_back(f.distanceTo2D(s));
663  myShapeRotations.push_back((double) atan2((s.x() - f.x()), (f.y() - s.y())) * (double) 180.0 / (double) PI);
664  }
665  }
666  // Update geometry of additionals vinculated with this lane
667  for (AdditionalVector::iterator i = myAdditionals.begin(); i != myAdditionals.end(); i++) {
668  (*i)->updateGeometry();
669  }
670  // In Move mode, connections aren't updated
672  // Update incoming connections of this lane
673  std::vector<GNEConnection*> incomingConnections = getGNEIncomingConnections();
674  for (std::vector<GNEConnection*>::iterator i = incomingConnections.begin(); i != incomingConnections.end(); i++) {
675  (*i)->updateGeometry();
676  }
677  // Update outgoings connections of this lane
678  std::vector<GNEConnection*> outGoingConnections = getGNEOutcomingConnections();
679  for (std::vector<GNEConnection*>::iterator i = outGoingConnections.begin(); i != outGoingConnections.end(); i++) {
680  (*i)->updateGeometry();
681  }
682  }
683  // If lane has enought length for show textures of restricted lanes
684  if ((getLaneShapeLength() > 4)) {
685  // if lane is restricted
687  // get values for position and rotation of icons
688  for (int i = 2; i < getLaneShapeLength() - 1; i += 15) {
689  myLaneRestrictedTexturePositions.push_back(getShape().positionAtOffset(i));
690  myLaneRestrictedTextureRotations.push_back(getShape().rotationDegreeAtOffset(i));
691  }
692  }
693  }
694 }
695 
696 int
698  return myIndex;
699 }
700 
701 void
702 GNELane::setIndex(int index) {
703  myIndex = index;
705 }
706 
707 
708 double
711 }
712 
713 
714 double
717 }
718 
719 
720 double
722  return getShape().length();
723 }
724 
725 
726 double
728  return (position * getLaneShapeLength()) / getLaneParametricLength();
729 }
730 
731 
732 double
734  return (position * getLaneParametricLength()) / getLaneShapeLength();
735 }
736 
737 
738 void
740  // First check that additional wasn't already inserted
741  for (AdditionalVector::iterator i = myAdditionals.begin(); i != myAdditionals.end(); i++) {
742  if (*i == additional) {
743  throw ProcessError(toString(getTag()) + " with ID='" + additional->getID() + "' was already inserted in lane with ID='" + getID() + "'");
744  }
745  }
746  myAdditionals.push_back(additional);
747 }
748 
749 
750 void
752  // Declare iterator
753  AdditionalVector::iterator i = myAdditionals.begin();
754  // Find additional
755  while ((*i != additional) && (i != myAdditionals.end())) {
756  i++;
757  }
758  // If additional was found, remove it
759  if (i == myAdditionals.end()) {
760  throw ProcessError(toString(getTag()) + " with ID='" + additional->getID() + "' doesn't exist in lane with ID='" + getID() + "'");
761  } else {
762  myAdditionals.erase(i);
763  }
764 }
765 
766 
767 const std::vector<GNEAdditional*>&
769  return myAdditionals;
770 }
771 
772 
773 bool
775  return myParentEdge.getNBEdge()->getPermissions(myIndex) == vclass;
776 }
777 
778 
779 std::string
781  const NBEdge* edge = myParentEdge.getNBEdge();
782  switch (key) {
783  case SUMO_ATTR_ID:
784  return getMicrosimID();
785  case SUMO_ATTR_SPEED:
786  return toString(edge->getLaneSpeed(myIndex));
787  case SUMO_ATTR_ALLOW:
788  // return all allowed classes (may differ from the written attributes)
790  case SUMO_ATTR_DISALLOW:
791  // return all disallowed classes (may differ from the written attributes)
792  return getVehicleClassNames(~(edge->getPermissions(myIndex)));
793  case SUMO_ATTR_WIDTH:
795  return "default";
796  } else {
797  return toString(edge->getLaneStruct(myIndex).width);
798  }
799  case SUMO_ATTR_ENDOFFSET:
800  return toString(edge->getLaneStruct(myIndex).endOffset);
802  return toString(edge->getLaneStruct(myIndex).accelRamp);
803  case SUMO_ATTR_INDEX:
804  return toString(myIndex);
805  default:
806  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
807  }
808 }
809 
810 
811 void
812 GNELane::setAttribute(SumoXMLAttr key, const std::string& value, GNEUndoList* undoList) {
813  switch (key) {
814  case SUMO_ATTR_ID:
815  throw InvalidArgument("Modifying attribute '" + toString(key) + "' of " + toString(getTag()) + " isn't allowed");
816  case SUMO_ATTR_SPEED:
817  case SUMO_ATTR_ALLOW:
818  case SUMO_ATTR_DISALLOW:
819  case SUMO_ATTR_WIDTH:
820  case SUMO_ATTR_ENDOFFSET:
822  case SUMO_ATTR_INDEX:
823  // no special handling
824  undoList->p_add(new GNEChange_Attribute(this, key, value));
825  break;
826  default:
827  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
828  }
829 }
830 
831 
832 bool
833 GNELane::isValid(SumoXMLAttr key, const std::string& value) {
834  switch (key) {
835  case SUMO_ATTR_ID:
836  return false;
837  case SUMO_ATTR_SPEED:
838  return canParse<double>(value);
839  case SUMO_ATTR_ALLOW:
840  case SUMO_ATTR_DISALLOW:
841  return canParseVehicleClasses(value);
842  case SUMO_ATTR_WIDTH:
843  if (value == "default") {
844  return true;
845  } else {
846  return canParse<double>(value) && (isPositive<double>(value) || parse<double>(value) == NBEdge::UNSPECIFIED_WIDTH);
847  }
848  case SUMO_ATTR_ENDOFFSET:
849  return canParse<double>(value);
851  return canParse<bool>(value);
852  case SUMO_ATTR_INDEX:
853  return value == toString(myIndex);
854  default:
855  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
856  }
857 }
858 
859 
860 void
862  mySpecialColor = color;
863 }
864 
865 // ===========================================================================
866 // private
867 // ===========================================================================
868 
869 void
870 GNELane::setAttribute(SumoXMLAttr key, const std::string& value) {
871  NBEdge* edge = myParentEdge.getNBEdge();
872  switch (key) {
873  case SUMO_ATTR_ID:
874  throw InvalidArgument("Modifying attribute '" + toString(key) + "' of " + toString(getTag()) + " isn't allowed");
875  case SUMO_ATTR_SPEED:
876  edge->setSpeed(myIndex, parse<double>(value));
877  break;
878  case SUMO_ATTR_ALLOW:
880  updateGeometry();
881  myNet->getViewNet()->update();
882  break;
883  case SUMO_ATTR_DISALLOW:
884  edge->setPermissions(~parseVehicleClasses(value), myIndex); // negation yields allowed
885  updateGeometry();
886  myNet->getViewNet()->update();
887  break;
888  case SUMO_ATTR_WIDTH:
889  if (value == "default") {
891  } else {
892  edge->setLaneWidth(myIndex, parse<double>(value));
893  }
894  updateGeometry();
895  myNet->getViewNet()->update();
896  break;
897  case SUMO_ATTR_ENDOFFSET:
898  edge->setEndOffset(myIndex, parse<double>(value));
899  break;
901  edge->setAcceleration(myIndex, parse<bool>(value));
902  break;
903  default:
904  throw InvalidArgument(toString(getTag()) + " doesn't have an attribute of type '" + toString(key) + "'");
905  }
906 }
907 
908 
909 bool
910 GNELane::setFunctionalColor(int activeScheme) const {
911  switch (activeScheme) {
912  case 6: {
913  double hue = GeomHelper::naviDegree(getShape().beginEndAngle()); // [0-360]
915  return true;
916  }
917  default:
918  return false;
919  }
920 }
921 
922 
923 bool
925  const int activeScheme = c.getActive();
926  myShapeColors.clear();
927  switch (activeScheme) {
928  case 9: // color by height at segment start
929  for (PositionVector::const_iterator ii = getShape().begin(); ii != getShape().end() - 1; ++ii) {
930  myShapeColors.push_back(c.getScheme().getColor(ii->z()));
931  }
932  return true;
933  case 11: // color by inclination at segment start
934  for (int ii = 1; ii < (int)getShape().size(); ++ii) {
935  const double inc = (getShape()[ii].z() - getShape()[ii - 1].z()) / MAX2(POSITION_EPS, getShape()[ii].distanceTo2D(getShape()[ii - 1]));
936  myShapeColors.push_back(c.getScheme().getColor(inc));
937  }
938  return true;
939  default:
940  return false;
941  }
942 }
943 
944 
945 double
946 GNELane::getColorValue(int activeScheme) const {
948  if (getVehicleClassNames(~myPermissions) == "all") {
949  myPermissions = 0;
950  }
951  switch (activeScheme) {
952  case 0:
953  switch (myPermissions) {
954  case SVC_PEDESTRIAN:
955  return 1;
956  case SVC_BICYCLE:
957  return 2;
958  case 0:
959  return 3;
960  case SVC_SHIP:
961  return 4;
962  default:
963  break;
964  }
965  if ((myPermissions & SVC_PASSENGER) != 0 || isRailway(myPermissions)) {
966  return 0;
967  } else {
968  return 5;
969  }
970  case 1:
971  return gSelected.isSelected(getType(), getGlID()) ||
972  gSelected.isSelected(GLO_EDGE, dynamic_cast<GNEEdge*>(&myParentEdge)->getGlID());
973  case 2:
974  return (double)myPermissions;
975  case 3:
977  case 4:
978  return myParentEdge.getNBEdge()->getNumLanes();
979  case 5: {
981  }
982  // case 6: by angle (functional)
983  case 7: {
984  return myParentEdge.getNBEdge()->getPriority();
985  }
986  case 8: {
987  // color by z of first shape point
988  return getShape()[0].z();
989  }
990  // case 9: by segment height
991  case 10: {
992  // color by incline
993  return (getShape()[-1].z() - getShape()[0].z()) / myParentEdge.getNBEdge()->getLength();
994  }
995  }
996  return 0;
997 }
998 
999 
1000 bool
1003 }
1004 
1005 
1006 bool
1008  return isWaterway(myParentEdge.getNBEdge()->getPermissions(myIndex)) && s.showRails; // reusing the showRails setting
1009 }
1010 
1011 
1012 void
1013 GNELane::drawCrossties(double length, double spacing, double halfWidth) const {
1014  glPushMatrix();
1015  // draw on top of of the white area between the rails
1016  glTranslated(0, 0, 0.1);
1017  int e = (int) getShape().size() - 1;
1018  for (int i = 0; i < e; ++i) {
1019  glPushMatrix();
1020  glTranslated(getShape()[i].x(), getShape()[i].y(), 0.0);
1021  glRotated(myShapeRotations[i], 0, 0, 1);
1022  for (double t = 0; t < myShapeLengths[i]; t += spacing) {
1023  glBegin(GL_QUADS);
1024  glVertex2d(-halfWidth, -t);
1025  glVertex2d(-halfWidth, -t - length);
1026  glVertex2d(halfWidth, -t - length);
1027  glVertex2d(halfWidth, -t);
1028  glEnd();
1029  }
1030  glPopMatrix();
1031  }
1032  glPopMatrix();
1033 }
1034 
1035 
1036 void
1038  const double width = myParentEdge.getNBEdge()->getLaneWidth(myIndex);
1039  glColor3d(0.3, 0.3, 0.3);
1040  glPushMatrix();
1041  glTranslated(0, 0, GLO_JUNCTION + 0.1);
1042  int e = (int) getShape().size() - 1;
1043  for (int i = 0; i < e; ++i) {
1044  glPushMatrix();
1045  glTranslated(getShape()[i].x(), getShape()[i].y(), 0.1);
1046  glRotated(myShapeRotations[i], 0, 0, 1);
1047  for (double t = 0; t < myShapeLengths[i]; t += width) {
1048  const double length = MIN2(width * 0.5, myShapeLengths[i] - t);
1049  glBegin(GL_TRIANGLES);
1050  glVertex2d(0, -t - length);
1051  glVertex2d(-width * 0.25, -t);
1052  glVertex2d(+width * 0.25, -t);
1053  glEnd();
1054  }
1055  glPopMatrix();
1056  }
1057  glPopMatrix();
1058 }
1059 
1060 
1061 
1062 const std::string&
1064  return myParentEdge.getMicrosimID();
1065 }
1066 
1067 
1068 long
1069 GNELane::onDefault(FXObject* obj, FXSelector sel, void* data) {
1070  if (myTLSEditor != 0) {
1071  myTLSEditor->handleMultiChange(this, obj, sel, data);
1072  }
1073  return 1;
1074 }
1075 
1076 
1077 GNEEdge&
1079  return myParentEdge;
1080 }
1081 
1082 
1083 std::vector<GNEConnection*>
1085  // Declare a vector to save incoming connections
1086  std::vector<GNEConnection*> incomingConnections;
1087  // Obtain incoming edges if junction source was already created
1088  GNEJunction* junctionSource = myParentEdge.getGNEJunctionSource();
1089  if (junctionSource) {
1090  // Iterate over incoming GNEEdges of junction
1091  for (std::vector<GNEEdge*>::const_iterator i = junctionSource->getGNEIncomingEdges().begin(); i != junctionSource->getGNEIncomingEdges().end(); i++) {
1092  // Iterate over connection of incoming edges
1093  for (std::vector<GNEConnection*>::const_iterator j = (*i)->getGNEConnections().begin(); j != (*i)->getGNEConnections().end(); j++) {
1094  if ((*j)->getNBEdgeConnection().fromLane == getIndex()) {
1095  incomingConnections.push_back(*j);
1096  }
1097  }
1098  }
1099  }
1100  return incomingConnections;
1101 }
1102 
1103 
1104 std::vector<GNEConnection*>
1106  // Obtain GNEConnection of edge parent
1107  const std::vector<GNEConnection*>& edgeConnections = myParentEdge.getGNEConnections();
1108  std::vector<GNEConnection*> outcomingConnections;
1109  // Obtain outgoing connections
1110  for (std::vector<GNEConnection*>::const_iterator i = edgeConnections.begin(); i != edgeConnections.end(); i++) {
1111  if ((*i)->getNBEdgeConnection().fromLane == getIndex()) {
1112  outcomingConnections.push_back(*i);
1113  }
1114  }
1115  return outcomingConnections;
1116 }
1117 
1118 
1119 void
1121  // update incoming connections of lane
1122  std::vector<GNEConnection*> incomingConnections = getGNEIncomingConnections();
1123  for (std::vector<GNEConnection*>::iterator i = incomingConnections.begin(); i != incomingConnections.end(); i++) {
1124  (*i)->updateID();
1125  }
1126  // update outocming connections of lane
1127  std::vector<GNEConnection*> outcomingConnections = getGNEOutcomingConnections();
1128  for (std::vector<GNEConnection*>::iterator i = outcomingConnections.begin(); i != outcomingConnections.end(); i++) {
1129  (*i)->updateID();
1130  }
1131 }
1132 
1133 /****************************************************************************/
bool drawAsWaterway(const GUIVisualizationSettings &s) const
whether to draw this lane as a waterways
Definition: GNELane.cpp:1007
static void drawTexturedBox(int which, double size)
Draws a named texture as a box with the given size.
double getPositionRelativeToParametricLength(double position) const
Definition: GNELane.cpp:727
double getLaneShapeLength() const
returns the length of the lane&#39;s shape
Definition: GNELane.cpp:721
EditMode getCurrentEditMode() const
get the current edit mode
The link is a partial left direction.
std::string getVehicleClassNames(SVCPermissions permissions, bool expand)
Returns the ids of the given classes, divided using a &#39; &#39;.
double z() const
Returns the z-position.
Definition: Position.h:73
std::vector< double > myShapeLengths
The lengths of the shape parts.
Definition: GNELane.h:229
bool controlsEdge(GNEEdge &edge) const
whether the given edge is controlled by the currently edited tlDef
const std::string & getParentName() const
Returns the name of the parent object (if any)
Definition: GNELane.cpp:1063
add busLane
Definition: GUIAppEnum.h:652
double scale
information about a lane&#39;s width (temporary, used for a single view)
double laneWidthExaggeration
The lane exaggeration (upscale thickness)
GNEJunction * getGNEJunctionSource() const
returns the source-junction
Definition: GNEEdge.cpp:159
double distanceTo2D(const Position &p2) const
returns the euclidean distance in the x-y-plane
Definition: Position.h:250
PositionVector shape
The lane&#39;s shape.
Definition: NBEdge.h:129
GNENet * myNet
the net to inform about updates
is a pedestrian
mode for moving things
Definition: GNEViewNet.h:53
GNETLSEditorFrame * myTLSEditor
the tls-editor for setting multiple links in TLS-mode
Definition: GNELane.h:248
static void drawBoxLines(const PositionVector &geom, const std::vector< double > &rots, const std::vector< double > &lengths, double width, int cornerDetail=0, double offset=0)
Draws thick lines.
Definition: GLHelper.cpp:172
AdditionalVector myAdditionals
list with the additionals vinculated with this lane
Definition: GNELane.h:239
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 single lane
GUIGLObjectPopupMenu * getPopUpMenu(GUIMainWindow &app, GUISUMOAbstractView &parent)
Returns an own popup-menu.
Definition: GNELane.cpp:452
SUMOVehicleClass
Definition of vehicle classes to differ between different lane usage and authority types...
NBNode * myTo
Definition: NBEdge.h:1353
void setEndOffset(int lane, double offset)
set lane specific end-offset (negative lane implies set for all lanes)
Definition: NBEdge.cpp:2846
const RGBColor * mySpecialColor
optional special color
Definition: GNELane.h:242
static const RGBColor selectedLaneColor
color of selected lane
Definition: GNENet.h:100
static void drawTextAtEnd(const std::string &text, const PositionVector &shape, double x, double size, RGBColor color)
draw text and the end of shape
Definition: GLHelper.cpp:514
static RGBColor fromHSV(double h, double s, double v)
Converts the given hsv-triplet to rgb.
Definition: RGBColor.cpp:290
std::vector< Connection > getConnectionsFromLane(int lane) const
Returns connections from a given lane.
Definition: NBEdge.cpp:1010
static GUIGlID getTexture(GUITexture which)
returns a texture previously defined in the enum GUITexture
double getLoadedLength() const
Returns the length was set explicitly or the computed length if it wasn&#39;t set.
Definition: NBEdge.h:490
double nearest_offset_to_point2D(const Position &p, bool perpendicular=true) const
return the nearest offest to point 2D
int getConnectionIndex(const NBEdge *from, const NBEdge::Connection &con) const
return the index of the given connection
Definition: NBNode.cpp:2603
void setSpeed(int lane, double speed)
set lane specific speed (negative lane implies set for all lanes)
Definition: NBEdge.cpp:2862
GUIColorer laneColorer
The lane colorer.
double x() const
Returns the x-position.
Definition: Position.h:63
Stores the information about how to visualize structures.
This is an uncontrolled, minor link, has to stop.
vehicle is a bicycle
bool isRestricted(SUMOVehicleClass vclass) const
check if this lane is restricted
Definition: GNELane.cpp:774
const std::vector< GNEAdditional * > & getAdditionalChilds() const
get additional childs of lane
Definition: GNELane.cpp:768
remove busLane
Definition: GUIAppEnum.h:658
int SVCPermissions
bitset where each bit declares whether a certain SVC may use this edge/lane
void removeAdditionalChild(GNEAdditional *additional)
remove additional child to this lane
Definition: GNELane.cpp:751
bool getBool(const std::string &name) const
Returns the boolean-value of the named option (only for Option_Bool)
The representation of a single edge during network building.
Definition: NBEdge.h:71
bool showRails
Information whether rails shall be drawn.
The link is a 180 degree turn.
static RGBColor colorForLinksState(FXuint state)
return the color for each linkstate
add reverse edge
Definition: GUIAppEnum.h:622
bool hasRestrictedLane(SUMOVehicleClass vclass) const
check if edge has a restricted lane
Definition: GNEEdge.cpp:1101
mode for editing tls
Definition: GNEViewNet.h:63
void buildCenterPopupEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds an entry which allows to center to the object.
bool setFunctionalColor(int activeScheme) const
sets the color according to the current scheme index and some lane function
Definition: GNELane.cpp:910
T MAX2(T a, T b)
Definition: StdDefs.h:70
double getColorValue(int activeScheme) const
return value for lane coloring according to the given scheme
Definition: GNELane.cpp:946
bool isSelected(GUIGlObjectType type, GUIGlID id)
Returns the information whether the object with the given type and id is selected.
void setPermissions(SVCPermissions permissions, int lane=-1)
set allowed/disallowed classes for the given lane or for all lanes if -1 is given ...
Definition: NBEdge.cpp:2885
This lane is powered by an underlying GNEEdge and basically knows how to draw itself.
Definition: GNELane.h:54
int editMode
the current NETEDIT mode (temporary)
bool showLaneDirection
Whether to show direction indicators for lanes.
Copy edge name (for lanes only)
Definition: GUIAppEnum.h:237
bool setMultiColor(const GUIColorer &c) const
sets multiple colors according to the current scheme index and some lane function ...
Definition: GNELane.cpp:924
double endOffset
This lane&#39;s offset to the intersection begin.
Definition: NBEdge.h:141
GNELane()
FOX needs this.
Definition: GNELane.cpp:83
SumoXMLAttr
Numbers representing SUMO-XML - attributes.
std::vector< RGBColor > myShapeColors
The color of the shape parts (cached)
Definition: GNELane.h:245
This is an uncontrolled, right-before-left link.
const double SUMO_const_laneOffset
Definition: StdDefs.h:51
const std::vector< GNEConnection * > & getGNEConnections()
returns a reference to the GNEConnection vector
Definition: GNEEdge.cpp:549
void handleMultiChange(GNELane *lane, FXObject *obj, FXSelector sel, void *data)
update phase definition for the current traffic light and phase
bool isRailway(SVCPermissions permissions)
Returns whether an edge with the given permission is a railway edge.
remove bikelane
Definition: GUIAppEnum.h:656
Lane & getLaneStruct(int lane)
Definition: NBEdge.h:1154
The link is controlled by a tls which is off, not blinking, may pass.
transform lane to bikelane
Definition: GUIAppEnum.h:642
This is an uncontrolled, all-way stop link.
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.
Boundary getBoundary() const
returns the boundry (including lanes)
Definition: GNELane.cpp:639
int getIndex() const
returns the index of the lane
Definition: GNELane.cpp:697
GUIGlID getGlID() const
Returns the numerical id of the object.
static const double UNSPECIFIED_WIDTH
unspecified lane width
Definition: NBEdge.h:255
void setIndex(int index)
Definition: GNELane.cpp:702
A class that stores a 2D geometrical boundary.
Definition: Boundary.h:48
int myIndex
The index of this lane.
Definition: GNELane.h:221
This is an uncontrolled, zipper-merge link.
The link is a (hard) left direction.
static OptionsCont & getOptions()
Retrieves the options.
Definition: OptionsCont.cpp:65
bool accelRamp
Whether this lane is an acceleration lane.
Definition: NBEdge.h:153
void setAcceleration(int lane, bool accelRamp)
marks one lane as acceleration lane
Definition: NBEdge.cpp:2877
std::vector< double > myLaneRestrictedTextureRotations
Rotations of textures of restricted lanes.
Definition: GNELane.h:235
LinkDirection
The different directions a link between two lanes may take (or a stream between two edges)...
std::vector< std::string > getStrings() const
The link is a straight direction.
virtual const std::string & getMicrosimID() const
Returns the id of the object as known to microsim.
double getSpeed() const
returns the current speed of lane
Definition: GNELane.cpp:709
void p_add(GNEChange_Attribute *cmd)
special method, avoid empty changes, always execute
bool drawAsRailway(const GUIVisualizationSettings &s) const
whether to draw this lane as a railway
Definition: GNELane.cpp:1001
void drawDirectionIndicators() const
direction indicators for lanes
Definition: GNELane.cpp:1037
GUIGlObjectType getType() const
Returns the type of the object as coded in GUIGlObjectType.
static double naviDegree(const double angle)
Definition: GeomHelper.cpp:187
set non-default geometry endpoint
Definition: GUIAppEnum.h:628
#define PI
Definition: polyfonts.c:61
void drawLane2LaneConnections() const
draw lane to lane connections
Definition: GNELane.cpp:219
double getLaneWidth() const
Returns the default width of lanes of this edge.
Definition: NBEdge.h:523
void drawArrows() const
draw arrows
Definition: GNELane.cpp:149
int getPriority() const
Returns the priority of the edge.
Definition: NBEdge.h:420
transform lane to busLane
Definition: GUIAppEnum.h:644
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:439
GNEEdge & getParentEdge()
Returns underlying parent edge.
Definition: GNELane.cpp:1078
reverse an edge
Definition: GUIAppEnum.h:620
void setAttribute(SumoXMLAttr key, const std::string &value, GNEUndoList *undoList)
Definition: GNELane.cpp:812
void drawTLSLinkNo(const GUIVisualizationSettings &s) const
draw TLS Link Number
Definition: GNELane.cpp:121
This is an uncontrolled, minor link, has to brake.
A point in 2D or 3D with translation and scaling methods.
Definition: Position.h:46
const std::vector< double > & getShapeRotations() const
returns the vector with the shape rotations
Definition: GNELane.cpp:627
void addAdditionalChild(GNEAdditional *additional)
add additional child to this lane
Definition: GNELane.cpp:739
A list of positions.
bool isLogicValid()
whether this junction has a valid logic
bool isWaterway(SVCPermissions permissions)
Returns whether an edge with the given permission is a waterway edge.
std::vector< double > myShapeRotations
Definition: GNELane.h:226
friend class GNEChange_Attribute
declare friend class
double y() const
Returns the y-position.
Definition: Position.h:68
std::vector< GNEConnection * > getGNEIncomingConnections()
returns a vector with the incoming GNEConnections of this lane
Definition: GNELane.cpp:1084
int getNumLanes() const
Returns the number of lanes.
Definition: NBEdge.h:413
LinkState
The right-of-way state of a link between two lanes used when constructing a NBTrafficLightLogic, in MSLink and GNEInternalLane.
const T getColor(const double value) const
double length() const
Returns the length.
transform lane to sidewalk
Definition: GUIAppEnum.h:640
GUIVisualizationTextSettings drawLinkTLIndex
T MIN2(T a, T b)
Definition: StdDefs.h:64
static void drawOutlineCircle(double width, double iwidth, int steps=8)
Draws an unfilled circle around (0,0)
Definition: GLHelper.cpp:371
The link is a (hard) right direction.
#define POSITION_EPS
Definition: config.h:176
LinkState getLinkState(const NBEdge *incoming, NBEdge *outgoing, int fromLane, int toLane, bool mayDefinitelyPass, const std::string &tlID) const
get link state
Definition: NBNode.cpp:1613
Position positionAtOffset2D(double pos, double lateralOffset=0) const
Returns the position at the given length.
Boundary & grow(double by)
extends the boundary by the given amount
Definition: Boundary.cpp:234
SVCPermissions parseVehicleClasses(const std::string &allowedS)
Parses the given definition of allowed vehicle classes into the given containers Deprecated classes g...
void drawMarkings(const bool &selectedEdge, double scale) const
draw lane markings
Definition: GNELane.cpp:407
static void drawLine(const Position &beg, double rot, double visLength)
Draws a thin line.
Definition: GLHelper.cpp:265
const std::string getID() const
function to support debugging
std::vector< GNEConnection * > getGNEOutcomingConnections()
returns a vector with the outgoing GNEConnections of this lane
Definition: GNELane.cpp:1105
LinkDirection getDirection(const NBEdge *const incoming, const NBEdge *const outgoing, bool leftHand=false) const
Returns the representation of the described stream&#39;s direction.
Definition: NBNode.cpp:1549
std::vector< Connection > myConnections
List of connections to following edges.
Definition: NBEdge.h:1374
restore geometry endpoint to node position
Definition: GUIAppEnum.h:630
double laneMinSize
The minimum visual lane width for drawing.
The link is a partial right direction.
double width
This lane&#39;s width.
Definition: NBEdge.h:144
vehicle is a passenger car (a "normal" car)
void updateGeometry()
update pre-computed geometry information
Definition: GNELane.cpp:645
remove inner geometry
Definition: GUIAppEnum.h:632
is an arbitrary ship
begin/end of the description of an edge
bool canParseVehicleClasses(const std::string &classes)
Checks whether the given string contains only known vehicle classes.
std::string getAttribute(SumoXMLAttr key) const
Definition: GNELane.cpp:780
A road/street connecting two junctions (netedit-version)
Definition: GNEEdge.h:57
const std::vector< double > & getShapeLengths() const
returns the vector with the shape lengths
Definition: GNELane.cpp:633
SVCPermissions getPermissions(int lane=-1) const
get the union of allowed classes over all lanes or for a specific lane
Definition: NBEdge.cpp:2913
void drawLinkRules() const
draw link rules
Definition: GNELane.cpp:144
GNEEdge & myParentEdge
The Edge that to which this lane belongs.
Definition: GNELane.h:218
vehicle is a bus
double getLaneSpeed(int lane) const
get lane speed
Definition: NBEdge.cpp:1612
add bikelane
Definition: GUIAppEnum.h:650
NBNode * getToNode() const
Returns the destination node of the edge.
Definition: NBEdge.h:434
double getLength() const
Returns the computed length of the edge.
Definition: NBEdge.h:481
const PositionVector & getShape() const
returns the shape of the lane
Definition: GNELane.cpp:621
double selectionScale
the current selection scaling in NETEDIT (temporary)
void updateConnectionIDs()
Definition: GNELane.cpp:1120
long onDefault(FXObject *, FXSelector, void *)
multiplexes message to two targets
Definition: GNELane.cpp:1069
virtual void setMicrosimID(const std::string &newID)
Changes the microsimID of the object.
double getPositionRelativeToShapeLength(double position) const
Definition: GNELane.cpp:733
An Element which don&#39;t belongs to GNENet but has influency in the simulation.
Definition: GNEAdditional.h:62
The link is controlled by a tls which is off and blinks, has to brake.
split an edge
Definition: GUIAppEnum.h:616
std::vector< Position > myLaneRestrictedTexturePositions
Position of textures of restricted lanes.
Definition: GNELane.h:232
void setSpecialColor(const RGBColor *Color2)
Definition: GNELane.cpp:861
The popup menu of a globject.
an edge
This is an uncontrolled, major link, may pass.
split an edge
Definition: GUIAppEnum.h:618
void buildSelectionPopupEntry(GUIGLObjectPopupMenu *ret, bool addSeparator=true)
Builds an entry which allows to (de)select the object.
Boundary getCenteringBoundary() const
Returns the boundary to which the view shall be centered in order to show the object.
Definition: GNELane.cpp:613
static const StringBijection< FXuint > LinkStateNames
long names for link states
static FXColor getFXColor(const RGBColor &col)
converts FXColor to RGBColor
Definition: MFXUtils.cpp:121
Represents a single node (junction) during network building.
Definition: NBNode.h:75
T get(const std::string &str) const
void insertMenuPaneChild(FXMenuPane *child)
Insert a sub-menu pane in this GUIGLObjectPopupMenu.
The link is a 180 degree turn (left-hand network)
SumoXMLTag getTag() const
get XML Tag assigned to this object
GUIVisualizationSettings * getVisualisationSettings() const
get visualitation settings
static void drawTriangleAtEnd(const Position &p1, const Position &p2, double tLength, double tWidth)
Draws a triangle at the end of the given line.
Definition: GLHelper.cpp:418
void drawCrossties(double length, double spacing, double halfWidth) const
draw crossties for railroads
Definition: GNELane.cpp:1013
std::string getLaneID(int lane) const
get Lane ID (Secure)
Definition: NBEdge.cpp:2679
const std::vector< GNEEdge * > & getGNEIncomingEdges() const
Returns incoming GNEEdges.
static const RGBColor selectionColor
color of selection
Definition: GNENet.h:97
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
bool isValid(SumoXMLAttr key, const std::string &value)
Definition: GNELane.cpp:833
NBEdge * getNBEdge()
returns the internal NBEdge
Definition: GNEEdge.cpp:261
Position getPositionInformation() const
Returns the cursor&#39;s x/y position within the network.
double getLaneParametricLength() const
returns the parameteric length of the lane
Definition: GNELane.cpp:715
Boundary getBoxBoundary() const
Returns a boundary enclosing this list of lines.
void mkItem(const char *name, bool dynamic, ValueSource< unsigned > *src)
Adds a row which obtains its value from an unsigned-ValueSource.
GUIParameterTableWindow * getParameterWindow(GUIMainWindow &app, GUISUMOAbstractView &parent)
Returns an own parameter window.
Definition: GNELane.cpp:601
GUISelectedStorage gSelected
A global holder of selected objects.
void closeBuilding()
Closes the building of the table.
revert transformation
Definition: GUIAppEnum.h:646
A window containing a gl-object&#39;s parameter.
GNEViewNet * getViewNet() const
get view net
Definition: GNENet.cpp:1165
static FXIcon * getIcon(GUIIcon which)
returns a icon previously defined in the enum GUIIcon
GUIVisualizationTextSettings drawLinkJunctionIndex
const PositionVector & getLaneShape(int i) const
Returns the shape of the nth lane.
Definition: NBEdge.cpp:757
void drawGL(const GUIVisualizationSettings &s) const
Draws the object.
Definition: GNELane.cpp:269
~GNELane()
Destructor.
Definition: GNELane.cpp:92
duplicate a lane
Definition: GUIAppEnum.h:638
void setLaneWidth(int lane, double width)
set lane specific width (negative lane implies set for all lanes)
Definition: NBEdge.cpp:2807
void buildPopupHeader(GUIGLObjectPopupMenu *ret, GUIMainWindow &app, bool addSeparator=true)
Builds the header.
void drawLinkNo(const GUIVisualizationSettings &s) const
draw link Number
Definition: GNELane.cpp:97
The link has no direction (is a dead end link)
a junction
GNEJunction * getGNEJunctionDestiny() const
returns the destination-junction
Definition: GNEEdge.cpp:165
static RGBColor getColor()
gets the gl-color
Definition: GLHelper.cpp:445