fix circle bounding box not scaling with transform

pull/2/head
thatcosmonaut 2019-09-18 17:00:43 -07:00
parent e292ad1875
commit e9eb796ede
3 changed files with 100 additions and 16 deletions

View File

@ -8,13 +8,13 @@ namespace MoonTools.Core.Bonk
{
public struct AABB
{
public int MinX { get; private set; }
public int MinY { get; private set; }
public int MaxX { get; private set; }
public int MaxY { get; private set; }
public float MinX { get; private set; }
public float MinY { get; private set; }
public float MaxX { get; private set; }
public float MaxY { get; private set; }
public int Width { get { return MaxX - MinX; } }
public int Height { get { return MaxY - MinY; } }
public float Width { get { return MaxX - MinX; } }
public float Height { get { return MaxY - MinY; } }
public static AABB FromTransformedVertices(IEnumerable<Position2D> vertices, Transform2D transform)
{
@ -22,14 +22,14 @@ namespace MoonTools.Core.Bonk
return new AABB
{
MinX = (int)Math.Round(TransformedVertices.Min(vertex => vertex.X)),
MinY = (int)Math.Round(TransformedVertices.Min(vertex => vertex.Y)),
MaxX = (int)Math.Round(TransformedVertices.Max(vertex => vertex.X)),
MaxY = (int)Math.Round(TransformedVertices.Max(vertex => vertex.Y))
MinX = TransformedVertices.Min(vertex => vertex.X),
MinY = TransformedVertices.Min(vertex => vertex.Y),
MaxX = TransformedVertices.Max(vertex => vertex.X),
MaxY = TransformedVertices.Max(vertex => vertex.Y)
};
}
public AABB(int minX, int minY, int maxX, int maxY)
public AABB(float minX, float minY, float maxX, float maxY)
{
MinX = minX;
MinY = minY;

View File

@ -18,13 +18,13 @@ namespace MoonTools.Core.Bonk
return Vector2.Transform(Vector2.Normalize(direction) * Radius, transform.TransformMatrix);
}
public AABB AABB(Transform2D Transform2D)
public AABB AABB(Transform2D transform2D)
{
return new AABB(
Transform2D.Position.X - Radius,
Transform2D.Position.Y - Radius,
Transform2D.Position.X + Radius,
Transform2D.Position.Y + Radius
transform2D.Position.X - Radius * transform2D.Scale.X,
transform2D.Position.Y - Radius * transform2D.Scale.Y,
transform2D.Position.X + Radius * transform2D.Scale.X,
transform2D.Position.Y + Radius * transform2D.Scale.Y
);
}

View File

@ -16,6 +16,17 @@ namespace Tests
Assert.IsTrue(GJK2D.TestCollision(lineA, Transform2D.DefaultTransform, lineB, Transform2D.DefaultTransform).Item1);
}
[Test]
public void ScaledLinesOverlapping()
{
var lineA = new Line(new Position2D(-1, -1), new Position2D(1, 1));
var lineB = new Line(new Position2D(-1, 1), new Position2D(1, -1));
var transform = new Transform2D(new Position2D(0, 0), 0f, new Vector2(2, 2));
Assert.IsTrue(GJK2D.TestCollision(lineA, transform, lineB, transform).Item1);
}
[Test]
public void LineLineNotOverlapping()
{
@ -25,6 +36,17 @@ namespace Tests
Assert.IsFalse(GJK2D.TestCollision(lineA, Transform2D.DefaultTransform, lineB, Transform2D.DefaultTransform).Item1);
}
[Test]
public void ScaledLinesNotOverlapping()
{
var lineA = new Line(new Position2D(0, 1), new Position2D(1, 0));
var lineB = new Line(new Position2D(-1, -1), new Position2D(-2, -2));
var transform = new Transform2D(new Position2D(0, 0), 0f, new Vector2(2, 2));
Assert.IsFalse(GJK2D.TestCollision(lineA, transform, lineB, transform).Item1);
}
[Test]
public void CircleCircleOverlapping()
{
@ -36,6 +58,17 @@ namespace Tests
Assert.IsTrue(GJK2D.TestCollision(circleA, transformA, circleB, transformB).Item1);
}
[Test]
public void ScaledCirclesOverlapping()
{
var circleA = new Circle(2);
var transformA = new Transform2D(new Vector2(-3, 0), 0f, new Vector2(2, 2));
var circleB = new Circle(2);
var transformB = new Transform2D(new Vector2(3, 0), 0f, new Vector2(2, 2));
Assert.IsTrue(GJK2D.TestCollision(circleA, transformA, circleB, transformB).Item1);
}
[Test]
public void CircleCircleNotOverlapping()
{
@ -47,6 +80,17 @@ namespace Tests
Assert.IsFalse(GJK2D.TestCollision(circleA, transformA, circleB, transformB).Item1);
}
[Test]
public void ScaledCirclesNotOverlapping()
{
var circleA = new Circle(2);
var transformA = new Transform2D(new Vector2(-5, -5), 0, new Vector2(0.2f, 0.2f));
var circleB = new Circle(2);
var transformB = new Transform2D(new Vector2(5, 5), 0, new Vector2(0.2f, 0.2f));
Assert.IsFalse(GJK2D.TestCollision(circleA, transformA, circleB, transformB).Item1);
}
[Test]
public void PolygonPolygonOverlapping()
{
@ -67,6 +111,26 @@ namespace Tests
Assert.IsTrue(GJK2D.TestCollision(shapeA, transformA, shapeB, transformB).Item1);
}
[Test]
public void ScaledPolygonsOverlapping()
{
var shapeA = new Polygon(
new Position2D(-1, 1), new Position2D(1, 1),
new Position2D(-1, -1), new Position2D(1, -1)
);
var transformA = Transform2D.DefaultTransform;
var shapeB = new Polygon(
new Position2D(-1, 1), new Position2D(1, 1),
new Position2D(-1, -1), new Position2D(1, -1)
);
var transformB = new Transform2D(new Vector2(3f, 0f), 0f, new Vector2(3f, 3f));
Assert.IsTrue(GJK2D.TestCollision(shapeA, transformA, shapeB, transformB).Item1);
}
[Test]
public void PolygonPolygonNotOverlapping()
{
@ -87,6 +151,26 @@ namespace Tests
Assert.IsFalse(GJK2D.TestCollision(shapeA, transformA, shapeB, transformB).Item1);
}
[Test]
public void ScaledPolygonsNotOverlapping()
{
var shapeA = new Polygon(
new Position2D(-1, 1), new Position2D(1, 1),
new Position2D(-1, -1), new Position2D(1, -1)
);
var transformA = Transform2D.DefaultTransform;
var shapeB = new Polygon(
new Position2D(-1, 1), new Position2D(1, 1),
new Position2D(-1, -1), new Position2D(1, -1)
);
var transformB = new Transform2D(new Vector2(2f, 0), 0f, new Vector2(0.2f, 0.2f));
Assert.IsFalse(GJK2D.TestCollision(shapeA, transformA, shapeB, transformB).Item1);
}
[Test]
public void LinePolygonOverlapping()
{