64 #include "BSPImplT.hh"
73 template <
class BSPCore>
80 data.dist = infinity_;
82 throw std::runtime_error(
"It seems like the BSP hasn't been built, yet. Did you call build(...)?");
83 _nearest(this->root_, data);
91 template <
class BSPCore>
94 _nearest(Node* _node, NearestNeighborData& _data)
const
97 if (!_node->left_child_)
100 for (HandleIter it=_node->begin(); it!=_node->end(); ++it)
102 dist = this->traits_.sqrdist(*it, _data.ref);
103 if (dist < _data.dist)
114 Scalar dist = _node->plane_.distance(_data.ref);
117 _nearest(_node->left_child_, _data);
118 if (dist*dist < _data.dist)
119 _nearest(_node->right_child_, _data);
123 _nearest(_node->right_child_, _data);
124 if (dist*dist < _data.dist)
125 _nearest(_node->left_child_, _data);
132 template <
class BSPCore>
141 data.hit_handles.clear();
143 _raycollision_non_directional(this->root_, data);
149 template <
class BSPCore>
158 data.hit_handles.clear();
160 _raycollision_directional(this->root_, data);
167 template <
class BSPCore>
176 data.hit_handles.clear();
178 _raycollision_nearest_directional(this->root_, data);
183 template<
class BSPCore>
184 template<
class Callback>
189 _intersect_ball(*(this->root_), _c, _r, _callback);
196 template <
class BSPCore>
202 if (!_node->left_child_)
208 for (HandleIter it=_node->begin(); it!=_node->end(); ++it)
210 this->traits_.points(*it, v0, v1, v2);
213 _data.hit_handles.push_back(std::pair<Handle,Scalar>(*it,dist));
223 _raycollision_non_directional(_node->left_child_, _data);
226 _raycollision_non_directional(_node->right_child_, _data);
234 template <
class BSPCore>
240 if (!_node->left_child_)
246 for (HandleIter it=_node->begin(); it!=_node->end(); ++it)
248 this->traits_.points(*it, v0, v1, v2);
251 _data.hit_handles.push_back(std::pair<Handle,Scalar>(*it,dist));
262 _raycollision_directional(_node->left_child_, _data);
265 _raycollision_directional(_node->right_child_, _data);
273 template <
class BSPCore>
279 if (!_node->left_child_)
285 for (HandleIter it=_node->begin(); it!=_node->end(); ++it)
287 this->traits_.points(*it, v0, v1, v2);
290 _data.hit_handles.push_back(std::pair<Handle,Scalar>(*it, dist));
295 if(!_data.hit_handles.empty()) {
296 std::partial_sort(_data.hit_handles.begin(), _data.hit_handles.begin() + 1, _data.hit_handles.end(), less_pair_second<Handle, Scalar>());
297 _data.hit_handles.resize(1);
305 Node* first_node = _node->left_child_, *second_node = _node->right_child_;
306 if (!_node->plane_(_data.ref)) {
307 std::swap(first_node, second_node);
312 _raycollision_nearest_directional(first_node, _data);
316 if(!_data.hit_handles.empty()) {
317 dist = _data.hit_handles.front().second;
320 _raycollision_nearest_directional(second_node, _data);
324 template<
class BSPCore>
325 template<
class Callback>
330 Callback _callback)
const
333 if (!_node.left_child_)
335 const double r_sqr = _r * _r;
336 for (
const auto &fh: _node) {
337 const double dist = this->traits_.sqrdist(fh, _c);
345 const Scalar dist = _node.plane_.distance(_c);
346 const Node &left = *_node.left_child_;
347 const Node &right = *_node.right_child_;
350 _intersect_ball(left, _c, _r, _callback);
353 _intersect_ball(right, _c, _r, _callback);
RayCollision raycollision(const Point &_p, const Point &_r) const
intersect mesh with ray
static Scalar max()
Return the maximum absolte value a scalar type can store.
void intersectBall(const Point &_c, Scalar _r, Callback _callback) const
intersect mesh with open ball
bool triangleIntersection(const Vec &_o, const Vec &_dir, const Vec &_v0, const Vec &_v1, const Vec &_v2, typename Vec::value_type &_t, typename Vec::value_type &_u, typename Vec::value_type &_v)
Intersect a ray and a triangle.
std::vector< std::pair< Handle, Scalar > > RayCollision
Store nearest neighbor information.
NearestNeighbor nearest(const Point &_p) const
Return handle of the nearest neighbor face.
Store nearest neighbor information.
Store ray collide information.
Store nearest neighbor information.
bool axisAlignedBBIntersection(const Vec &_o, const Vec &_dir, const Vec &_bbmin, const Vec &_bbmax, typename Vec::value_type &tmin, typename Vec::value_type &tmax)
Intersect a ray and an axis aligned bounding box.
void _raycollision_non_directional(Node *_node, RayCollisionData &_data) const
recursive part of raycollision()
RayCollision directionalRaycollision(const Point &_p, const Point &_r) const
intersect mesh with ray
void _raycollision_directional(Node *_node, RayCollisionData &_data) const
recursive part of directionalRaycollision()
RayCollision nearestRaycollision(const Point &_p, const Point &_r) const
intersect mesh with ray