| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190 |
- using UnityEngine;
- namespace PF
- {
- /** Integer Rectangle.
- * Works almost like UnityEngine.Rect but with integer coordinates
- */
- [System.Serializable]
- public struct IntRect {
- public int xmin, ymin, xmax, ymax;
- public IntRect (int xmin, int ymin, int xmax, int ymax) {
- this.xmin = xmin;
- this.xmax = xmax;
- this.ymin = ymin;
- this.ymax = ymax;
- }
- public bool Contains (int x, int y) {
- return !(x < xmin || y < ymin || x > xmax || y > ymax);
- }
- public int Width {
- get {
- return xmax-xmin+1;
- }
- }
- public int Height {
- get {
- return ymax-ymin+1;
- }
- }
- /** Returns if this rectangle is valid.
- * An invalid rect could have e.g xmin > xmax.
- * Rectamgles with a zero area area invalid.
- */
- public bool IsValid () {
- return xmin <= xmax && ymin <= ymax;
- }
- public static bool operator == (IntRect a, IntRect b) {
- return a.xmin == b.xmin && a.xmax == b.xmax && a.ymin == b.ymin && a.ymax == b.ymax;
- }
- public static bool operator != (IntRect a, IntRect b) {
- return a.xmin != b.xmin || a.xmax != b.xmax || a.ymin != b.ymin || a.ymax != b.ymax;
- }
- public override bool Equals (System.Object obj) {
- var rect = (IntRect)obj;
- return xmin == rect.xmin && xmax == rect.xmax && ymin == rect.ymin && ymax == rect.ymax;
- }
- public override int GetHashCode () {
- return xmin*131071 ^ xmax*3571 ^ ymin*3109 ^ ymax*7;
- }
- /** Returns the intersection rect between the two rects.
- * The intersection rect is the area which is inside both rects.
- * If the rects do not have an intersection, an invalid rect is returned.
- * \see IsValid
- */
- public static IntRect Intersection (IntRect a, IntRect b) {
- return new IntRect(
- System.Math.Max(a.xmin, b.xmin),
- System.Math.Max(a.ymin, b.ymin),
- System.Math.Min(a.xmax, b.xmax),
- System.Math.Min(a.ymax, b.ymax)
- );
- }
- /** Returns if the two rectangles intersect each other
- */
- public static bool Intersects (IntRect a, IntRect b) {
- return !(a.xmin > b.xmax || a.ymin > b.ymax || a.xmax < b.xmin || a.ymax < b.ymin);
- }
- /** Returns a new rect which contains both input rects.
- * This rectangle may contain areas outside both input rects as well in some cases.
- */
- public static IntRect Union (IntRect a, IntRect b) {
- return new IntRect(
- System.Math.Min(a.xmin, b.xmin),
- System.Math.Min(a.ymin, b.ymin),
- System.Math.Max(a.xmax, b.xmax),
- System.Math.Max(a.ymax, b.ymax)
- );
- }
- /** Returns a new IntRect which is expanded to contain the point */
- public IntRect ExpandToContain (int x, int y) {
- return new IntRect(
- System.Math.Min(xmin, x),
- System.Math.Min(ymin, y),
- System.Math.Max(xmax, x),
- System.Math.Max(ymax, y)
- );
- }
- /** Returns a new rect which is expanded by \a range in all directions.
- * \param range How far to expand. Negative values are permitted.
- */
- public IntRect Expand (int range) {
- return new IntRect(xmin-range,
- ymin-range,
- xmax+range,
- ymax+range
- );
- }
- /** Matrices for rotation.
- * Each group of 4 elements is a 2x2 matrix.
- * The XZ position is multiplied by this.
- * So
- * \code
- * //A rotation by 90 degrees clockwise, second matrix in the array
- * (5,2) * ((0, 1), (-1, 0)) = (2,-5)
- * \endcode
- */
- private static readonly int[] Rotations = {
- 1, 0, //Identity matrix
- 0, 1,
- 0, 1,
- -1, 0,
- -1, 0,
- 0, -1,
- 0, -1,
- 1, 0
- };
- /** Returns a new rect rotated around the origin 90*r degrees.
- * Ensures that a valid rect is returned.
- */
- public IntRect Rotate (int r) {
- int mx1 = Rotations[r*4+0];
- int mx2 = Rotations[r*4+1];
- int my1 = Rotations[r*4+2];
- int my2 = Rotations[r*4+3];
- int p1x = mx1*xmin + mx2*ymin;
- int p1y = my1*xmin + my2*ymin;
- int p2x = mx1*xmax + mx2*ymax;
- int p2y = my1*xmax + my2*ymax;
- return new IntRect(
- System.Math.Min(p1x, p2x),
- System.Math.Min(p1y, p2y),
- System.Math.Max(p1x, p2x),
- System.Math.Max(p1y, p2y)
- );
- }
- /** Returns a new rect which is offset by the specified amount.
- */
- public IntRect Offset (Int2 offset) {
- return new IntRect(xmin+offset.x, ymin + offset.y, xmax + offset.x, ymax + offset.y);
- }
- /** Returns a new rect which is offset by the specified amount.
- */
- public IntRect Offset (int x, int y) {
- return new IntRect(xmin+x, ymin + y, xmax + x, ymax + y);
- }
- public override string ToString () {
- return "[x: "+xmin+"..."+xmax+", y: " + ymin +"..."+ymax+"]";
- }
- #if !SERVER
- /** Draws some debug lines representing the rect */
- public void DebugDraw (GraphTransform transform, UnityEngine.Color color) {
- Vector3 p1 = transform.Transform(new Vector3(xmin, 0, ymin));
- Vector3 p2 = transform.Transform(new Vector3(xmin, 0, ymax));
- Vector3 p3 = transform.Transform(new Vector3(xmax, 0, ymax));
- Vector3 p4 = transform.Transform(new Vector3(xmax, 0, ymin));
- UnityEngine.Debug.DrawLine(p1, p2, color);
- UnityEngine.Debug.DrawLine(p2, p3, color);
- UnityEngine.Debug.DrawLine(p3, p4, color);
- UnityEngine.Debug.DrawLine(p4, p1, color);
- }
- #endif
- }
- }
|