public ShapeCollision clone() { var clone = new ShapeCollision(); clone.copy_from(this); return(clone); }
////////////////private static bool Intersect(Vector2[] polygon1, Vector2[] polygon2) ////////////////{ //////////////// var pointsA = polygon1; //////////////// var edgesA = BuildEdges(pointsA); //////////////// int edgeCountA = edgesA.Length; //////////////// var pointsB = polygon2; //////////////// var edgesB = BuildEdges(pointsB); //////////////// int edgeCountB = edgesB.Length; //////////////// Vector2 edge; //////////////// // Loop through all the edges of both polygons //////////////// for (int edgeIndex = 0; edgeIndex < edgeCountA + edgeCountB; edgeIndex++) //////////////// { //////////////// if (edgeIndex < edgeCountA) //////////////// { //////////////// edge = edgesA[edgeIndex]; //////////////// } //////////////// else //////////////// { //////////////// edge = edgesB[edgeIndex - edgeCountA]; //////////////// } //////////////// // ===== 1. Find if the polygons are currently intersecting ===== //////////////// // Find the axis perpendicular to the current edge //////////////// Vector2 axis = new Vector2(-edge.y, edge.x); //////////////// axis.Normalize(); //////////////// // Find the projection of the polygon on the current axis //////////////// float minA = 0; float minB = 0; float maxA = 0; float maxB = 0; //////////////// ProjectPolygon(axis, pointsA, ref minA, ref maxA); //////////////// ProjectPolygon(axis, pointsB, ref minB, ref maxB); //////////////// // Check if the polygon projections are currentlty intersecting //////////////// //if (IntervalDistance(minA, maxA, minB, maxB) <= 0.000001) return true; //////////////// if (Intersects(minA, maxA, minB, maxB, true)) //////////////// return true; //////////////// } //////////////// return false; ////////////////} ////////////////private static Vector2[] BuildEdges(Vector2[] points/*,Vector2 offset*/) ////////////////{ //////////////// Vector2 p1; //////////////// Vector2 p2; //////////////// List<Vector2> edges = new List<Vector2>(points.Length - 1); //////////////// for (int i = 0; i < points.Length; i++) //////////////// { //////////////// p1 = points[i]; //////////////// if (i + 1 >= points.Length) //////////////// { //////////////// p2 = points[0]; //////////////// } //////////////// else //////////////// { //////////////// p2 = points[i + 1]; //////////////// } //////////////// //edges.Add(offset+p2 - p1); //////////////// edges.Add(p2 - p1); //////////////// } //////////////// return edges.ToArray(); ////////////////} ////////////////// Calculate the distance between [minA, maxA] and [minB, maxB] ////////////////// The distance will be negative if the intervals overlap ////////////////private static float IntervalDistance(float minA, float maxA, float minB, float maxB) ////////////////{ //////////////// if (minA < minB) //////////////// { //////////////// return minB - maxA; //////////////// } //////////////// else //////////////// { //////////////// return minA - maxB; //////////////// } ////////////////} ////////////////public static bool Intersects(float min1, float max1, float min2, float max2, bool strict, bool correctMinMax = true) ////////////////{ //////////////// if (correctMinMax) //////////////// { //////////////// float tmp1 = min1, tmp2 = max1; //////////////// min1 = Math.Min(tmp1, tmp2); //////////////// max1 = Math.Max(tmp1, tmp2); //////////////// tmp1 = min2; //////////////// tmp2 = max2; //////////////// min2 = Math.Min(tmp1, tmp2); //////////////// max2 = Math.Max(tmp1, tmp2); //////////////// } //////////////// if (strict) //////////////// return (min1 <= min2 && max1 > min2) || (min2 <= min1 && max2 > min1); //////////////// else //////////////// return (min1 <= min2 && max1 >= min2) || (min2 <= min1 && max2 >= min1); ////////////////} ////////////////// Calculate the projection of a polygon on an axis and returns it as a [min, max] interval ////////////////private static void ProjectPolygon(Vector2 axis, Vector2[] polygon, ref float min, ref float max) ////////////////{ //////////////// // To project a point on an axis use the dot product //////////////// //float d = Vector2.Dot(axis, polygon[0]); //////////////// float d = DotProduct(axis, polygon[0]); //////////////// min = d; //////////////// max = d; //////////////// for (int i = 0; i < polygon.Length; i++) //////////////// { //////////////// d = DotProduct(polygon[i], axis); //////////////// if (d < min) //////////////// { //////////////// min = d; //////////////// } //////////////// else //////////////// { //////////////// if (d > max) //////////////// { //////////////// max = d; //////////////// } //////////////// } //////////////// } ////////////////} ////////////////public static float DotProduct(Vector2 vectorA, Vector2 vectorB) ////////////////{ //////////////// return vectorA.x * vectorB.x + vectorA.y * vectorB.y; ////////////////} private static bool Intersect(Vector2[] polygon1, Vector2[] polygon2) { var into = new ShapeCollision(); var flip = false; var tmp1 = checkPolygons(polygon1, polygon2, flip); var tmp2 = checkPolygons(polygon2, polygon1, !flip); if (tmp1 == null) { return(false); } if (tmp2 == null) { return(false); } ShapeCollision result = null; ShapeCollision other = null; if (System.Math.Abs(tmp1.overlap) < System.Math.Abs(tmp2.overlap)) { result = tmp1; other = tmp2; } else { result = tmp2; other = tmp1; } result.otherOverlap = other.overlap; result.otherSeparationX = other.separationX; result.otherSeparationY = other.separationY; result.otherUnitVectorX = other.unitVectorX; result.otherUnitVectorY = other.unitVectorY; into.copy_from(result); result = other = null; //return Math.Abs(into.otherOverlap) > 0.00001; return(true); }
public static ShapeCollision testPolygonVsPolygon(Polygon polygon1, Polygon polygon2, bool flip = false) { var output = new ShapeCollision(); if ((tmp1 = checkPolygons(polygon1, polygon2, flip)) == null) { return(null); } if ((tmp2 = checkPolygons(polygon2, polygon1, !flip)) == null) { return(null); } ShapeCollision result = null; ShapeCollision other = null; if (System.Math.Abs(tmp1.overlap) < System.Math.Abs(tmp2.overlap)) { result = tmp1; other = tmp2; } else { result = tmp2; other = tmp1; } result.otherOverlap = other.overlap; result.otherSeparationX = other.separationX; result.otherSeparationY = other.separationY; result.otherUnitVectorX = other.unitVectorX; result.otherUnitVectorY = other.unitVectorY; output.copy_from(result); result = other = null; return(result); } //testPolygonVsPolygon