// Copyright (c) 2015, Google Inc. Please see the AUTHORS file for details.
// All rights reserved. Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

part of vector_math_64;

/// Defines a 3-dimensional axis-aligned bounding box between a [min] and a
/// [max] position.
class Aabb3 {
  final Vector3 _min;
  final Vector3 _max;

  Vector3 get min => _min;
  Vector3 get max => _max;

  /// The center of the AABB.
  Vector3 get center => _min.clone()
    ..add(_max)
    ..scale(0.5);

  /// Create a new AABB with [min] and [max] set to the origin.
  Aabb3()
      : _min = new Vector3.zero(),
        _max = new Vector3.zero();

  /// Create a new AABB as a copy of [other].
  Aabb3.copy(Aabb3 other)
      : _min = new Vector3.copy(other._min),
        _max = new Vector3.copy(other._max);

  /// Create a new AABB with a [min] and [max].
  Aabb3.minMax(Vector3 min, Vector3 max)
      : _min = new Vector3.copy(min),
        _max = new Vector3.copy(max);

  /// Create a new AABB that encloses a [sphere].
  factory Aabb3.fromSphere(Sphere sphere) => new Aabb3()..setSphere(sphere);

  /// Create a new AABB that encloses a [triangle].
  factory Aabb3.fromTriangle(Triangle triangle) =>
      new Aabb3()..setTriangle(triangle);

  /// Create a new AABB that encloses a [quad].
  factory Aabb3.fromQuad(Quad quad) => new Aabb3()..setQuad(quad);

  /// Create a new AABB that encloses a [obb].
  factory Aabb3.fromObb3(Obb3 obb) => new Aabb3()..setObb3(obb);

  /// Create a new AABB that encloses a limited [ray] (or line segment) that has
  /// a minLimit and maxLimit.
  factory Aabb3.fromRay(Ray ray, double limitMin, double limitMax) =>
      new Aabb3()..setRay(ray, limitMin, limitMax);

  /// Create a new AABB with a [center] and [halfExtents].
  factory Aabb3.centerAndHalfExtents(Vector3 center, Vector3 halfExtents) =>
      new Aabb3()..setCenterAndHalfExtents(center, halfExtents);

  /// Constructs [Aabb3] with a min/max [storage] that views given [buffer]
  /// starting at [offset]. [offset] has to be multiple of
  /// [Float64List.bytesPerElement].
  Aabb3.fromBuffer(ByteBuffer buffer, int offset)
      : _min = new Vector3.fromBuffer(buffer, offset),
        _max = new Vector3.fromBuffer(
            buffer, offset + Float64List.bytesPerElement * 3);

  /// Set the AABB by a [center] and [halfExtents].
  void setCenterAndHalfExtents(Vector3 center, Vector3 halfExtents) {
    _min
      ..setFrom(center)
      ..sub(halfExtents);
    _max
      ..setFrom(center)
      ..add(halfExtents);
  }

  /// Set the AABB to enclose a [sphere].
  void setSphere(Sphere sphere) {
    _min
      ..splat(-sphere._radius)
      ..add(sphere._center);
    _max
      ..splat(sphere._radius)
      ..add(sphere._center);
  }

  /// Set the AABB to enclose a [triangle].
  void setTriangle(Triangle triangle) {
    _min.setValues(
        math.min(triangle._point0.x,
            math.min(triangle._point1.x, triangle._point2.x)),
        math.min(triangle._point0.y,
            math.min(triangle._point1.y, triangle._point2.y)),
        math.min(triangle._point0.z,
            math.min(triangle._point1.z, triangle._point2.z)));
    _max.setValues(
        math.max(triangle._point0.x,
            math.max(triangle._point1.x, triangle._point2.x)),
        math.max(triangle._point0.y,
            math.max(triangle._point1.y, triangle._point2.y)),
        math.max(triangle._point0.z,
            math.max(triangle._point1.z, triangle._point2.z)));
  }

  /// Set the AABB to enclose a [quad].
  void setQuad(Quad quad) {
    _min.setValues(
        math.min(quad._point0.x,
            math.min(quad._point1.x, math.min(quad._point2.x, quad._point3.x))),
        math.min(quad._point0.y,
            math.min(quad._point1.y, math.min(quad._point2.y, quad._point3.y))),
        math.min(
            quad._point0.z,
            math.min(
                quad._point1.z, math.min(quad._point2.z, quad._point3.z))));
    _max.setValues(
        math.max(quad._point0.x,
            math.max(quad._point1.x, math.max(quad._point2.x, quad._point3.x))),
        math.max(quad._point0.y,
            math.max(quad._point1.y, math.max(quad._point2.y, quad._point3.y))),
        math.max(
            quad._point0.z,
            math.max(
                quad._point1.z, math.max(quad._point2.z, quad._point3.z))));
  }

  /// Set the AABB to enclose a [obb].
  void setObb3(Obb3 obb) {
    final Vector3 corner = new Vector3.zero();

    obb.copyCorner(0, corner);
    _min.setFrom(corner);
    _max.setFrom(corner);

    obb.copyCorner(1, corner);
    hullPoint(corner);

    obb.copyCorner(2, corner);
    hullPoint(corner);

    obb.copyCorner(3, corner);
    hullPoint(corner);

    obb.copyCorner(4, corner);
    hullPoint(corner);

    obb.copyCorner(5, corner);
    hullPoint(corner);

    obb.copyCorner(6, corner);
    hullPoint(corner);

    obb.copyCorner(7, corner);
    hullPoint(corner);
  }

  /// Set the AABB to enclose a limited [ray] (or line segment) that is limited
  /// by [limitMin] and [limitMax].
  void setRay(Ray ray, double limitMin, double limitMax) {
    ray..copyAt(_min, limitMin)..copyAt(_max, limitMax);

    if (_max.x < _min.x) {
      final double temp = _max.x;
      _max.x = _min.x;
      _min.x = temp;
    }

    if (_max.y < _min.y) {
      final double temp = _max.y;
      _max.y = _min.y;
      _min.y = temp;
    }

    if (_max.z < _min.z) {
      final double temp = _max.z;
      _max.z = _min.z;
      _min.z = temp;
    }
  }

  /// Copy the [center] and the [halfExtends] of [this].
  void copyCenterAndHalfExtents(Vector3 center, Vector3 halfExtents) {
    center
      ..setFrom(_min)
      ..add(_max)
      ..scale(0.5);
    halfExtents
      ..setFrom(_max)
      ..sub(_min)
      ..scale(0.5);
  }

  /// Copy the [center] of [this].
  void copyCenter(Vector3 center) {
    center
      ..setFrom(_min)
      ..add(_max)
      ..scale(0.5);
  }

  /// Copy the [min] and [max] from [other] into [this].
  void copyFrom(Aabb3 other) {
    _min.setFrom(other._min);
    _max.setFrom(other._max);
  }

  /// Transform [this] by the transform [t].
  void transform(Matrix4 t) {
    final Vector3 center = new Vector3.zero();
    final Vector3 halfExtents = new Vector3.zero();
    copyCenterAndHalfExtents(center, halfExtents);
    t
      ..transform3(center)
      ..absoluteRotate(halfExtents);
    _min
      ..setFrom(center)
      ..sub(halfExtents);
    _max
      ..setFrom(center)
      ..add(halfExtents);
  }

  /// Rotate [this] by the rotation matrix [t].
  void rotate(Matrix4 t) {
    final Vector3 center = new Vector3.zero();
    final Vector3 halfExtents = new Vector3.zero();
    copyCenterAndHalfExtents(center, halfExtents);
    t.absoluteRotate(halfExtents);
    _min
      ..setFrom(center)
      ..sub(halfExtents);
    _max
      ..setFrom(center)
      ..add(halfExtents);
  }

  /// Create a copy of [this] that is transformed by the transform [t] and store
  /// it in [out].
  Aabb3 transformed(Matrix4 t, Aabb3 out) => out
    ..copyFrom(this)
    ..transform(t);

  /// Create a copy of [this] that is rotated by the rotation matrix [t] and
  /// store it in [out].
  Aabb3 rotated(Matrix4 t, Aabb3 out) => out
    ..copyFrom(this)
    ..rotate(t);

  void getPN(Vector3 planeNormal, Vector3 outP, Vector3 outN) {
    if (planeNormal.x < 0.0) {
      outP.x = _min.x;
      outN.x = _max.x;
    } else {
      outP.x = _max.x;
      outN.x = _min.x;
    }

    if (planeNormal.y < 0.0) {
      outP.y = _min.y;
      outN.y = _max.y;
    } else {
      outP.y = _max.y;
      outN.y = _min.y;
    }

    if (planeNormal.z < 0.0) {
      outP.z = _min.z;
      outN.z = _max.z;
    } else {
      outP.z = _max.z;
      outN.z = _min.z;
    }
  }

  /// Set the min and max of [this] so that [this] is a hull of [this] and
  /// [other].
  void hull(Aabb3 other) {
    Vector3.min(_min, other._min, _min);
    Vector3.max(_max, other._max, _max);
  }

  /// Set the min and max of [this] so that [this] contains [point].
  void hullPoint(Vector3 point) {
    Vector3.min(_min, point, _min);
    Vector3.max(_max, point, _max);
  }

  /// Return if [this] contains [other].
  bool containsAabb3(Aabb3 other) {
    final Vector3 otherMax = other._max;
    final Vector3 otherMin = other._min;

    return (_min.x < otherMin.x) &&
        (_min.y < otherMin.y) &&
        (_min.z < otherMin.z) &&
        (_max.x > otherMax.x) &&
        (_max.y > otherMax.y) &&
        (_max.z > otherMax.z);
  }

  /// Return if [this] contains [other].
  bool containsSphere(Sphere other) {
    final Vector3 boxExtends = new Vector3.all(other._radius);
    final Aabb3 sphereBox =
        new Aabb3.centerAndHalfExtents(other._center, boxExtends);

    return containsAabb3(sphereBox);
  }

  /// Return if [this] contains [other].
  bool containsVector3(Vector3 other) =>
      (_min.x < other.x) &&
      (_min.y < other.y) &&
      (_min.z < other.z) &&
      (_max.x > other.x) &&
      (_max.y > other.y) &&
      (_max.z > other.z);

  /// Return if [this] contains [other].
  bool containsTriangle(Triangle other) =>
      containsVector3(other._point0) &&
      containsVector3(other._point1) &&
      containsVector3(other._point2);

  /// Return if [this] intersects with [other].
  bool intersectsWithAabb3(Aabb3 other) {
    final Vector3 otherMax = other._max;
    final Vector3 otherMin = other._min;

    return (_min.x <= otherMax.x) &&
        (_min.y <= otherMax.y) &&
        (_min.z <= otherMax.z) &&
        (_max.x >= otherMin.x) &&
        (_max.y >= otherMin.y) &&
        (_max.z >= otherMin.z);
  }

  /// Return if [this] intersects with [other].
  bool intersectsWithSphere(Sphere other) {
    final Vector3 center = other._center;
    final double radius = other._radius;
    double d = 0.0;
    double e = 0.0;

    for (int i = 0; i < 3; ++i) {
      if ((e = center[i] - _min[i]) < 0.0) {
        if (e < -radius) {
          return false;
        }

        d = d + e * e;
      } else {
        if ((e = center[i] - _max[i]) > 0.0) {
          if (e > radius) {
            return false;
          }

          d = d + e * e;
        }
      }
    }

    return d <= radius * radius;
  }

  /// Return if [this] intersects with [other].
  bool intersectsWithVector3(Vector3 other) =>
      (_min.x <= other.x) &&
      (_min.y <= other.y) &&
      (_min.z <= other.z) &&
      (_max.x >= other.x) &&
      (_max.y >= other.y) &&
      (_max.z >= other.z);

  // Avoid allocating these instance on every call to intersectsWithTriangle
  static final Vector3 _aabbCenter = new Vector3.zero();
  static final Vector3 _aabbHalfExtents = new Vector3.zero();
  static final Vector3 _v0 = new Vector3.zero();
  static final Vector3 _v1 = new Vector3.zero();
  static final Vector3 _v2 = new Vector3.zero();
  static final Vector3 _f0 = new Vector3.zero();
  static final Vector3 _f1 = new Vector3.zero();
  static final Vector3 _f2 = new Vector3.zero();
  static final Plane _trianglePlane = new Plane();

  static final Vector3 _u0 = new Vector3(1.0, 0.0, 0.0);
  static final Vector3 _u1 = new Vector3(0.0, 1.0, 0.0);
  static final Vector3 _u2 = new Vector3(0.0, 0.0, 1.0);

  /// Return if [this] intersects with [other].
  /// [epsilon] allows the caller to specify a custum eplsilon value that should
  /// be used for the test. If [result] is specified and an intersection is
  /// found, result is modified to contain more details about the type of
  /// intersection.
  bool intersectsWithTriangle(Triangle other,
      {double epsilon: 1e-3, IntersectionResult result}) {
    double p0, p1, p2, r, len;
    double a;

    // This line isn't required if we are using center and half extents to
    // define a aabb
    copyCenterAndHalfExtents(_aabbCenter, _aabbHalfExtents);

    // Translate triangle as conceptually moving AABB to origin
    _v0
      ..setFrom(other.point0)
      ..sub(_aabbCenter);
    _v1
      ..setFrom(other.point1)
      ..sub(_aabbCenter);
    _v2
      ..setFrom(other.point2)
      ..sub(_aabbCenter);

    // Translate triangle as conceptually moving AABB to origin
    _f0
      ..setFrom(_v1)
      ..sub(_v0);
    _f1
      ..setFrom(_v2)
      ..sub(_v1);
    _f2
      ..setFrom(_v0)
      ..sub(_v2);

    // Test axes a00..a22 (category 3)
    // Test axis a00
    len = _f0.y * _f0.y + _f0.z * _f0.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.z * _f0.y - _v0.y * _f0.z;
      p2 = _v2.z * _f0.y - _v2.y * _f0.z;
      r = _aabbHalfExtents[1] * _f0.z.abs() + _aabbHalfExtents[2] * _f0.y.abs();
      if (math.max(-math.max(p0, p2), math.min(p0, p2)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p2) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u0.crossInto(_f0, result.axis);
      }
    }

    // Test axis a01
    len = _f1.y * _f1.y + _f1.z * _f1.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.z * _f1.y - _v0.y * _f1.z;
      p1 = _v1.z * _f1.y - _v1.y * _f1.z;
      r = _aabbHalfExtents[1] * _f1.z.abs() + _aabbHalfExtents[2] * _f1.y.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u0.crossInto(_f1, result.axis);
      }
    }

    // Test axis a02
    len = _f2.y * _f2.y + _f2.z * _f2.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.z * _f2.y - _v0.y * _f2.z;
      p1 = _v1.z * _f2.y - _v1.y * _f2.z;
      r = _aabbHalfExtents[1] * _f2.z.abs() + _aabbHalfExtents[2] * _f2.y.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u0.crossInto(_f2, result.axis);
      }
    }

    // Test axis a10
    len = _f0.x * _f0.x + _f0.z * _f0.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.x * _f0.z - _v0.z * _f0.x;
      p2 = _v2.x * _f0.z - _v2.z * _f0.x;
      r = _aabbHalfExtents[0] * _f0.z.abs() + _aabbHalfExtents[2] * _f0.x.abs();
      if (math.max(-math.max(p0, p2), math.min(p0, p2)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p2) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u1.crossInto(_f0, result.axis);
      }
    }

    // Test axis a11
    len = _f1.x * _f1.x + _f1.z * _f1.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.x * _f1.z - _v0.z * _f1.x;
      p1 = _v1.x * _f1.z - _v1.z * _f1.x;
      r = _aabbHalfExtents[0] * _f1.z.abs() + _aabbHalfExtents[2] * _f1.x.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u1.crossInto(_f1, result.axis);
      }
    }

    // Test axis a12
    len = _f2.x * _f2.x + _f2.z * _f2.z;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.x * _f2.z - _v0.z * _f2.x;
      p1 = _v1.x * _f2.z - _v1.z * _f2.x;
      r = _aabbHalfExtents[0] * _f2.z.abs() + _aabbHalfExtents[2] * _f2.x.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u1.crossInto(_f2, result.axis);
      }
    }

    // Test axis a20
    len = _f0.x * _f0.x + _f0.y * _f0.y;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.y * _f0.x - _v0.x * _f0.y;
      p2 = _v2.y * _f0.x - _v2.x * _f0.y;
      r = _aabbHalfExtents[0] * _f0.y.abs() + _aabbHalfExtents[1] * _f0.x.abs();
      if (math.max(-math.max(p0, p2), math.min(p0, p2)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p2) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u2.crossInto(_f0, result.axis);
      }
    }

    // Test axis a21
    len = _f1.x * _f1.x + _f1.y * _f1.y;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.y * _f1.x - _v0.x * _f1.y;
      p1 = _v1.y * _f1.x - _v1.x * _f1.y;
      r = _aabbHalfExtents[0] * _f1.y.abs() + _aabbHalfExtents[1] * _f1.x.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u2.crossInto(_f1, result.axis);
      }
    }

    // Test axis a22
    len = _f2.x * _f2.x + _f2.y * _f2.y;
    if (len > epsilon) {
      // Ignore tests on degenerate axes.
      p0 = _v0.y * _f2.x - _v0.x * _f2.y;
      p1 = _v1.y * _f2.x - _v1.x * _f2.y;
      r = _aabbHalfExtents[0] * _f2.y.abs() + _aabbHalfExtents[1] * _f2.x.abs();
      if (math.max(-math.max(p0, p1), math.min(p0, p1)) > r + epsilon) {
        return false; // Axis is a separating axis
      }

      a = math.min(p0, p1) - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        _u2.crossInto(_f2, result.axis);
      }
    }

    // Test the three axes corresponding to the face normals of AABB b (category 1). // Exit if...
    // ... [-e0, e0] and [min(v0.x,v1.x,v2.x), max(v0.x,v1.x,v2.x)] do not overlap
    if (math.max(_v0.x, math.max(_v1.x, _v2.x)) < -_aabbHalfExtents[0] ||
        math.min(_v0.x, math.min(_v1.x, _v2.x)) > _aabbHalfExtents[0]) {
      return false;
    }
    a = math.min(_v0.x, math.min(_v1.x, _v2.x)) - _aabbHalfExtents[0];
    if (result != null && (result._depth == null || result._depth < a)) {
      result._depth = a;
      result.axis.setFrom(_u0);
    }
    // ... [-e1, e1] and [min(v0.y,v1.y,v2.y), max(v0.y,v1.y,v2.y)] do not overlap
    if (math.max(_v0.y, math.max(_v1.y, _v2.y)) < -_aabbHalfExtents[1] ||
        math.min(_v0.y, math.min(_v1.y, _v2.y)) > _aabbHalfExtents[1]) {
      return false;
    }
    a = math.min(_v0.y, math.min(_v1.y, _v2.y)) - _aabbHalfExtents[1];
    if (result != null && (result._depth == null || result._depth < a)) {
      result._depth = a;
      result.axis.setFrom(_u1);
    }
    // ... [-e2, e2] and [min(v0.z,v1.z,v2.z), max(v0.z,v1.z,v2.z)] do not overlap
    if (math.max(_v0.z, math.max(_v1.z, _v2.z)) < -_aabbHalfExtents[2] ||
        math.min(_v0.z, math.min(_v1.z, _v2.z)) > _aabbHalfExtents[2]) {
      return false;
    }
    a = math.min(_v0.z, math.min(_v1.z, _v2.z)) - _aabbHalfExtents[2];
    if (result != null && (result._depth == null || result._depth < a)) {
      result._depth = a;
      result.axis.setFrom(_u2);
    }

    // It seems like that wee need to move the edges before creating the
    // plane
    _v0.add(_aabbCenter);

    // Test separating axis corresponding to triangle face normal (category 2)
    _f0.crossInto(_f1, _trianglePlane.normal);
    _trianglePlane.constant = _trianglePlane.normal.dot(_v0);
    return intersectsWithPlane(_trianglePlane, result: result);
  }

  /// Return if [this] intersects with [other]
  bool intersectsWithPlane(Plane other, {IntersectionResult result}) {
    // This line is not necessary with a (center, extents) AABB representation
    copyCenterAndHalfExtents(_aabbCenter, _aabbHalfExtents);

    // Compute the projection interval radius of b onto L(t) = b.c + t * p.n
    final double r = _aabbHalfExtents[0] * other.normal[0].abs() +
        _aabbHalfExtents[1] * other.normal[1].abs() +
        _aabbHalfExtents[2] * other.normal[2].abs();
    // Compute distance of box center from plane
    final double s = other.normal.dot(_aabbCenter) - other.constant;
    // Intersection occurs when distance s falls within [-r,+r] interval
    if (s.abs() <= r) {
      final double a = s - r;
      if (result != null && (result._depth == null || result._depth < a)) {
        result._depth = a;
        result.axis.setFrom(other.normal);
      }
      return true;
    }

    return false;
  }

  // Avoid allocating these instance on every call to intersectsWithTriangle
  static final Triangle _quadTriangle0 = new Triangle();
  static final Triangle _quadTriangle1 = new Triangle();

  /// Return if [this] intersects with [other].
  /// [epsilon] allows the caller to specify a custum eplsilon value that should
  /// be used for the test. If [result] is specified and an intersection is
  /// found, result is modified to contain more details about the type of
  /// intersection.
  bool intersectsWithQuad(Quad other, {IntersectionResult result}) {
    other.copyTriangles(_quadTriangle0, _quadTriangle1);

    return intersectsWithTriangle(_quadTriangle0, result: result) ||
        intersectsWithTriangle(_quadTriangle1, result: result);
  }
}
