aboutsummaryrefslogtreecommitdiffstats
path: root/src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java')
-rw-r--r--src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java923
1 files changed, 0 insertions, 923 deletions
diff --git a/src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java b/src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java
deleted file mode 100644
index 1720caf0e..000000000
--- a/src/jogl/classes/com/jogamp/opengl/math/geom/AABBox.java
+++ /dev/null
@@ -1,923 +0,0 @@
-/**
- * Copyright 2010-2023 JogAmp Community. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without modification, are
- * permitted provided that the following conditions are met:
- *
- * 1. Redistributions of source code must retain the above copyright notice, this list of
- * conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright notice, this list
- * of conditions and the following disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
- * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * The views and conclusions contained in the software and documentation are those of the
- * authors and should not be interpreted as representing official policies, either expressed
- * or implied, of JogAmp Community.
- */
-package com.jogamp.opengl.math.geom;
-
-import com.jogamp.graph.geom.plane.AffineTransform;
-import com.jogamp.opengl.math.FloatUtil;
-import com.jogamp.opengl.math.Matrix4f;
-import com.jogamp.opengl.math.Quaternion;
-import com.jogamp.opengl.math.Ray;
-import com.jogamp.opengl.math.Recti;
-import com.jogamp.opengl.math.Vec3f;
-import com.jogamp.opengl.util.PMVMatrix;
-
-
-/**
- * Axis Aligned Bounding Box. Defined by two 3D coordinates (low and high)
- * The low being the the lower left corner of the box, and the high being the upper
- * right corner of the box.
- * <p>
- * A few references for collision detection, intersections:
- * <pre>
- * http://www.realtimerendering.com/intersections.html
- * http://www.codercorner.com/RayAABB.cpp
- * http://www.siggraph.org/education/materials/HyperGraph/raytrace/rtinter0.htm
- * http://realtimecollisiondetection.net/files/levine_swept_sat.txt
- * </pre>
- * </p>
- *
- */
-public class AABBox {
- private static final boolean DEBUG = FloatUtil.DEBUG;
- private final Vec3f low = new Vec3f();
- private final Vec3f high = new Vec3f();
- private final Vec3f center = new Vec3f();
-
- /**
- * Create an Axis Aligned bounding box (AABBox) with the
- * inverse low/high, allowing the next {@link #resize(float, float, float)} command to hit.
- * <p>
- * The dimension, i.e. {@link #getWidth()} abd {@link #getHeight()} is {@link Float#isInfinite()} thereafter.
- * </p>
- * @see #reset()
- */
- public AABBox() {
- reset();
- }
-
- /**
- * Create an AABBox copying all values from the given one
- * @param src the box value to be used for the new instance
- */
- public AABBox(final AABBox src) {
- copy(src);
- }
-
- /**
- * Create an AABBox specifying the coordinates
- * of the low and high
- * @param lx min x-coordinate
- * @param ly min y-coordnate
- * @param lz min z-coordinate
- * @param hx max x-coordinate
- * @param hy max y-coordinate
- * @param hz max z-coordinate
- */
- public AABBox(final float lx, final float ly, final float lz,
- final float hx, final float hy, final float hz) {
- setSize(lx, ly, lz, hx, hy, hz);
- }
-
- /**
- * Create a AABBox defining the low and high
- * @param low min xyz-coordinates
- * @param high max xyz-coordinates
- */
- public AABBox(final float[] low, final float[] high) {
- setSize(low, high);
- }
-
- /**
- * Create a AABBox defining the low and high
- * @param low min xyz-coordinates
- * @param high max xyz-coordinates
- */
- public AABBox(final Vec3f low, final Vec3f high) {
- setSize(low, high);
- }
-
- /**
- * Resets this box to the inverse low/high, allowing the next {@link #resize(float, float, float)} command to hit.
- * <p>
- * The dimension, i.e. {@link #getWidth()} abd {@link #getHeight()} is {@link Float#isInfinite()} thereafter.
- * </p>
- * @return this AABBox for chaining
- */
- public final AABBox reset() {
- setLow(Float.MAX_VALUE,Float.MAX_VALUE,Float.MAX_VALUE);
- setHigh(-1*Float.MAX_VALUE,-1*Float.MAX_VALUE,-1*Float.MAX_VALUE);
- center.set( 0f, 0f, 0f);
- return this;
- }
-
- /** Get the max xyz-coordinates
- * @return max xyz coordinates
- */
- public final Vec3f getHigh() {
- return high;
- }
-
- private final void setHigh(final float hx, final float hy, final float hz) {
- this.high.set(hx, hy, hz);
- }
-
- /** Get the min xyz-coordinates
- * @return min xyz coordinates
- */
- public final Vec3f getLow() {
- return low;
- }
-
- private final void setLow(final float lx, final float ly, final float lz) {
- this.low.set(lx, ly, lz);
- }
-
- private final void computeCenter() {
- center.set(high).add(low).scale(1f/2f);
- }
-
- /**
- * Copy given AABBox 'src' values to this AABBox.
- *
- * @param src source AABBox
- * @return this AABBox for chaining
- */
- public final AABBox copy(final AABBox src) {
- low.set(src.low);
- high.set(src.high);
- center.set(src.center);
- return this;
- }
-
- /**
- * Set size of the AABBox specifying the coordinates
- * of the low and high.
- *
- * @param low min xyz-coordinates
- * @param high max xyz-coordinates
- * @return this AABBox for chaining
- */
- public final AABBox setSize(final float[] low, final float[] high) {
- return setSize(low[0],low[1],low[2], high[0],high[1],high[2]);
- }
-
- /**
- * Set size of the AABBox specifying the coordinates
- * of the low and high.
- *
- * @param lx min x-coordinate
- * @param ly min y-coordnate
- * @param lz min z-coordinate
- * @param hx max x-coordinate
- * @param hy max y-coordinate
- * @param hz max z-coordinate
- * @return this AABBox for chaining
- */
- public final AABBox setSize(final float lx, final float ly, final float lz,
- final float hx, final float hy, final float hz) {
- this.low.set(lx, ly, lz);
- this.high.set(hx, hy, hz);
- computeCenter();
- return this;
- }
-
- /**
- * Set size of the AABBox specifying the coordinates
- * of the low and high.
- *
- * @param low min xyz-coordinates
- * @param high max xyz-coordinates
- * @return this AABBox for chaining
- */
- public final AABBox setSize(final Vec3f low, final Vec3f high) {
- this.low.set(low);
- this.high.set(high);
- computeCenter();
- return this;
- }
-
- /**
- * Resize width of this AABBox with explicit left- and right delta values
- * @param deltaLeft positive value will shrink width, otherwise expand width
- * @param deltaRight positive value will expand width, otherwise shrink width
- * @return this AABBox for chaining
- */
- public final AABBox resizeWidth(final float deltaLeft, final float deltaRight) {
- boolean mod = false;
- if( !FloatUtil.isZero(deltaLeft) ) {
- low.setX( low.x() + deltaLeft );
- mod = true;
- }
- if( !FloatUtil.isZero(deltaRight) ) {
- high.setX( high.x() + deltaRight );
- mod = true;
- }
- if( mod ) {
- computeCenter();
- }
- return this;
- }
-
- /**
- * Resize height of this AABBox with explicit bottom- and top delta values
- * @param deltaBottom positive value will shrink height, otherwise expand height
- * @param deltaTop positive value will expand height, otherwise shrink height
- * @return this AABBox for chaining
- */
- public final AABBox resizeHeight(final float deltaBottom, final float deltaTop) {
- boolean mod = false;
- if( !FloatUtil.isZero(deltaBottom) ) {
- low.setY( low.y() + deltaBottom );
- mod = true;
- }
- if( !FloatUtil.isZero(deltaTop) ) {
- high.setY( high.y() + deltaTop );
- mod = true;
- }
- if( mod ) {
- computeCenter();
- }
- return this;
- }
-
- /**
- * Assign values of given AABBox to this instance.
- *
- * @param o source AABBox
- * @return this AABBox for chaining
- */
- public final AABBox set(final AABBox o) {
- this.low.set(o.low);
- this.high.set(o.high);
- this.center.set(o.center);
- return this;
- }
-
- /**
- * Resize the AABBox to encapsulate another AABox
- * @param newBox AABBox to be encapsulated in
- * @return this AABBox for chaining
- */
- public final AABBox resize(final AABBox newBox) {
- final Vec3f newLow = newBox.getLow();
- final Vec3f newHigh = newBox.getHigh();
-
- /** test low */
- if (newLow.x() < low.x()) {
- low.setX( newLow.x() );
- }
- if (newLow.y() < low.y()) {
- low.setY( newLow.y() );
- }
- if (newLow.z() < low.z()) {
- low.setZ( newLow.z() );
- }
-
- /** test high */
- if (newHigh.x() > high.x()) {
- high.setX( newHigh.x() );
- }
- if (newHigh.y() > high.y()) {
- high.setY( newHigh.y() );
- }
- if (newHigh.z() > high.z()) {
- high.setZ( newHigh.z() );
- }
- computeCenter();
- return this;
- }
-
- /**
- * Resize the AABBox to encapsulate another AABox, which will be <i>transformed</i> on the fly first.
- * @param newBox AABBox to be encapsulated in
- * @param t the {@link AffineTransform} applied on <i>newBox</i> on the fly
- * @param tmpV3 temporary storage
- * @return this AABBox for chaining
- */
- public final AABBox resize(final AABBox newBox, final AffineTransform t, final Vec3f tmpV3) {
- /** test low */
- {
- final Vec3f newBoxLow = newBox.getLow();
- t.transform(newBoxLow, tmpV3);
- if (tmpV3.x() < low.x())
- low.setX( tmpV3.x() );
- if (tmpV3.y() < low.y())
- low.setY( tmpV3.y() );
- if (tmpV3.z() < low.z())
- low.setZ( tmpV3.z() );
- }
-
- /** test high */
- {
- final Vec3f newBoxHigh = newBox.getHigh();
- t.transform(newBoxHigh, tmpV3);
- if (tmpV3.x() > high.x())
- high.setX( tmpV3.x() );
- if (tmpV3.y() > high.y())
- high.setY( tmpV3.y() );
- if (tmpV3.z() > high.z())
- high.setZ( tmpV3.z() );
- }
-
- computeCenter();
- return this;
- }
-
- /**
- * Resize the AABBox to encapsulate the passed
- * xyz-coordinates.
- * @param x x-axis coordinate value
- * @param y y-axis coordinate value
- * @param z z-axis coordinate value
- * @return this AABBox for chaining
- */
- public final AABBox resize(final float x, final float y, final float z) {
- /** test low */
- if (x < low.x()) {
- low.setX( x );
- }
- if (y < low.y()) {
- low.setY( y );
- }
- if (z < low.z()) {
- low.setZ( z );
- }
-
- /** test high */
- if (x > high.x()) {
- high.setX( x );
- }
- if (y > high.y()) {
- high.setY( y );
- }
- if (z > high.z()) {
- high.setZ( z );
- }
-
- computeCenter();
- return this;
- }
-
- /**
- * Resize the AABBox to encapsulate the passed
- * xyz-coordinates.
- * @param xyz xyz-axis coordinate values
- * @param offset of the array
- * @return this AABBox for chaining
- */
- public final AABBox resize(final float[] xyz, final int offset) {
- return resize(xyz[0+offset], xyz[1+offset], xyz[2+offset]);
- }
-
- /**
- * Resize the AABBox to encapsulate the passed
- * xyz-coordinates.
- * @param xyz xyz-axis coordinate values
- * @return this AABBox for chaining
- */
- public final AABBox resize(final float[] xyz) {
- return resize(xyz[0], xyz[1], xyz[2]);
- }
-
- /**
- * Resize the AABBox to encapsulate the passed
- * xyz-coordinates.
- * @param xyz xyz-axis coordinate values
- * @return this AABBox for chaining
- */
- public final AABBox resize(final Vec3f xyz) {
- return resize(xyz.x(), xyz.y(), xyz.z());
- }
-
- /**
- * Check if the x & y coordinates are bounded/contained
- * by this AABBox
- * @param x x-axis coordinate value
- * @param y y-axis coordinate value
- * @return true if x belong to (low.x, high.x) and
- * y belong to (low.y, high.y)
- */
- public final boolean contains(final float x, final float y) {
- if(x<low.x() || x>high.x()){
- return false;
- }
- if(y<low.y()|| y>high.y()){
- return false;
- }
- return true;
- }
-
- /**
- * Check if the xyz coordinates are bounded/contained
- * by this AABBox.
- * @param x x-axis coordinate value
- * @param y y-axis coordinate value
- * @param z z-axis coordinate value
- * @return true if x belong to (low.x, high.x) and
- * y belong to (low.y, high.y) and z belong to (low.z, high.z)
- */
- public final boolean contains(final float x, final float y, final float z) {
- if(x<low.x() || x>high.x()){
- return false;
- }
- if(y<low.y()|| y>high.y()){
- return false;
- }
- if(z<low.z() || z>high.z()){
- return false;
- }
- return true;
- }
-
- /**
- * Check if there is a common region between this AABBox and the passed
- * 2D region irrespective of z range
- * @param x lower left x-coord
- * @param y lower left y-coord
- * @param w width
- * @param h hight
- * @return true if this AABBox might have a common region with this 2D region
- */
- public final boolean intersects2DRegion(final float x, final float y, final float w, final float h) {
- if (w <= 0 || h <= 0) {
- return false;
- }
-
- final float _w = getWidth();
- final float _h = getHeight();
- if (_w <= 0 || _h <= 0) {
- return false;
- }
-
- final float x0 = getMinX();
- final float y0 = getMinY();
- return (x >= x0 &&
- y >= y0 &&
- x + w <= x0 + _w &&
- y + h <= y0 + _h);
- }
-
- /**
- * Check if {@link Ray} intersects this bounding box.
- * <p>
- * Versions uses the SAT[1], testing 6 axes.
- * Original code for OBBs from MAGIC.
- * Rewritten for AABBs and reorganized for early exits[2].
- * </p>
- * <pre>
- * [1] SAT = Separating Axis Theorem
- * [2] http://www.codercorner.com/RayAABB.cpp
- * </pre>
- * @param ray
- * @return
- */
- public final boolean intersectsRay(final Ray ray) {
- // diff[XYZ] -> VectorUtil.subVec3(diff, ray.orig, center);
- // ext[XYZ] -> extend VectorUtil.subVec3(ext, high, center);
-
- final float dirX = ray.dir.x();
- final float diffX = ray.orig.x() - center.x();
- final float extX = high.x() - center.x();
- if( Math.abs(diffX) > extX && diffX*dirX >= 0f ) return false;
-
- final float dirY = ray.dir.y();
- final float diffY = ray.orig.y() - center.y();
- final float extY = high.y() - center.y();
- if( Math.abs(diffY) > extY && diffY*dirY >= 0f ) return false;
-
- final float dirZ = ray.dir.z();
- final float diffZ = ray.orig.z() - center.z();
- final float extZ = high.z() - center.z();
- if( Math.abs(diffZ) > extZ && diffZ*dirZ >= 0f ) return false;
-
- final float absDirY = Math.abs(dirY);
- final float absDirZ = Math.abs(dirZ);
-
- float f = dirY * diffZ - dirZ * diffY;
- if( Math.abs(f) > extY*absDirZ + extZ*absDirY ) return false;
-
- final float absDirX = Math.abs(dirX);
-
- f = dirZ * diffX - dirX * diffZ;
- if( Math.abs(f) > extX*absDirZ + extZ*absDirX ) return false;
-
- f = dirX * diffY - dirY * diffX;
- if( Math.abs(f) > extX*absDirY + extY*absDirX ) return false;
-
- return true;
- }
-
- /**
- * Return intersection of a {@link Ray} with this bounding box,
- * or null if none exist.
- * <p>
- * <ul>
- * <li>Original code by Andrew Woo, from "Graphics Gems", Academic Press, 1990 [2]</li>
- * <li>Optimized code by Pierre Terdiman, 2000 (~20-30% faster on my Celeron 500)</li>
- * <li>Epsilon value added by Klaus Hartmann.</li>
- * </ul>
- * </p>
- * <p>
- * Method is based on the requirements:
- * <ul>
- * <li>the integer representation of 0.0f is 0x00000000</li>
- * <li>the sign bit of the float is the most significant one</li>
- * </ul>
- * </p>
- * <p>
- * Report bugs: [email protected] (original author)
- * </p>
- * <pre>
- * [1] http://www.codercorner.com/RayAABB.cpp
- * [2] http://tog.acm.org/resources/GraphicsGems/gems/RayBox.c
- * </pre>
- * @param result vec3
- * @param ray
- * @param epsilon
- * @param assumeIntersection if true, method assumes an intersection, i.e. by pre-checking via {@link #intersectsRay(Ray)}.
- * In this case method will not validate a possible non-intersection and just computes
- * coordinates.
- * @return float[3] result of intersection coordinates, or null if none exists
- */
- public final Vec3f getRayIntersection(final Vec3f result, final Ray ray, final float epsilon,
- final boolean assumeIntersection) {
- final float[] maxT = { -1f, -1f, -1f };
-
- final Vec3f origin = ray.orig;
- final Vec3f dir = ray.dir;
-
- boolean inside = true;
-
- // Find candidate planes.
- for(int i=0; i<3; i++) {
- final float origin_i = origin.get(i);
- final float dir_i = dir.get(i);
- final float low_i = low.get(i);
- final float high_i = high.get(i);
- if(origin_i < low_i) {
- result.set(i, low_i);
- inside = false;
-
- // Calculate T distances to candidate planes
- if( 0 != Float.floatToIntBits(dir_i) ) {
- maxT[i] = (low_i - origin_i) / dir_i;
- }
- } else if(origin_i > high_i) {
- result.set(i, high_i);
- inside = false;
-
- // Calculate T distances to candidate planes
- if( 0 != Float.floatToIntBits(dir_i) ) {
- maxT[i] = (high_i - origin_i) / dir_i;
- }
- }
- }
-
- // Ray origin inside bounding box
- if(inside) {
- result.set(origin);
- return result;
- }
-
- // Get largest of the maxT's for final choice of intersection
- int whichPlane = 0;
- if(maxT[1] > maxT[whichPlane]) { whichPlane = 1; }
- if(maxT[2] > maxT[whichPlane]) { whichPlane = 2; }
-
- if( !assumeIntersection ) {
- // Check final candidate actually inside box
- if( 0 != ( Float.floatToIntBits(maxT[whichPlane]) & 0x80000000 ) ) {
- return null;
- }
-
- /** Use unrolled version below ..
- for(int i=0; i<3; i++) {
- if( i!=whichPlane ) {
- result[i] = origin[i] + maxT[whichPlane] * dir[i];
- if(result[i] < minB[i] - epsilon || result[i] > maxB[i] + epsilon) { return null; }
- // if(result[i] < minB[i] || result[i] > maxB[i] ) { return null; }
- }
- } */
- switch( whichPlane ) {
- case 0:
- result.setY( origin.y() + maxT[whichPlane] * dir.y() );
- if(result.y() < low.y() - epsilon || result.y() > high.y() + epsilon) { return null; }
- result.setZ( origin.z() + maxT[whichPlane] * dir.z() );
- if(result.z() < low.z() - epsilon || result.z() > high.z() + epsilon) { return null; }
- break;
- case 1:
- result.setX( origin.x() + maxT[whichPlane] * dir.x() );
- if(result.x() < low.x() - epsilon || result.x() > high.x() + epsilon) { return null; }
- result.setZ( origin.z() + maxT[whichPlane] * dir.z() );
- if(result.z() < low.z() - epsilon || result.z() > high.z() + epsilon) { return null; }
- break;
- case 2:
- result.setX( origin.x() + maxT[whichPlane] * dir.x() );
- if(result.x() < low.x() - epsilon || result.x() > high.x() + epsilon) { return null; }
- result.setY( origin.y() + maxT[whichPlane] * dir.y() );
- if(result.y() < low.y() - epsilon || result.y() > high.y() + epsilon) { return null; }
- break;
- default:
- throw new InternalError("XXX");
- }
- } else {
- switch( whichPlane ) {
- case 0:
- result.setY( origin.y() + maxT[whichPlane] * dir.y() );
- result.setZ( origin.z() + maxT[whichPlane] * dir.z() );
- break;
- case 1:
- result.setX( origin.x() + maxT[whichPlane] * dir.x() );
- result.setZ( origin.z() + maxT[whichPlane] * dir.z() );
- break;
- case 2:
- result.setX( origin.x() + maxT[whichPlane] * dir.x() );
- result.setY( origin.y() + maxT[whichPlane] * dir.y() );
- break;
- default:
- throw new InternalError("XXX");
- }
- }
- return result; // ray hits box
- }
-
- /**
- * Get the size of this AABBox where the size is represented by the
- * length of the vector between low and high.
- * @return a float representing the size of the AABBox
- */
- public final float getSize() {
- return low.dist(high);
- }
-
- /**
- * Get the Center of this AABBox
- * @return the xyz-coordinates of the center of the AABBox
- */
- public final Vec3f getCenter() {
- return center;
- }
-
- /**
- * Scale this AABBox by a constant around fixed center
- * <p>
- * high and low is recomputed by scaling its distance to fixed center.
- * </p>
- * @param size a constant float value
- * @return this AABBox for chaining
- * @see #scale2(float, float[])
- */
- public final AABBox scale(final float size) {
- final Vec3f tmp = new Vec3f();
- tmp.set(high).sub(center).scale(size);
- high.set(center).add(tmp);
-
- tmp.set(low).sub(center).scale(size);
- low.set(center).add(tmp);
-
- return this;
- }
-
- /**
- * Scale this AABBox by a constant, recomputing center
- * <p>
- * high and low is scaled and center recomputed.
- * </p>
- * @param size a constant float value
- * @return this AABBox for chaining
- * @see #scale(float, float[])
- */
- public final AABBox scale2(final float size) {
- high.scale(size);
- low.scale(size);
- computeCenter();
- return this;
- }
-
- /**
- * Translate this AABBox by a float[3] vector
- * @param dx the translation x-component
- * @param dy the translation y-component
- * @param dz the translation z-component
- * @param t the float[3] translation vector
- * @return this AABBox for chaining
- */
- public final AABBox translate(final float dx, final float dy, final float dz) {
- low.add(dx, dy, dz);
- high.add(dx, dy, dz);
- computeCenter();
- return this;
- }
-
- /**
- * Translate this AABBox by a float[3] vector
- * @param t the float[3] translation vector
- * @return this AABBox for chaining
- */
- public final AABBox translate(final Vec3f t) {
- low.add(t);
- high.add(t);
- computeCenter();
- return this;
- }
-
- /**
- * Rotate this AABBox by a float[3] vector
- * @param quat the {@link Quaternion} used for rotation
- * @return this AABBox for chaining
- */
- public final AABBox rotate(final Quaternion quat) {
- quat.rotateVector(low, low);
- quat.rotateVector(high, high);
- computeCenter();
- return this;
- }
-
- public final float getMinX() {
- return low.x();
- }
-
- public final float getMinY() {
- return low.y();
- }
-
- public final float getMinZ() {
- return low.z();
- }
-
- public final float getMaxX() {
- return high.x();
- }
-
- public final float getMaxY() {
- return high.y();
- }
-
- public final float getMaxZ() {
- return high.z();
- }
-
- public final float getWidth(){
- return high.x() - low.x();
- }
-
- public final float getHeight() {
- return high.y() - low.y();
- }
-
- public final float getDepth() {
- return high.z() - low.z();
- }
-
- /** Returns the volume, i.e. width * height * depth */
- public final float getVolume() {
- return getWidth() * getHeight() * getDepth();
- }
-
- /** Return true if {@link #getVolume()} is {@link FloatUtil#isZero(float)}, considering epsilon. */
- public final boolean hasZeroVolume() {
- return FloatUtil.isZero(getVolume());
- }
-
- /** Returns the assumed 2D area, i.e. width * height while assuming low and high lies on same plane. */
- public final float get2DArea() {
- return getWidth() * getHeight();
- }
-
- /** Return true if {@link #get2DArea()} is {@link FloatUtil#isZero(float)}, considering epsilon. */
- public final boolean hasZero2DArea() {
- return FloatUtil.isZero(get2DArea());
- }
-
- @Override
- public final boolean equals(final Object obj) {
- if( obj == this ) {
- return true;
- }
- if( null == obj || !(obj instanceof AABBox) ) {
- return false;
- }
- final AABBox other = (AABBox) obj;
- return low.isEqual(other.low) && high.isEqual(other.high);
- }
- @Override
- public final int hashCode() {
- throw new InternalError("hashCode not designed");
- }
-
- /**
- * Transform this box using the given {@link Matrix4f} into {@code out}
- * @param mat transformation {@link Matrix4f}
- * @param out the resulting {@link AABBox}
- * @return the resulting {@link AABBox} for chaining
- */
- public AABBox transform(final Matrix4f mat, final AABBox out) {
- final Vec3f tmp = new Vec3f();
- out.reset();
- out.resize( mat.mulVec3f(low, tmp) );
- out.resize( mat.mulVec3f(high, tmp) );
- out.computeCenter();
- return out;
- }
-
- /**
- * Transform this box using the {@link PMVMatrix#getMvMat() modelview} of the given {@link PMVMatrix} into {@code out}
- * @param pmv transformation {@link PMVMatrix}
- * @param out the resulting {@link AABBox}
- * @return the resulting {@link AABBox} for chaining
- */
- public AABBox transformMv(final PMVMatrix pmv, final AABBox out) {
- final Vec3f tmp = new Vec3f();
- out.reset();
- out.resize( pmv.mulMvMatVec3f(low, tmp) );
- out.resize( pmv.mulMvMatVec3f(high, tmp) );
- out.computeCenter();
- return out;
- }
-
- /**
- * Assume this bounding box as being in object space and
- * compute the window bounding box.
- * <p>
- * If <code>useCenterZ</code> is <code>true</code>,
- * only 4 {@link FloatUtil#mapObjToWin(float, float, float, float[], int[], float[], float[], float[]) mapObjToWinCoords}
- * operations are made on points [1..4] using {@link #getCenter()}'s z-value.
- * Otherwise 8 {@link FloatUtil#mapObjToWin(float, float, float, float[], int[], float[], float[], float[]) mapObjToWinCoords}
- * operation on all 8 points are performed.
- * </p>
- * <pre>
- * .z() ------ [4]
- * | |
- * | |
- * .y() ------ [3]
- * </pre>
- * @param mat4PMv [projection] x [modelview] matrix, i.e. P x Mv
- * @param viewport viewport rectangle
- * @param useCenterZ
- * @param vec3Tmp0 3 component vector for temp storage
- * @param vec4Tmp1 4 component vector for temp storage
- * @param vec4Tmp2 4 component vector for temp storage
- * @return
- */
- public AABBox mapToWindow(final AABBox result, final Matrix4f mat4PMv, final Recti viewport, final boolean useCenterZ) {
- final Vec3f tmp = new Vec3f();
- final Vec3f winPos = new Vec3f();
- {
- final float objZ = useCenterZ ? center.z() : getMinZ();
- result.reset();
-
- Matrix4f.mapObjToWin(tmp.set(getMinX(), getMinY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMinX(), getMaxY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMaxX(), getMaxY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMaxX(), getMinY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
- }
-
- if( !useCenterZ ) {
- final float objZ = getMaxZ();
-
- Matrix4f.mapObjToWin(tmp.set(getMinX(), getMinY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMinX(), getMaxY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMaxX(), getMaxY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
-
- Matrix4f.mapObjToWin(tmp.set(getMaxX(), getMinY(), objZ), mat4PMv, viewport, winPos);
- result.resize(winPos);
- }
- if( DEBUG ) {
- System.err.printf("AABBox.mapToWindow: view[%s], this %s -> %s%n", viewport, toString(), result.toString());
- }
- return result;
- }
-
- @Override
- public final String toString() {
- return "[dim "+getWidth()+" x "+getHeight()+" x "+getDepth()+
- ", box "+low+" .. "+high+", ctr "+center+"]";
- }
-}