-
Notifications
You must be signed in to change notification settings - Fork 28
Expand file tree
/
Copy pathPolygon.hx
More file actions
171 lines (110 loc) · 4.95 KB
/
Polygon.hx
File metadata and controls
171 lines (110 loc) · 4.95 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
package differ.shapes;
import differ.math.*;
import differ.shapes.*;
import differ.data.*;
import differ.sat.*;
/** A polygonal collision shape */
class Polygon extends Shape {
/** The transformed (rotated/scale) vertices cache */
public var transformedVertices ( get, never ) : Array<Vector>;
/** The vertices of this shape */
public var vertices ( get, never ) : Array<Vector>;
var _transformedVertices : Array<Vector>;
var _vertices : Array<Vector>;
var _transformed : Bool = false;
/** Create a new polygon with a given set of vertices at position x,y. */
public function new( x:Float, y:Float, vertices:Array<Vector> ) {
super( x,y );
name = 'polygon(sides:${vertices.length})';
_vertices = vertices;
_transformedVertices = [for (v in _vertices) v.clone()];
} //new
/** Test for a collision with a shape. */
override public function test( shape:Shape, ?into:ShapeCollision ) : ShapeCollision {
return shape.testPolygon(this, into, true);
} //test
/** Test for a collision with a circle. */
override public function testCircle( circle:Circle, ?into:ShapeCollision, flip:Bool = false ) : ShapeCollision {
return SAT2D.testCircleVsPolygon( circle, this, into, !flip );
} //testCircle
/** Test for a collision with a polygon. */
override public function testPolygon( polygon:Polygon, ?into:ShapeCollision, flip:Bool = false ) : ShapeCollision {
return SAT2D.testPolygonVsPolygon( this, polygon, into, flip );
} //testPolygon
/** Test for a collision with a ray. */
override public function testRay( ray:Ray, ?into:RayCollision ) : RayCollision {
return SAT2D.testRayVsPolygon(ray, this, into);
} //testRay
/** Destroy this polygon and clean up. */
override public function destroy() : Void {
_transformedVertices = null;
_vertices = null;
super.destroy();
} //destroy
//Public static API
/** Helper to create an Ngon at x,y with given number of sides, and radius.
A default radius of 100 if unspecified. Returns a ready made `Polygon` collision `Shape` */
public static function create( x:Float, y:Float, sides:Int, radius:Float=100):Polygon {
if(sides < 3) {
throw 'Polygon - Needs at least 3 sides';
}
var rotation:Float = (Math.PI * 2) / sides;
var angle:Float;
var vector:Vector;
var vertices:Array<Vector> = new Array<Vector>();
for(i in 0 ... sides) {
angle = (i * rotation) + ((Math.PI - rotation) * 0.5);
vector = new Vector();
vector.x = Math.cos(angle) * radius;
vector.y = Math.sin(angle) * radius;
vertices.push(vector);
}
return new Polygon(x,y,vertices);
} //create
/** Helper generate a rectangle at x,y with a given width/height and centered state.
Centered by default. Returns a ready made `Polygon` collision `Shape` */
public static function rectangle(x:Float, y:Float, width:Float, height:Float, centered:Bool = true):Polygon {
var vertices:Array<Vector> = new Array<Vector>();
if(centered) {
vertices.push( new Vector( -width / 2, -height / 2) );
vertices.push( new Vector( width / 2, -height / 2) );
vertices.push( new Vector( width / 2, height / 2) );
vertices.push( new Vector( -width / 2, height / 2) );
} else {
vertices.push( new Vector( 0, 0 ) );
vertices.push( new Vector( width, 0 ) );
vertices.push( new Vector( width, height) );
vertices.push( new Vector( 0, height) );
}
return new Polygon(x,y,vertices);
} //rectangle
/** Helper generate a square at x,y with a given width/height with given centered state.
Centered by default. Returns a ready made `Polygon` collision `Shape` */
public static inline function square(x:Float, y:Float, width:Float, centered:Bool = true) : Polygon {
return rectangle(x, y, width, width, centered);
} //square
/** Helper generate a triangle at x,y with a given radius.
Returns a ready made `Polygon` collision `Shape` */
public static function triangle(x:Float, y:Float, radius:Float) : Polygon {
return create(x, y, 3, radius);
} //triangle
//Internal
function get_transformedVertices() : Array<Vector> {
if (_transformed) {
_transformed = false;
var _count : Int = _vertices.length;
for (i in 0..._count) {
_transformedVertices[i].copy(_vertices[i]).transform(_transformMatrix);
}
}
return _transformedVertices;
}
function get_vertices() : Array<Vector> {
return _vertices;
}
override function refresh_transform()
{
super.refresh_transform();
_transformed = true;
}
} //Polygon