91 lines
3.8 KiB
C#
91 lines
3.8 KiB
C#
using System.Diagnostics;
|
|
using System.Drawing;
|
|
using System.Numerics;
|
|
|
|
namespace Dashboard
|
|
{
|
|
[DebuggerDisplay("\\{{Min}; {Max}\\}")]
|
|
public readonly record struct Box2d(Vector2 Min, Vector2 Max)
|
|
{
|
|
public float Left => Min.X;
|
|
public float Top => Min.Y;
|
|
public float Right => Max.X;
|
|
public float Bottom => Max.Y;
|
|
|
|
public Vector2 Size => Max - Min;
|
|
public Vector2 Center => (Min + Max) * 0.5f;
|
|
|
|
public Box2d(RectangleF rectangle)
|
|
: this(new Vector2(rectangle.Left, rectangle.Top), new Vector2(rectangle.Right, rectangle.Bottom))
|
|
{
|
|
}
|
|
|
|
public Box2d(float x0, float y0, float x1, float y1)
|
|
: this(new Vector2(x0, y0), new Vector2(x1, y1))
|
|
{
|
|
}
|
|
|
|
public static Box2d FromPositionAndSize(Vector2 position, Vector2 size, Origin anchor = Origin.Center) =>
|
|
// Hoping the redundent additions+muls become conditional fma instructions.
|
|
anchor switch
|
|
{
|
|
Origin.Left => new Box2d(
|
|
position + (size * new Vector2(0.0f, -0.5f)),
|
|
position + (size * new Vector2(1.0f, 0.5f))
|
|
),
|
|
Origin.TopLeft => new Box2d(position, position + size),
|
|
Origin.Top => new Box2d(
|
|
position + (size * new Vector2(-0.5f, 0f)),
|
|
position + (size * new Vector2(0.5f, 1f))),
|
|
Origin.TopRight => new Box2d(
|
|
position + (size * new Vector2(-1.0f, 0.0f)),
|
|
position + (size * new Vector2(0.0f, 1.0f))
|
|
),
|
|
Origin.Right => new Box2d(
|
|
position + (size * new Vector2(-1.0f, -0.5f)),
|
|
position + (size * new Vector2(0.0f, 0.5f))
|
|
),
|
|
Origin.BottomRight => new Box2d(
|
|
position + (size * new Vector2(-1.0f, -1.0f)),
|
|
position + (size * new Vector2(0.0f, 0.0f))
|
|
),
|
|
Origin.Bottom => new Box2d(
|
|
position + (size * new Vector2(-0.5f, -1.0f)),
|
|
position + (size * new Vector2(0.5f, 0.0f))
|
|
),
|
|
Origin.BottomLeft => new Box2d(
|
|
position + (size * new Vector2(0.0f, -1.0f)),
|
|
position + (size * new Vector2(1.0f, 0.0f))
|
|
),
|
|
Origin.Center => new Box2d(
|
|
position + (size * new Vector2(-0.5f, -0.5f)),
|
|
position + (size * new Vector2(0.5f, 0.5f))),
|
|
_ => throw new ArgumentOutOfRangeException(nameof(anchor)),
|
|
};
|
|
|
|
public static Box2d Union(Box2d left, Box2d right)
|
|
{
|
|
Vector2 min = Vector2.Min(left.Min, right.Min);
|
|
Vector2 max = Vector2.Max(left.Max, right.Max);
|
|
return new Box2d(min, max);
|
|
}
|
|
|
|
public static Box2d Intersect(Box2d left, Box2d right)
|
|
{
|
|
Vector2 min = Vector2.Max(left.Min, right.Min);
|
|
Vector2 max = Vector2.Min(left.Max, right.Max);
|
|
return new Box2d(min, max);
|
|
}
|
|
|
|
public static explicit operator RectangleF(Box2d box2d)
|
|
{
|
|
return new RectangleF((PointF)box2d.Center, (SizeF)box2d.Size);
|
|
}
|
|
|
|
public static explicit operator Box2d(RectangleF rectangle)
|
|
{
|
|
return new Box2d(rectangle);
|
|
}
|
|
}
|
|
}
|