Path: blob/master/SLICK_HOME/src/org/newdawn/slick/geom/Path.java
1461 views
package org.newdawn.slick.geom;12import java.util.ArrayList;34/**5* A shape built from lines and curves. Hole support is present but6* restricted.7*8* @author kevin9*/10public class Path extends Shape {11/** The local list of points */12private ArrayList localPoints = new ArrayList();13/** The current x coordinate */14private float cx;15/** The current y coordiante */16private float cy;17/** True if the path has been closed */18private boolean closed;19/** The list of holes placed */20private ArrayList holes = new ArrayList();21/** The current hole being built */22private ArrayList hole;2324/**25* Create a new path26*27* @param sx The start x coordinate of the path28* @param sy The start y coordiante of the path29*/30public Path(float sx, float sy) {31localPoints.add(new float[] {sx,sy});32cx = sx;33cy = sy;34pointsDirty = true;35}3637/**38* Start building a hole in the previously defined contour39*40* @param sx The start point of the hole41* @param sy The start point of the hole42*/43public void startHole(float sx, float sy) {44hole = new ArrayList();45holes.add(hole);46}4748/**49* Add a line to the contour or hole which ends at the specified50* location.51*52* @param x The x coordinate to draw the line to53* @param y The y coordiante to draw the line to54*/55public void lineTo(float x, float y) {56if (hole != null) {57hole.add(new float[] {x,y});58} else {59localPoints.add(new float[] {x,y});60}61cx = x;62cy = y;63pointsDirty = true;64}6566/**67* Close the path to form a polygon68*/69public void close() {70closed = true;71}7273/**74* Add a curve to the specified location (using the default segments 10)75*76* @param x The destination x coordinate77* @param y The destination y coordiante78* @param cx1 The x coordiante of the first control point79* @param cy1 The y coordiante of the first control point80* @param cx2 The x coordinate of the second control point81* @param cy2 The y coordinate of the second control point82*/83public void curveTo(float x, float y, float cx1, float cy1, float cx2, float cy2) {84curveTo(x,y,cx1,cy1,cx2,cy2,10);85}8687/**88* Add a curve to the specified location (specifing the number of segments)89*90* @param x The destination x coordinate91* @param y The destination y coordiante92* @param cx1 The x coordiante of the first control point93* @param cy1 The y coordiante of the first control point94* @param cx2 The x coordinate of the second control point95* @param cy2 The y coordinate of the second control point96* @param segments The number of segments to use for the new curve97*/98public void curveTo(float x, float y, float cx1, float cy1, float cx2, float cy2, int segments) {99// special case for zero movement100if ((cx == x) && (cy == y)) {101return;102}103104Curve curve = new Curve(new Vector2f(cx,cy),new Vector2f(cx1,cy1),new Vector2f(cx2,cy2),new Vector2f(x,y));105float step = 1.0f / segments;106107for (int i=1;i<segments+1;i++) {108float t = i * step;109Vector2f p = curve.pointAt(t);110if (hole != null) {111hole.add(new float[] {p.x,p.y});112} else {113localPoints.add(new float[] {p.x,p.y});114}115cx = p.x;116cy = p.y;117}118pointsDirty = true;119}120121/**122* @see org.newdawn.slick.geom.Shape#createPoints()123*/124protected void createPoints() {125points = new float[localPoints.size() * 2];126for (int i=0;i<localPoints.size();i++) {127float[] p = (float[]) localPoints.get(i);128points[(i*2)] = p[0];129points[(i*2)+1] = p[1];130}131}132133/**134* @see org.newdawn.slick.geom.Shape#transform(org.newdawn.slick.geom.Transform)135*/136public Shape transform(Transform transform) {137Path p = new Path(cx,cy);138p.localPoints = transform(localPoints, transform);139for (int i=0;i<holes.size();i++) {140p.holes.add(transform((ArrayList) holes.get(i), transform));141}142p.closed = this.closed;143144return p;145}146147/**148* Transform a list of points149*150* @param pts The pts to transform151* @param t The transform to apply152* @return The transformed points153*/154private ArrayList transform(ArrayList pts, Transform t) {155float[] in = new float[pts.size()*2];156float[] out = new float[pts.size()*2];157158for (int i=0;i<pts.size();i++) {159in[i*2] = ((float[]) pts.get(i))[0];160in[(i*2)+1] = ((float[]) pts.get(i))[1];161}162t.transform(in, 0, out, 0, pts.size());163164ArrayList outList = new ArrayList();165for (int i=0;i<pts.size();i++) {166outList.add(new float[] {out[(i*2)],out[(i*2)+1]});167}168169return outList;170}171172// /**173// * Calculate the triangles that can fill this shape174// */175// protected void calculateTriangles() {176// if (!trianglesDirty) {177// return;178// }179// if (points.length >= 6) {180// boolean clockwise = true;181// float area = 0;182// for (int i=0;i<(points.length/2)-1;i++) {183// float x1 = points[(i*2)];184// float y1 = points[(i*2)+1];185// float x2 = points[(i*2)+2];186// float y2 = points[(i*2)+3];187//188// area += (x1 * y2) - (y1 * x2);189// }190// area /= 2;191// clockwise = area > 0;192//193// if (clockwise) {194// tris = new MannTriangulator();195// for (int i=0;i<points.length;i+=2) {196// tris.addPolyPoint(points[i], points[i+1]);197// }198//199// for (int h=0;h<holes.size();h++) {200// ArrayList hole = (ArrayList) holes.get(h);201// tris.startHole();202// for (int i=0;i<hole.size();i++) {203// float[] pt = (float[]) hole.get(i);204// tris.addPolyPoint(pt[0],pt[1]);205// }206// }207// tris.triangulate();208// } else {209// tris = new MannTriangulator();210// for (int i=points.length-2;i>=0;i-=2) {211// tris.addPolyPoint(points[i], points[i+1]);212// }213//214// for (int h=0;h<holes.size();h++) {215// ArrayList hole = (ArrayList) holes.get(h);216// tris.startHole();217// for (int i=hole.size()-1;i>=0;i--) {218// float[] pt = (float[]) hole.get(i);219// tris.addPolyPoint(pt[0],pt[1]);220// }221// }222// tris.triangulate();223// }224//225// } else {226// tris.triangulate();227// }228//229// trianglesDirty = false;230// }231232/**233* True if this is a closed shape234*235* @return True if this is a closed shape236*/237public boolean closed() {238return closed;239}240}241242243