// // System.Drawing.Rectangle.cs // // Author: // Mike Kestner (mkestner@speakeasy.net) // // Copyright (C) 2001 Mike Kestner // Copyright (C) 2004 Novell, Inc. http://www.novell.com // using System; namespace Terminal.Gui { /// /// Stores a set of four integers that represent the location and size of a rectangle /// public struct Rect { int width; int height; /// /// Gets or sets the x-coordinate of the upper-left corner of this Rectangle structure. /// public int X; /// /// Gets or sets the y-coordinate of the upper-left corner of this Rectangle structure. /// public int Y; /// /// Gets or sets the width of this Rect structure. /// public int Width { get { return width; } set { if (value < 0) throw new ArgumentException ("Width must be greater or equal to 0."); width = value; } } /// /// Gets or sets the height of this Rectangle structure. /// public int Height { get { return height; } set { if (value < 0) throw new ArgumentException ("Height must be greater or equal to 0."); height = value; } } /// /// Empty Shared Field /// /// /// /// An uninitialized Rectangle Structure. /// public static readonly Rect Empty; /// /// FromLTRB Shared Method /// /// /// /// Produces a Rectangle structure from left, top, right /// and bottom coordinates. /// public static Rect FromLTRB (int left, int top, int right, int bottom) { return new Rect (left, top, right - left, bottom - top); } /// /// Inflate Shared Method /// /// /// /// Produces a new Rectangle by inflating an existing /// Rectangle by the specified coordinate values. /// public static Rect Inflate (Rect rect, int x, int y) { Rect r = new Rect (rect.Location, rect.Size); r.Inflate (x, y); return r; } /// /// Inflate Method /// /// /// /// Inflates the Rectangle by a specified width and height. /// public void Inflate (int width, int height) { Inflate (new Size (width, height)); } /// /// Inflate Method /// /// /// /// Inflates the Rectangle by a specified Size. /// public void Inflate (Size size) { X -= size.Width; Y -= size.Height; Width += size.Width * 2; Height += size.Height * 2; } /// /// Intersect Shared Method /// /// /// /// Produces a new Rectangle by intersecting 2 existing /// Rectangles. Returns null if there is no intersection. /// public static Rect Intersect (Rect a, Rect b) { // MS.NET returns a non-empty rectangle if the two rectangles // touch each other if (!a.IntersectsWithInclusive (b)) return Empty; return Rect.FromLTRB ( Math.Max (a.Left, b.Left), Math.Max (a.Top, b.Top), Math.Min (a.Right, b.Right), Math.Min (a.Bottom, b.Bottom)); } /// /// Intersect Method /// /// /// /// Replaces the Rectangle with the intersection of itself /// and another Rectangle. /// public void Intersect (Rect rect) { this = Rect.Intersect (this, rect); } /// /// Union Shared Method /// /// /// /// Produces a new Rectangle from the union of 2 existing /// Rectangles. /// public static Rect Union (Rect a, Rect b) { return FromLTRB (Math.Min (a.Left, b.Left), Math.Min (a.Top, b.Top), Math.Max (a.Right, b.Right), Math.Max (a.Bottom, b.Bottom)); } /// /// Equality Operator /// /// /// /// Compares two Rectangle objects. The return value is /// based on the equivalence of the Location and Size /// properties of the two Rectangles. /// public static bool operator == (Rect left, Rect right) { return ((left.Location == right.Location) && (left.Size == right.Size)); } /// /// Inequality Operator /// /// /// /// Compares two Rectangle objects. The return value is /// based on the equivalence of the Location and Size /// properties of the two Rectangles. /// public static bool operator != (Rect left, Rect right) { return ((left.Location != right.Location) || (left.Size != right.Size)); } // ----------------------- // Public Constructors // ----------------------- /// /// Rectangle Constructor /// /// /// /// Creates a Rectangle from Point and Size values. /// public Rect (Point location, Size size) { X = location.X; Y = location.Y; width = size.Width; height = size.Height; Width = width; Height = height; } /// /// Rectangle Constructor /// /// /// /// Creates a Rectangle from a specified x,y location and /// width and height values. /// public Rect (int x, int y, int width, int height) { X = x; Y = y; this.width = width; this.height = height; Width = this.width; Height = this.height; } /// /// Bottom Property /// /// /// /// The Y coordinate of the bottom edge of the Rectangle. /// Read only. /// public int Bottom { get { return Y + Height; } } /// /// IsEmpty Property /// /// /// /// Indicates if the width or height are zero. Read only. /// public bool IsEmpty { get { return ((X == 0) && (Y == 0) && (Width == 0) && (Height == 0)); } } /// /// Left Property /// /// /// /// The X coordinate of the left edge of the Rectangle. /// Read only. /// public int Left { get { return X; } } /// /// Location Property /// /// /// /// The Location of the top-left corner of the Rectangle. /// public Point Location { get { return new Point (X, Y); } set { X = value.X; Y = value.Y; } } /// /// Right Property /// /// /// /// The X coordinate of the right edge of the Rectangle. /// Read only. /// public int Right { get { return X + Width; } } /// /// Size Property /// /// /// /// The Size of the Rectangle. /// public Size Size { get { return new Size (Width, Height); } set { Width = value.Width; Height = value.Height; } } /// /// Top Property /// /// /// /// The Y coordinate of the top edge of the Rectangle. /// Read only. /// public int Top { get { return Y; } } /// /// Contains Method /// /// /// /// Checks if an x,y coordinate lies within this Rectangle. /// public bool Contains (int x, int y) { return ((x >= Left) && (x < Right) && (y >= Top) && (y < Bottom)); } /// /// Contains Method /// /// /// /// Checks if a Point lies within this Rectangle. /// public bool Contains (Point pt) { return Contains (pt.X, pt.Y); } /// /// Contains Method /// /// /// /// Checks if a Rectangle lies entirely within this /// Rectangle. /// public bool Contains (Rect rect) { return (rect == Intersect (this, rect)); } /// /// Equals Method /// /// /// /// Checks equivalence of this Rectangle and another object. /// public override bool Equals (object obj) { if (!(obj is Rect)) return false; return (this == (Rect) obj); } /// /// GetHashCode Method /// /// /// /// Calculates a hashing value. /// public override int GetHashCode () { return (Height + Width) ^ X + Y; } /// /// IntersectsWith Method /// /// /// /// Checks if a Rectangle intersects with this one. /// public bool IntersectsWith (Rect rect) { return !((Left >= rect.Right) || (Right <= rect.Left) || (Top >= rect.Bottom) || (Bottom <= rect.Top)); } bool IntersectsWithInclusive (Rect r) { return !((Left > r.Right) || (Right < r.Left) || (Top > r.Bottom) || (Bottom < r.Top)); } /// /// Offset Method /// /// /// /// Moves the Rectangle a specified distance. /// public void Offset (int x, int y) { this.X += x; this.Y += y; } /// /// Offset Method /// /// /// /// Moves the Rectangle a specified distance. /// public void Offset (Point pos) { X += pos.X; Y += pos.Y; } /// /// ToString Method /// /// /// /// Formats the Rectangle as a string in (x,y,w,h) notation. /// public override string ToString () { return String.Format ("{{X={0},Y={1},Width={2},Height={3}}}", X, Y, Width, Height); } } }