I'm currently attempting to add an overlap tester for an axis aligned and orientated bounding box but the solution only seems to work accurately when the OBB's angle is between -10 and +10. As the angle approaches +90 degrees the collision area seems to at first move to the right half of the OBB and then become non existent. Between 90 and 270 I couldn't get an overlap and then when it comes round a full 360 the area registers accurately again.
Any light on this subject would be great. I'm using positive X for 0 degrees increasing CCW.
EDIT: Did a little more research and realized that projecting a vector onto another requires more than just a dot product. Could any one give me a correct version of one of the check axis methods below?
EDIT 2: Actually just a dot product should do I think since the vectors being projected onto are unit length.
public static bool overlapAABB_OBB(AABB a, OBB o)
{
float rads = MathHelper.ToRadians(-o.angle);
T = Vector2.Subtract(o.position, a.position);
Ax.X = 1;
Ax.Y = 0;
Ay.X = 0;
Ay.Y = 1;
Ox.X = (float)Math.Cos(rads);
Ox.Y = (float)Math.Sin(rads);
Oy.X = -Ox.Y;
Oy.Y = Ox.X;
if (checkAX(a, o) &&
checkAY(a, o) &&
checkOX(a, o) &&
checkOY(a, o))
return true;
else
return false;
}
private static bool checkAX(AABB a, OBB o)
{
float TAx = Vector2.Dot(T, Ax);
float WoOxAx = Vector2.Dot(Vector2.Multiply(Ox, o.halfWidth), Ax);
float HoOyAx = Vector2.Dot(Vector2.Multiply(Oy, o.halfHeight), Ax);
if (TAx > a.halfWidth + WoOxAx + HoOyAx)
return false;
else
return true;
}
private static bool checkAY(AABB a, OBB o)
{
float TAy = Vector2.Dot(T, Ay);
float WoOxAy = Vector2.Dot(Vector2.Multiply(Ox, o.halfWidth), Ay);
float HoOyAy = Vector2.Dot(Vector2.Multiply(Oy, o.halfHeight), Ay);
if (TAy > a.halfHeight + WoOxAy + HoOyAy)
return false;
else
return true;
}
private static bool checkOX(AABB a, OBB o)
{
float TOx = Vector2.Dot(T, Ox);
float WaAxOx = Vector2.Dot(Vector2.Multiply(Ax, a.halfWidth), Ox);
float HaAyOx = Vector2.Dot(Vector2.Multiply(Ay, a.halfHeight), Ox);
if (TOx > o.halfWidth + WaAxOx + HaAyOx)
return false;
else
return true;
}
private static bool checkOY(AABB a, OBB o)
{
float TOy = Vector2.Dot(T, Oy);
float WaAxOy = Vector2.Dot(Vector2.Multiply(Ax, a.halfWidth), Oy);
float HaAyOy = Vector2.Dot(Vector2.Multiply(Ay, a.halfHeight), Oy);
if (TOy > o.halfHeight + WaAxOy + HaAyOy)
return false;
else
return true;
}