📄 boundingbox.java
字号:
/* * $RCSfile: BoundingBox.java,v $ * * Copyright (c) 2007 Sun Microsystems, Inc. All rights reserved. * * Use is subject to license terms. * * $Revision: 1.8 $ * $Date: 2007/04/12 17:34:04 $ * $State: Exp $ */package javax.media.j3d;import javax.vecmath.*;import com.sun.j3d.internal.HashCodeUtil;/** * This class defines an axis aligned bounding box which is used for * bounding regions. * */public class BoundingBox extends Bounds { /** * The corner of the bounding box with the numerically smallest * values. */ Point3d lower; /** * The corner of the bounding box with the numerically largest * values. */ Point3d upper; private Point3d centroid = null; private static final double EPS = 1.0E-8; // reusable temp objects private BoundingSphere tmpSphere = null; private BoundingBox tmpBox = null; private BoundingPolytope tmpPolytope = null; private Point3d tmpP3d = new Point3d(); /** * Constructs and initializes a BoundingBox given min,max in x,y,z. * @param lower the "small" corner * @param upper the "large" corner */ public BoundingBox(Point3d lower, Point3d upper) { boundId = BOUNDING_BOX; this.lower = new Point3d(lower); this.upper = new Point3d(upper); updateBoundsStates(); } /** * Constructs and initializes a 2X bounding box about the * origin. The lower corner is initialized to (-1.0d, -1.0d, -1.0d) * and the opper corner is initialized to (1.0d, 1.0d, 1.0d). */ public BoundingBox() { boundId = BOUNDING_BOX; lower = new Point3d(-1.0d, -1.0d, -1.0d); upper = new Point3d( 1.0d, 1.0d, 1.0d); updateBoundsStates(); } /** * Constructs a BoundingBox from a bounding object. * @param boundsObject a bounds object */ public BoundingBox(Bounds boundsObject) { int i; boundId = BOUNDING_BOX; if( boundsObject == null ) { // Negative volume. lower = new Point3d( 1.0d, 1.0d, 1.0d); upper = new Point3d(-1.0d, -1.0d, -1.0d); } else if( boundsObject.boundsIsInfinite ) { lower = new Point3d( Double.NEGATIVE_INFINITY, Double.NEGATIVE_INFINITY, Double.NEGATIVE_INFINITY); upper = new Point3d(Double.POSITIVE_INFINITY, Double.POSITIVE_INFINITY, Double.POSITIVE_INFINITY); } else if( boundsObject.boundId == BOUNDING_BOX){ BoundingBox box = (BoundingBox)boundsObject; lower = new Point3d(box.lower.x, box.lower.y, box.lower.z); upper = new Point3d(box.upper.x, box.upper.y, box.upper.z); } else if( boundsObject.boundId == BOUNDING_SPHERE ) { BoundingSphere sphere = (BoundingSphere)boundsObject; lower = new Point3d(sphere.center.x-sphere.radius, sphere.center.y-sphere.radius, sphere.center.z-sphere.radius); upper = new Point3d(sphere.center.x+sphere.radius, sphere.center.y+sphere.radius, sphere.center.z+sphere.radius); } else if(boundsObject.boundId == BOUNDING_POLYTOPE) { BoundingPolytope polytope = (BoundingPolytope)boundsObject; if( polytope.nVerts < 1 ) { // handle degenerate case lower = new Point3d(-1.0d, -1.0d, -1.0d); upper = new Point3d( 1.0d, 1.0d, 1.0d); } else { lower = new Point3d( polytope.verts[0].x, polytope.verts[0].y, polytope.verts[0].z); upper = new Point3d( polytope.verts[0].x, polytope.verts[0].y, polytope.verts[0].z); for(i=1;i<polytope.nVerts;i++) { if( polytope.verts[i].x < lower.x ) lower.x = polytope.verts[i].x; if( polytope.verts[i].y < lower.y ) lower.y = polytope.verts[i].y; if( polytope.verts[i].z < lower.z ) lower.z = polytope.verts[i].z; if( polytope.verts[i].x > upper.x ) upper.x = polytope.verts[i].x; if( polytope.verts[i].y > upper.y ) upper.y = polytope.verts[i].y; if( polytope.verts[i].z > upper.z ) upper.z = polytope.verts[i].z; } } } else { throw new IllegalArgumentException(J3dI18N.getString("BoundingBox0")); } updateBoundsStates(); } /** * Constructs a BoundingBox from an array of bounding objects. * @param bounds an array of bounding objects */ public BoundingBox(Bounds[] bounds) { int i=0; upper = new Point3d(); lower = new Point3d(); boundId = BOUNDING_BOX; if( bounds == null || bounds.length <= 0 ) { // Negative volume. lower = new Point3d( 1.0d, 1.0d, 1.0d); upper = new Point3d(-1.0d, -1.0d, -1.0d); updateBoundsStates(); return; } // find first non empty bounds object while( bounds[i] == null && i < bounds.length) { i++; } if( i >= bounds.length ) { // all bounds objects were empty // Negative volume. lower = new Point3d( 1.0d, 1.0d, 1.0d); upper = new Point3d(-1.0d, -1.0d, -1.0d); updateBoundsStates(); return; } this.set(bounds[i++]); if(boundsIsInfinite) return; for(;i<bounds.length;i++) { if( bounds[i] == null ); // do nothing else if( bounds[i].boundsIsEmpty); // do nothing else if( bounds[i].boundsIsInfinite ) { lower.x = lower.y = lower.z = Double.NEGATIVE_INFINITY; upper.x = upper.y = upper.z = Double.POSITIVE_INFINITY; break; // We're done. } else if(bounds[i].boundId == BOUNDING_BOX){ BoundingBox box = (BoundingBox)bounds[i]; if( lower.x > box.lower.x) lower.x = box.lower.x; if( lower.y > box.lower.y) lower.y = box.lower.y; if( lower.z > box.lower.z) lower.z = box.lower.z; if( upper.x < box.upper.x) upper.x = box.upper.x; if( upper.y < box.upper.y) upper.y = box.upper.y; if( upper.z < box.upper.z) upper.z = box.upper.z; } else if(bounds[i].boundId == BOUNDING_SPHERE) { BoundingSphere sphere = (BoundingSphere)bounds[i]; if( lower.x > (sphere.center.x - sphere.radius)) lower.x = sphere.center.x - sphere.radius; if( lower.y > (sphere.center.y - sphere.radius)) lower.y = sphere.center.y - sphere.radius; if( lower.z > (sphere.center.z - sphere.radius)) lower.z = sphere.center.z - sphere.radius; if( upper.x < (sphere.center.x + sphere.radius)) upper.x = sphere.center.x + sphere.radius; if( upper.y < (sphere.center.y + sphere.radius)) upper.y = sphere.center.y + sphere.radius; if( upper.z < (sphere.center.z + sphere.radius)) upper.z = sphere.center.z + sphere.radius; } else if(bounds[i].boundId == BOUNDING_POLYTOPE) { BoundingPolytope polytope = (BoundingPolytope)bounds[i]; for(i=0;i<polytope.nVerts;i++) { // XXXX: handle polytope with no verts if( polytope.verts[i].x < lower.x ) lower.x = polytope.verts[i].x; if( polytope.verts[i].y < lower.y ) lower.y = polytope.verts[i].y; if( polytope.verts[i].z < lower.z ) lower.z = polytope.verts[i].z; if( polytope.verts[i].x > upper.x ) upper.x = polytope.verts[i].x; if( polytope.verts[i].y > upper.y ) upper.y = polytope.verts[i].y; if( polytope.verts[i].z > upper.z ) upper.z = polytope.verts[i].z; } } else { throw new IllegalArgumentException(J3dI18N.getString("BoundingBox1")); } } updateBoundsStates(); } /** * Gets the lower corner of this bounding box. * @param p1 a Point to receive the lower corner of the bounding box */ public void getLower(Point3d p1) { p1.x = lower.x; p1.y = lower.y; p1.z = lower.z; } /** * Sets the lower corner of this bounding box. * @param xmin minimum x value of boundining box * @param ymin minimum y value of boundining box * @param zmin minimum z value of boundining box */ public void setLower(double xmin, double ymin, double zmin ) { lower.x = xmin; lower.y = ymin; lower.z = zmin; updateBoundsStates(); } /** * Sets the lower corner of this bounding box. * @param p1 a Point defining the new lower corner of the bounding box */ public void setLower(Point3d p1) { lower.x = p1.x; lower.y = p1.y; lower.z = p1.z; updateBoundsStates(); } /** * Gets the upper corner of this bounding box. * @param p1 a Point to receive the upper corner of the bounding box */ public void getUpper(Point3d p1) { p1.x = upper.x; p1.y = upper.y; p1.z = upper.z; } /** * Sets the upper corner of this bounding box. * @param xmax max x value of boundining box * @param ymax max y value of boundining box * @param zmax max z value of boundining box */ public void setUpper(double xmax, double ymax, double zmax ) { upper.x = xmax; upper.y = ymax; upper.z = zmax; updateBoundsStates(); } /** * Sets the upper corner of this bounding box. * @param p1 a Point defining the new upper corner of the bounding box */ public void setUpper(Point3d p1) { upper.x = p1.x; upper.y = p1.y; upper.z = p1.z; updateBoundsStates(); } /** * Sets the the value of this BoundingBox * @param boundsObject another bounds object */ public void set(Bounds boundsObject) { int i; if(( boundsObject == null ) ||( boundsObject.boundsIsEmpty)) { // Negative volume. lower.x = lower.y = lower.z = 1.0d; upper.x = upper.y = upper.z = -1.0d; } else if( boundsObject.boundsIsInfinite ) { lower.x = lower.y = lower.z = Double.NEGATIVE_INFINITY; upper.x = upper.y = upper.z = Double.POSITIVE_INFINITY; } else if( boundsObject.boundId == BOUNDING_BOX){ BoundingBox box = (BoundingBox)boundsObject; lower.x = box.lower.x; lower.y = box.lower.y; lower.z = box.lower.z; upper.x = box.upper.x; upper.y = box.upper.y; upper.z = box.upper.z; } else if( boundsObject.boundId == BOUNDING_SPHERE ) { BoundingSphere sphere = (BoundingSphere)boundsObject; lower.x = sphere.center.x - sphere.radius; lower.y = sphere.center.y - sphere.radius; lower.z = sphere.center.z - sphere.radius; upper.x = sphere.center.x + sphere.radius; upper.y = sphere.center.y + sphere.radius; upper.z = sphere.center.z + sphere.radius; } else if(boundsObject.boundId == BOUNDING_POLYTOPE) { BoundingPolytope polytope = (BoundingPolytope)boundsObject; lower.x = upper.x = polytope.verts[0].x; lower.y = upper.y = polytope.verts[0].y; lower.z = upper.z = polytope.verts[0].z; for(i=1;i<polytope.nVerts;i++) { if( polytope.verts[i].x < lower.x ) lower.x = polytope.verts[i].x; if( polytope.verts[i].y < lower.y ) lower.y = polytope.verts[i].y; if( polytope.verts[i].z < lower.z ) lower.z = polytope.verts[i].z; if( polytope.verts[i].x > upper.x ) upper.x = polytope.verts[i].x; if( polytope.verts[i].y > upper.y ) upper.y = polytope.verts[i].y; if( polytope.verts[i].z > upper.z ) upper.z = polytope.verts[i].z; } } else { throw new IllegalArgumentException(J3dI18N.getString("BoundingBox0")); } updateBoundsStates(); } /** * Creates a copy of this bounding box. * @return a new bounding box */ public Object clone() { return new BoundingBox(this.lower, this.upper); } /** * Indicates whether the specified <code>bounds</code> object is * equal to this BoundingBox object. They are equal if the * specified <code>bounds</code> object is an instance of * BoundingBox and all of the data * members of <code>bounds</code> are equal to the corresponding * data members in this BoundingBox. * @param bounds the object with which the comparison is made. * @return true if this BoundingBox is equal to <code>bounds</code>; * otherwise false * * @since Java 3D 1.2 */ public boolean equals(Object bounds) { try { BoundingBox box = (BoundingBox)bounds; return (lower.equals(box.lower) && upper.equals(box.upper)); } catch (NullPointerException e) { return false; } catch (ClassCastException e) { return false; } } /** * Returns a hash code value for this BoundingBox object * based on the data values in this object. Two different * BoundingBox objects with identical data values (i.e., * BoundingBox.equals returns true) will return the same hash * code value. Two BoundingBox objects with different data * members may return the same hash code value, although this is * not likely. * @return a hash code value for this BoundingBox object. * * @since Java 3D 1.2 */ public int hashCode() { long bits = 1L; bits = 31L * bits + HashCodeUtil.doubleToLongBits(lower.x); bits = 31L * bits + HashCodeUtil.doubleToLongBits(lower.y); bits = 31L * bits + HashCodeUtil.doubleToLongBits(lower.z); bits = 31L * bits + HashCodeUtil.doubleToLongBits(upper.x); bits = 31L * bits + HashCodeUtil.doubleToLongBits(upper.y); bits = 31L * bits + HashCodeUtil.doubleToLongBits(upper.z); return (int) (bits ^ (bits >> 32)); } /** * Combines this bounding box with a bounding object so that the * resulting bounding box encloses the original bounding box and the * specified bounds object. * @param boundsObject another bounds object */ public void combine(Bounds boundsObject) { if((boundsObject == null) || (boundsObject.boundsIsEmpty) || (boundsIsInfinite)) return; if((boundsIsEmpty) || (boundsObject.boundsIsInfinite)) { this.set(boundsObject); return; } if( boundsObject.boundId == BOUNDING_BOX){ BoundingBox box = (BoundingBox)boundsObject; if( lower.x > box.lower.x) lower.x = box.lower.x; if( lower.y > box.lower.y) lower.y = box.lower.y; if( lower.z > box.lower.z) lower.z = box.lower.z; if( upper.x < box.upper.x) upper.x = box.upper.x; if( upper.y < box.upper.y) upper.y = box.upper.y; if( upper.z < box.upper.z) upper.z = box.upper.z; } else if( boundsObject.boundId == BOUNDING_SPHERE ) { BoundingSphere sphere = (BoundingSphere)boundsObject; if( lower.x > (sphere.center.x - sphere.radius)) lower.x = sphere.center.x - sphere.radius; if( lower.y > (sphere.center.y - sphere.radius)) lower.y = sphere.center.y - sphere.radius; if( lower.z > (sphere.center.z - sphere.radius)) lower.z = sphere.center.z - sphere.radius; if( upper.x < (sphere.center.x + sphere.radius)) upper.x = sphere.center.x + sphere.radius; if( upper.y < (sphere.center.y + sphere.radius)) upper.y = sphere.center.y + sphere.radius; if( upper.z < (sphere.center.z + sphere.radius)) upper.z = sphere.center.z + sphere.radius; } else if(boundsObject.boundId == BOUNDING_POLYTOPE) { BoundingPolytope polytope = (BoundingPolytope)boundsObject; int i; for(i=1;i<polytope.nVerts;i++) { if( polytope.verts[i].x < lower.x ) lower.x = polytope.verts[i].x; if( polytope.verts[i].y < lower.y ) lower.y = polytope.verts[i].y;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -