210 lines
5.8 KiB
C++
210 lines
5.8 KiB
C++
//
|
|
// Redistribution and use in source and binary forms, with or without
|
|
// modification, are permitted provided that the following conditions
|
|
// are met:
|
|
// * Redistributions of source code must retain the above copyright
|
|
// notice, this list of conditions and the following disclaimer.
|
|
// * 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.
|
|
// * Neither the name of NVIDIA CORPORATION nor the names of its
|
|
// contributors may be used to endorse or promote products derived
|
|
// from this software without specific prior written permission.
|
|
//
|
|
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``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 THE COPYRIGHT OWNER 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.
|
|
//
|
|
// Copyright (c) 2018 NVIDIA Corporation. All rights reserved.
|
|
|
|
#ifndef BOUNDS3_H
|
|
#define BOUNDS3_H
|
|
|
|
#include "Vec3.h"
|
|
|
|
// Singe / VecVecReal Precision Vec 3
|
|
// Matthias Mueller
|
|
// derived from Vec3.h
|
|
|
|
namespace M
|
|
{
|
|
|
|
class Bounds3
|
|
{
|
|
public:
|
|
|
|
Vec3 minimum, maximum;
|
|
|
|
Bounds3()
|
|
{
|
|
// Default to empty boxes for compatibility TODO: PT: remove this if useless
|
|
setEmpty();
|
|
}
|
|
|
|
|
|
~Bounds3()
|
|
{
|
|
//nothing
|
|
}
|
|
|
|
|
|
void setEmpty()
|
|
{
|
|
// We know use this particular pattern for empty boxes
|
|
set(MAX_VEC_REAL, MAX_VEC_REAL, MAX_VEC_REAL,
|
|
MIN_VEC_REAL, MIN_VEC_REAL, MIN_VEC_REAL);
|
|
}
|
|
|
|
void setInfinite()
|
|
{
|
|
set(MIN_VEC_REAL, MIN_VEC_REAL, MIN_VEC_REAL,
|
|
MAX_VEC_REAL, MAX_VEC_REAL, MAX_VEC_REAL);
|
|
}
|
|
|
|
void set(VecReal mi, VecReal miny, VecReal minz, VecReal maxx, VecReal maxy,VecReal maxz)
|
|
{
|
|
minimum.set(mi, miny, minz);
|
|
maximum.set(maxx, maxy, maxz);
|
|
}
|
|
|
|
void set(const Vec3& _min, const Vec3& _max)
|
|
{
|
|
minimum = _min;
|
|
maximum = _max;
|
|
}
|
|
|
|
void include(const Vec3& v)
|
|
{
|
|
maximum.max(v);
|
|
minimum.min(v);
|
|
}
|
|
|
|
void combine(const Bounds3& b2)
|
|
{
|
|
// - if we're empty, min = MAX,MAX,MAX => min will be b2 in all cases => it will copy b2, ok
|
|
// - if b2 is empty, the opposite happens => keep us unchanged => ok
|
|
// => same behavior as before, automatically
|
|
minimum.min(b2.minimum);
|
|
maximum.max(b2.maximum);
|
|
}
|
|
|
|
//void boundsOfOBB(const Mat33& orientation, const Vec3& translation, const Vec3& halfDims)
|
|
//{
|
|
//VecReal dimx = halfDims[0];
|
|
//VecReal dimy = halfDims[1];
|
|
//VecReal dimz = halfDims[2];
|
|
|
|
//VecReal x = Math::abs(orientation(0,0) * dimx) + Math::abs(orientation(0,1) * dimy) + Math::abs(orientation(0,2) * dimz);
|
|
//VecReal y = Math::abs(orientation(1,0) * dimx) + Math::abs(orientation(1,1) * dimy) + Math::abs(orientation(1,2) * dimz);
|
|
//VecReal z = Math::abs(orientation(2,0) * dimx) + Math::abs(orientation(2,1) * dimy) + Math::abs(orientation(2,2) * dimz);
|
|
|
|
//set(-x + translation[0], -y + translation[1], -z + translation[2], x + translation[0], y + translation[1], z + translation[2]);
|
|
//}
|
|
|
|
//void transform(const Mat33& orientation, const Vec3& translation)
|
|
//{
|
|
//// convert to center and extents form
|
|
//Vec3 center, extents;
|
|
//getCenter(center);
|
|
//getExtents(extents);
|
|
|
|
//center = orientation * center + translation;
|
|
//boundsOfOBB(orientation, center, extents);
|
|
//}
|
|
|
|
bool isEmpty() const
|
|
{
|
|
// Consistency condition for (Min, Max) boxes: min < max
|
|
// TODO: PT: should we test against the explicit pattern ?
|
|
if(minimum.x < maximum.x) return false;
|
|
if(minimum.y < maximum.y) return false;
|
|
if(minimum.z < maximum.z) return false;
|
|
return true;
|
|
}
|
|
|
|
bool intersects(const Bounds3& b) const
|
|
{
|
|
if ((b.minimum.x > maximum.x) || (minimum.x > b.maximum.x)) return false;
|
|
if ((b.minimum.y > maximum.y) || (minimum.y > b.maximum.y)) return false;
|
|
if ((b.minimum.z > maximum.z) || (minimum.z > b.maximum.z)) return false;
|
|
return true;
|
|
}
|
|
|
|
bool intersects2D(const Bounds3& b, unsigned axis) const
|
|
{
|
|
// TODO: PT: could be static and like this:
|
|
// static unsigned i[3] = { 1,2,0,1 };
|
|
// const unsigned ii = i[axis];
|
|
// const unsigned jj = i[axis+1];
|
|
const unsigned i[3] = { 1,0,0 };
|
|
const unsigned j[3] = { 2,2,1 };
|
|
const unsigned ii = i[axis];
|
|
const unsigned jj = j[axis];
|
|
if ((b.minimum[ii] > maximum[ii]) || (minimum[ii] > b.maximum[ii])) return false;
|
|
if ((b.minimum[jj] > maximum[jj]) || (minimum[jj] > b.maximum[jj])) return false;
|
|
return true;
|
|
}
|
|
|
|
bool contain(const Vec3& v) const
|
|
{
|
|
if ((v.x < minimum.x) || (v.x > maximum.x)) return false;
|
|
if ((v.y < minimum.y) || (v.y > maximum.y)) return false;
|
|
if ((v.z < minimum.z) || (v.z > maximum.z)) return false;
|
|
return true;
|
|
}
|
|
|
|
void getCenter(Vec3& center) const
|
|
{
|
|
center.add(minimum,maximum);
|
|
center *= VecReal(0.5);
|
|
}
|
|
|
|
void getDimensions(Vec3& dims) const
|
|
{
|
|
dims.subtract(maximum,minimum);
|
|
}
|
|
|
|
void getExtents(Vec3& extents) const
|
|
{
|
|
extents.subtract(maximum,minimum);
|
|
extents *= VecReal(0.5);
|
|
}
|
|
|
|
void setCenterExtents(const Vec3& c, const Vec3& e)
|
|
{
|
|
minimum = c - e;
|
|
maximum = c + e;
|
|
}
|
|
|
|
void scale(VecReal _scale)
|
|
{
|
|
Vec3 center, extents;
|
|
getCenter(center);
|
|
getExtents(extents);
|
|
setCenterExtents(center, extents * _scale);
|
|
}
|
|
|
|
void fatten(VecReal distance)
|
|
{
|
|
minimum.x -= distance;
|
|
minimum.y -= distance;
|
|
minimum.z -= distance;
|
|
|
|
maximum.x += distance;
|
|
maximum.y += distance;
|
|
maximum.z += distance;
|
|
}
|
|
};
|
|
|
|
}
|
|
|
|
#endif
|