159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta/* 259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * Copyright (c) 2009-2010 jMonkeyEngine 359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * All rights reserved. 459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * 559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * Redistribution and use in source and binary forms, with or without 659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * modification, are permitted provided that the following conditions are 759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * met: 859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * 959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * * Redistributions of source code must retain the above copyright 1059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * notice, this list of conditions and the following disclaimer. 1159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * 1259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * * Redistributions in binary form must reproduce the above copyright 1359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * notice, this list of conditions and the following disclaimer in the 1459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * documentation and/or other materials provided with the distribution. 1559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * 1659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * * Neither the name of 'jMonkeyEngine' nor the names of its contributors 1759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * may be used to endorse or promote products derived from this software 1859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * without specific prior written permission. 1959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * 2059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 2159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 2259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 2359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 2459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 2559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 2659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 2759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 2859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 2959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 3059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 3159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta */ 3259b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartapackage com.jme3.bounding; 3359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 3459b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport com.jme3.math.FastMath; 3559b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport com.jme3.math.Plane; 3659b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport com.jme3.math.Vector3f; 3759b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport com.jme3.util.TempVars; 3859b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport static java.lang.Math.max; 3959b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartaimport static java.lang.Math.min; 4059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 4159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta/** 4259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * This class includes some utility methods for computing intersection 4359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * between bounding volumes and triangles. 4459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta * @author Kirill 4559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta */ 4659b2e6871c65f58fdad78cd7229c292f6a177578Scott Bartapublic class Intersection { 4759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 4859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta private static final void findMinMax(float x0, float x1, float x2, Vector3f minMax) { 4959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta minMax.set(x0, x0, 0); 5059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (x1 < minMax.x) { 5159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta minMax.setX(x1); 5259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 5359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (x1 > minMax.y) { 5459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta minMax.setY(x1); 5559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 5659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (x2 < minMax.x) { 5759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta minMax.setX(x2); 5859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 5959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (x2 > minMax.y) { 6059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta minMax.setY(x2); 6159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 6259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 6359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 6459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// private boolean axisTest(float a, float b, float fa, float fb, Vector3f v0, Vector3f v1, ) 6559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// private boolean axisTestX01(float a, float b, float fa, float fb, 6659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// Vector3f center, Vector3f ext, 6759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// Vector3f v1, Vector3f v2, Vector3f v3){ 6859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// float p0 = a * v0.y - b * v0.z; 6959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// float p2 = a * v2.y - b * v2.z; 7059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// if(p0 < p2){ 7159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// min = p0; 7259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// max = p2; 7359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// } else { 7459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// min = p2; 7559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// max = p0; 7659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// } 7759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// float rad = fa * boxhalfsize.y + fb * boxhalfsize.z; 7859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// if(min > rad || max < -rad) 7959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// return false; 8059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// } 8159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta public static boolean intersect(BoundingBox bbox, Vector3f v1, Vector3f v2, Vector3f v3) { 8259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // use separating axis theorem to test overlap between triangle and box 8359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // need to test for overlap in these directions: 8459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // 1) the {x,y,z}-directions (actually, since we use the AABB of the triangle 8559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // we do not even need to test these) 8659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // 2) normal of the triangle 8759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // 3) crossproduct(edge from tri, {x,y,z}-directin) 8859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // this gives 3x3=9 more tests 8959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 9059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta TempVars vars = TempVars.get(); 9159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 9259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 9359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Vector3f tmp0 = vars.vect1, 9459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta tmp1 = vars.vect2, 9559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta tmp2 = vars.vect3; 9659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 9759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Vector3f e0 = vars.vect4, 9859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta e1 = vars.vect5, 9959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta e2 = vars.vect6; 10059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 10159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Vector3f center = bbox.getCenter(); 10259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Vector3f extent = bbox.getExtent(null); 10359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 10459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// float min,max,p0,p1,p2,rad,fex,fey,fez; 10559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// float normal[3] 10659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 10759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // This is the fastest branch on Sun 10859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // move everything so that the boxcenter is in (0,0,0) 10959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta v1.subtract(center, tmp0); 11059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta v2.subtract(center, tmp1); 11159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta v3.subtract(center, tmp2); 11259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 11359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // compute triangle edges 11459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta tmp1.subtract(tmp0, e0); // tri edge 0 11559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta tmp2.subtract(tmp1, e1); // tri edge 1 11659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta tmp0.subtract(tmp2, e2); // tri edge 2 11759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 11859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // Bullet 3: 11959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // test the 9 tests first (this was faster) 12059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta float min, max; 12159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta float p0, p1, p2, rad; 12259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta float fex = FastMath.abs(e0.x); 12359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta float fey = FastMath.abs(e0.y); 12459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta float fez = FastMath.abs(e0.z); 12559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 12659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 12759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 12859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta //AXISTEST_X01(e0[Z], e0[Y], fez, fey); 12959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = e0.z * tmp0.y - e0.y * tmp0.z; 13059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = e0.z * tmp2.y - e0.y * tmp2.z; 13159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p2); 13259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p2); 13359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.y + fey * extent.z; 13459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 13559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 13659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 13759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 13859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 13959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_Y02(e0[Z], e0[X], fez, fex); 14059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = -e0.z * tmp0.x + e0.x * tmp0.z; 14159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = -e0.z * tmp2.x + e0.x * tmp2.z; 14259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p2); 14359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p2); 14459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.x + fex * extent.z; 14559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 14659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 14759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 14859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 14959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 15059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_Z12(e0[Y], e0[X], fey, fex); 15159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p1 = e0.y * tmp1.x - e0.x * tmp1.y; 15259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = e0.y * tmp2.x - e0.x * tmp2.y; 15359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p1, p2); 15459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p1, p2); 15559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fey * extent.x + fex * extent.y; 15659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 15759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 15859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 15959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 16059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 16159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fex = FastMath.abs(e1.x); 16259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fey = FastMath.abs(e1.y); 16359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fez = FastMath.abs(e1.z); 16459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 16559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// AXISTEST_X01(e1[Z], e1[Y], fez, fey); 16659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = e1.z * tmp0.y - e1.y * tmp0.z; 16759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = e1.z * tmp2.y - e1.y * tmp2.z; 16859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p2); 16959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p2); 17059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.y + fey * extent.z; 17159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 17259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 17359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 17459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 17559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 17659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_Y02(e1[Z], e1[X], fez, fex); 17759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = -e1.z * tmp0.x + e1.x * tmp0.z; 17859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = -e1.z * tmp2.x + e1.x * tmp2.z; 17959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p2); 18059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p2); 18159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.x + fex * extent.z; 18259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 18359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 18459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 18559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 18659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 18759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_Z0(e1[Y], e1[X], fey, fex); 18859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = e1.y * tmp0.x - e1.x * tmp0.y; 18959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p1 = e1.y * tmp1.x - e1.x * tmp1.y; 19059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p1); 19159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p1); 19259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fey * extent.x + fex * extent.y; 19359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 19459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 19559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 19659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 19759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// 19859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fex = FastMath.abs(e2.x); 19959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fey = FastMath.abs(e2.y); 20059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta fez = FastMath.abs(e2.z); 20159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 20259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_X2(e2[Z], e2[Y], fez, fey); 20359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = e2.z * tmp0.y - e2.y * tmp0.z; 20459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p1 = e2.z * tmp1.y - e2.y * tmp1.z; 20559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p1); 20659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p1); 20759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.y + fey * extent.z; 20859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 20959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 21059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 21159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 21259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 21359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // AXISTEST_Y1(e2[Z], e2[X], fez, fex); 21459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p0 = -e2.z * tmp0.x + e2.x * tmp0.z; 21559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p1 = -e2.z * tmp1.x + e2.x * tmp1.z; 21659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p0, p1); 21759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p0, p1); 21859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fez * extent.x + fex * extent.y; 21959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 22059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 22159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 22259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 22359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 22459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// AXISTEST_Z12(e2[Y], e2[X], fey, fex); 22559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p1 = e2.y * tmp1.x - e2.x * tmp1.y; 22659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p2 = e2.y * tmp2.x - e2.x * tmp2.y; 22759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta min = min(p1, p2); 22859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta max = max(p1, p2); 22959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta rad = fey * extent.x + fex * extent.y; 23059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (min > rad || max < -rad) { 23159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 23259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 23359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 23459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 23559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // Bullet 1: 23659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // first test overlap in the {x,y,z}-directions 23759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // find min, max of the triangle each direction, and test for overlap in 23859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // that direction -- this is equivalent to testing a minimal AABB around 23959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // the triangle against the AABB 24059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 24159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 24259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Vector3f minMax = vars.vect7; 24359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 24459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // test in X-direction 24559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta findMinMax(tmp0.x, tmp1.x, tmp2.x, minMax); 24659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (minMax.x > extent.x || minMax.y < -extent.x) { 24759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 24859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 24959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 25059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 25159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // test in Y-direction 25259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta findMinMax(tmp0.y, tmp1.y, tmp2.y, minMax); 25359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (minMax.x > extent.y || minMax.y < -extent.y) { 25459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 25559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 25659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 25759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 25859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta // test in Z-direction 25959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta findMinMax(tmp0.z, tmp1.z, tmp2.z, minMax); 26059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (minMax.x > extent.z || minMax.y < -extent.z) { 26159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 26259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 26359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 26459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 26559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// // Bullet 2: 26659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// // test if the box intersects the plane of the triangle 26759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// // compute plane equation of triangle: normal * x + d = 0 26859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// Vector3f normal = new Vector3f(); 26959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// e0.cross(e1, normal); 27059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta Plane p = vars.plane; 27159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 27259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta p.setPlanePoints(v1, v2, v3); 27359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta if (bbox.whichSide(p) == Plane.Side.Negative) { 27459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 27559b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return false; 27659b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 27759b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// 27859b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta// if(!planeBoxOverlap(normal,v0,boxhalfsize)) return false; 27959b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 28059b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta vars.release(); 28159b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta 28259b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta return true; /* box and triangle overlaps */ 28359b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta } 28459b2e6871c65f58fdad78cd7229c292f6a177578Scott Barta} 285