1 package org.opentrafficsim.base.geometry;
2
3 import java.util.Iterator;
4 import java.util.NoSuchElementException;
5
6 import org.djutils.draw.bounds.Bounds2d;
7 import org.djutils.draw.line.Polygon2d;
8 import org.djutils.draw.point.Point2d;
9 import org.djutils.exceptions.Throw;
10
11
12
13
14
15
16
17
18
19 public abstract class CircleShape implements OtsShape
20 {
21
22
23 private final double radius;
24
25
26 private final int polygonSegments;
27
28
29 private Polygon2d polygon;
30
31
32 private final Bounds2d bounds;
33
34
35
36
37
38 public CircleShape(final double radius)
39 {
40 this(radius, DEFAULT_POLYGON_SEGMENTS);
41 }
42
43
44
45
46
47
48 public CircleShape(final double radius, final int polygonSegments)
49 {
50 Throw.whenNull(radius, "Radius must not be null.");
51 Throw.when(radius <= 0.0, IllegalArgumentException.class, "Radius must be above 0.0.");
52 this.radius = radius;
53 this.polygonSegments = polygonSegments;
54 this.bounds = new Bounds2d(2 * radius, 2 * radius);
55 }
56
57 @Override
58 public Bounds2d getRelativeBounds()
59 {
60 return this.bounds;
61 }
62
63 @Override
64 public double signedDistance(final Point2d point)
65 {
66 return Math.hypot(point.x, point.y) - this.radius;
67 }
68
69 @Override
70 public Polygon2d getRelativeContour()
71 {
72 if (this.polygon == null)
73 {
74 if (this.radius == 0.0)
75 {
76 this.polygon = new Polygon2d(new double[] {0.0}, new double[] {0.0});
77 }
78 else
79 {
80 this.polygon = new Polygon2d(new Iterator<Point2d>()
81 {
82
83 private int step = 0;
84
85 @Override
86 public boolean hasNext()
87 {
88 return this.step <= CircleShape.this.polygonSegments;
89 }
90
91 @Override
92 public Point2d next()
93 {
94 Throw.when(!hasNext(), NoSuchElementException.class, "Iterator has no more elements.");
95
96
97 double ang = this.step == CircleShape.this.polygonSegments ? 0.0
98 : (2.0 * Math.PI * this.step) / CircleShape.this.polygonSegments;
99 this.step++;
100 return new Point2d(Math.cos(ang) * CircleShape.this.radius, Math.sin(ang) * CircleShape.this.radius);
101 }
102 });
103 }
104 }
105 return this.polygon;
106 }
107
108 @Override
109 public String toString()
110 {
111 return "CircleShape [radius=" + this.radius + "]";
112 }
113
114 }