Microscopic Traffic Simulator
BezierLane.cs
Go to the documentation of this file.
1 using System;
2 using System.Collections.Generic;
3 using System.Windows;
4 
5 namespace Microscopic_Traffic_Simulator___Model.GeometricObjects.Lanes
6 {
10  [Serializable]
11  public class BezierLane : Lane
12  {
16  private struct PointAndDistanceToOtherPoint
17  {
21  private Point point;
25  public Point Point { get { return point; } }
26 
30  private double distance;
34  public double Distance { get { return distance; } }
35 
42  internal PointAndDistanceToOtherPoint(Point point, Point otherPoint)
43  {
44  this.point = point;
45  distance = (otherPoint - point).Length;
46  }
47  }
48 
52  private Point firstControlLocation;
56  public Point FirstControlLocation
57  {
58  get { return firstControlLocation; }
59  set { firstControlLocation = value; }
60  }
61 
65  private Point secondControlLocation;
69  public Point SecondControlLocation
70  {
71  get { return secondControlLocation; }
72  set { SecondControlLocation = value; }
73  }
74 
82  public BezierLane(Point startLocation, Point firstControlLocation, Point secondControlLocation,
83  Point endLocation)
84  : base(startLocation, endLocation)
85  {
86  this.firstControlLocation = firstControlLocation;
87  this.secondControlLocation = secondControlLocation;
88  }
89 
95  internal override IEnumerable<Point> LanePoints(double lanePointsMaxDistance)
96  {
97  //return start point
98  Point lastPoint;
99  yield return lastPoint = startNode.Location;
100 
101  //initialization of variables and main cycle returning new lane point after each iteration
102  double currentT = 0.0;
103  double distanceDivided10 = lanePointsMaxDistance / 10.0;
104  while (currentT < 1.0)
105  {
106  //initialize base t for computing next last point. The base t is t of the previous point.
107  double tBase = currentT;
108  //get range from current t to 1.0
109  double tRange = 1.0 - currentT;
110  //initialize addend to find the next last point by initializing it to half of the tRange
111  double tAddend = tRange / 2.0;
112  //divide addend by 2 until the point of t is distant less or equal than tenth of maximum distance
113  //between points
114  while ((lastPoint - ComputePoint(tBase + tAddend)).Length > distanceDivided10)
115  {
116  tAddend /= 2.0;
117  }
118  //initialize previous and current point and distance to last lane point
119  PointAndDistanceToOtherPoint previousPointAndDistanceToOtherPoint =
120  new PointAndDistanceToOtherPoint(lastPoint, lastPoint);
121  PointAndDistanceToOtherPoint currentPointAndDistanceToOtherPoint =
122  new PointAndDistanceToOtherPoint(lastPoint, lastPoint);
123  //find point distant from last point as much as the maximum distance of lane points
124  while (currentPointAndDistanceToOtherPoint.Distance < lanePointsMaxDistance && currentT < 1.0)
125  {
126  currentT += tAddend;
127  previousPointAndDistanceToOtherPoint = currentPointAndDistanceToOtherPoint;
128  currentPointAndDistanceToOtherPoint =
129  new PointAndDistanceToOtherPoint(ComputePoint(currentT), lastPoint);
130  }
131 
132  //determine whether there is no other point except the end point
133  if (currentT < 1.0)
134  {
135  //determine whether the point before or after the current-t is nearer to current-t
136  if (previousPointAndDistanceToOtherPoint.Distance < currentPointAndDistanceToOtherPoint.Distance)
137  {
138  currentT -= tAddend;
139  lastPoint = previousPointAndDistanceToOtherPoint.Point;
140  }
141  else
142  {
143  lastPoint = currentPointAndDistanceToOtherPoint.Point;
144  }
145  yield return lastPoint;
146  }
147  }
148  yield return endNode.Location;
149  }
150 
156  private Point ComputePoint(double t)
157  {
158  Point p = new Point();
159  double u = 1 - t;
160  p.X = u * u * u * startNode.Location.X +
161  3 * u * u * t * firstControlLocation.X +
162  3 * u * t * t * secondControlLocation.X +
163  t * t * t * endNode.Location.X;
164  p.Y = u * u * u * startNode.Location.Y +
165  3 * u * u * t * firstControlLocation.Y +
166  3 * u * t * t * secondControlLocation.Y +
167  t * t * t * endNode.Location.Y;
168  return p;
169  }
170  }
171 }
BezierLane(Point startLocation, Point firstControlLocation, Point secondControlLocation, Point endLocation)
Constructor for bezier lane.
Definition: BezierLane.cs:82