/* ----------------------------------------------------------------------- * * This file is part of GEL, http://www.imm.dtu.dk/GEL * Copyright (C) the authors and DTU Informatics * For license and list of authors, see ../../doc/intro.pdf * ----------------------------------------------------------------------- */ #include #include "AABox.h" using namespace std; using namespace CGLA; namespace Geometry { bool AABox::intersect(const CGLA::Vec3f& p, const CGLA::Vec3f& dir) const { Vec3f t0,t1; for(int i=0;i<3;++i) { t0[i] = (pmin[i]-p[i])/dir[i]; t1[i] = (pmax[i]-p[i])/dir[i]; } Vec3f tin = v_min(t0, t1); Vec3f tout = v_max(t0,t1); float tmin = max(tin[0], max(tin[1], tin[2])); float tmax = min(tout[0], min(tout[1], tout[2])); return ( (tmin-CGLA::TINY) < (tmax+CGLA::TINY)); } void AABox::minmax_sq_dist(const CGLA::Vec3f& p, float& dmin, float& dmax) const { const Vec3f a = 0.5*pmax-0.5*pmin; const Vec3f p0 = pmin + a; Vec3f d = p-p0; Vec3f f(d); for(int i=0;i<3;++i) { if(f[i]>=0) f[i] = p[i]-pmin[i]; else f[i] = p[i]-pmax[i]; if(d[i]<-a[i]) d[i] = p[i]-pmin[i]; else if(d[i]>a[i]) d[i] = p[i]-pmax[i]; else d[i] = 0; } dmin = sqr_length(d); // dmax = sqr_length(p-interior_point); dmax = sqr_length(f); assert(dmin<=dmax); } AABox AABox::box_triangle(const Triangle& t) { return AABox(t.get_pmin(), t.get_pmax(), t.get_centre()); } AABox AABox::box_and_split(const std::vector& invec, std::vector& lvec, std::vector& rvec) { const size_t N = invec.size(); Vec3f tri_pmin(FLT_MAX), tri_pmax(-FLT_MAX); for(size_t i=0;idiff[1]) { if(diff[0]>diff[2]) k = 0; else k = 2; } else { if(diff[1]>diff[2]) k = 1; else k = 2; } float thresh = diff[k]/2.0f + tri_pmin[k]; for(size_t i=0;i thresh) rvec.push_back(invec[i]); else lvec.push_back(invec[i]); } if(lvec.empty() || rvec.empty()) { lvec.clear(); lvec.insert(lvec.end(), invec.begin(), invec.begin()+N/2); rvec.clear(); rvec.insert(rvec.end(), invec.begin()+N/2, invec.end()); } assert(!lvec.empty()); assert(!rvec.empty()); assert(lvec.size()+rvec.size() == invec.size()); return AABox(tri_pmin, tri_pmax, centre_close); } }