我有一个外部矩形和一个矩形。如何在切割相交的矩形后返回所有剩余的矩形?
答案 0 :(得分:0)
我创建了这个函数,它返回一个不包含相交的List。
private IEnumerable<Rectangle> GetExternalRectangles(Rectangle surface, Rectangle test)
{
var result = new List<Rectangle>();
if (!test.IntersectsWith(surface)) return new List<Rectangle> { surface };
#region Top and Bottom
if (test.Top>surface.Top && test.Bottom < surface.Bottom) // test inside surface vertically
{
result.Add(new Rectangle(surface.Location, new Size(surface.Width, test.Top - surface.Top)));
result.Add(new Rectangle(new Point(surface.Left,test.Bottom), new Size(surface.Width, surface.Bottom-test.Bottom)));
}
if (test.Top > surface.Top && test.Bottom > surface.Bottom) // test inside surface vertically, overflow bottom
{
result.Add(new Rectangle(surface.Location, new Size(surface.Width, test.Top - surface.Top)));
//result.Add(new Rectangle(new Point(surface.Left,test.Bottom), new Size(surface.Width, surface.Bottom-test.Bottom)));
}
if (test.Top < surface.Top && test.Bottom < surface.Bottom) // test inside surface vertically, overflow top
{
//result.Add(new Rectangle(surface.Location, new Size(surface.Width, test.Top - surface.Top)));
result.Add(new Rectangle(new Point(surface.Left, test.Bottom), new Size(surface.Width, surface.Bottom - test.Bottom)));
}
#endregion
#region Lateral
if (test.Left > surface.Left && test.Right < surface.Right) // test inside surface horizontally
{
result.Add(new Rectangle(new Point(surface.Left,Math.Max(surface.Top,test.Top)), new Size(test.Left-surface.Left, Math.Min(surface.Bottom, test.Bottom)- Math.Max(surface.Top, test.Top))));
result.Add(new Rectangle(new Point(test.Right, Math.Max(surface.Top, test.Top)), new Size(surface.Right - test.Right, Math.Min(surface.Bottom, test.Bottom) - Math.Max(surface.Top, test.Top))));
}
if (test.Left > surface.Left && test.Right > surface.Right) // test inside surface horizontally, overflow right
{
result.Add(new Rectangle(new Point(surface.Left, Math.Max(surface.Top, test.Top)), new Size(test.Left - surface.Left, Math.Min(surface.Bottom, test.Bottom) - Math.Max(surface.Top, test.Top))));
//result.Add(new Rectangle(new Point(test.Right, Math.Max(surface.Top, test.Top)), new Size(surface.Right - test.Right, Math.Min(surface.Bottom, test.Bottom) - Math.Max(surface.Top, test.Top))));
}
if (test.Left < surface.Left && test.Right < surface.Right) // test inside surface horizontally, overflow left
{
//result.Add(new Rectangle(new Point(surface.Left, Math.Max(surface.Top, test.Top)), new Size(test.Left - surface.Left, Math.Min(surface.Bottom, test.Bottom) - Math.Max(surface.Top, test.Top))));
result.Add(new Rectangle(new Point(test.Right, Math.Max(surface.Top, test.Top)), new Size(surface.Right - test.Right, Math.Min(surface.Bottom, test.Bottom) - Math.Max(surface.Top, test.Top))));
}
#endregion
return result;
}
答案 1 :(得分:0)
表示这种情况的自然方式是使用Region
class,例如:
var result = new Region(outer);
result.Exclude(inner);
如果您确实需要Rectangle
结构列表,可以使用{1}}使用单位矩阵转换为RectangleF
,然后将其转换为GetRegionScans
s使用Rectangle
或Ceiling
。