OpenVDB  11.0.0
Ray.h
Go to the documentation of this file.
1 // Copyright Contributors to the OpenVDB Project
2 // SPDX-License-Identifier: MPL-2.0
3 
4 /// @file Ray.h
5 ///
6 /// @author Ken Museth
7 ///
8 /// @brief A Ray class.
9 
10 #ifndef NANOVDB_RAY_H_HAS_BEEN_INCLUDED
11 #define NANOVDB_RAY_H_HAS_BEEN_INCLUDED
12 
13 #include <nanovdb/NanoVDB.h> // for Vec3
14 
15 namespace nanovdb {
16 
17 template<typename RealT>
18 class Ray
19 {
20 public:
21  using RealType = RealT;
23  using Vec3T = Vec3Type;
24 
25  struct TimeSpan
26  {
27  RealT t0, t1;
28  /// @brief Default constructor
30  /// @brief Constructor
31  __hostdev__ TimeSpan(RealT _t0, RealT _t1)
32  : t0(_t0)
33  , t1(_t1)
34  {
35  }
36  /// @brief Set both times
37  __hostdev__ void set(RealT _t0, RealT _t1)
38  {
39  t0 = _t0;
40  t1 = _t1;
41  }
42  /// @brief Get both times
43  __hostdev__ void get(RealT& _t0, RealT& _t1) const
44  {
45  _t0 = t0;
46  _t1 = t1;
47  }
48  /// @brief Return @c true if t1 is larger than t0 by at least eps.
49  __hostdev__ bool valid(RealT eps = Delta<RealT>::value()) const { return (t1 - t0) > eps; }
50  /// @brief Return the midpoint of the ray.
51  __hostdev__ RealT mid() const { return 0.5 * (t0 + t1); }
52  /// @brief Multiplies both times
53  __hostdev__ void scale(RealT s)
54  {
55  assert(s > 0);
56  t0 *= s;
57  t1 *= s;
58  }
59  /// @brief Return @c true if time is inclusive
60  __hostdev__ bool test(RealT t) const { return (t >= t0 && t <= t1); }
61  };
62 
63  __hostdev__ Ray(const Vec3Type& eye = Vec3Type(0, 0, 0),
64  const Vec3Type& direction = Vec3Type(1, 0, 0),
65  RealT t0 = Delta<RealT>::value(),
66  RealT t1 = Maximum<RealT>::value())
67  : mEye(eye)
68  , mDir(direction)
69  , mInvDir(1 / mDir[0], 1 / mDir[1], 1 / mDir[2])
70  , mTimeSpan(t0, t1)
71  , mSign{mInvDir[0] < 0, mInvDir[1] < 0, mInvDir[2] < 0}
72  {
73  }
74 
75  __hostdev__ Ray& offsetEye(RealT offset)
76  {
77  mEye[0] += offset;
78  mEye[1] += offset;
79  mEye[2] += offset;
80  return *this;
81  }
82 
84  {
85  mEye = eye;
86  return *this;
87  }
88 
90  {
91  mDir = dir;
92  mInvDir[0] = 1.0 / mDir[0];
93  mInvDir[1] = 1.0 / mDir[1];
94  mInvDir[2] = 1.0 / mDir[2];
95  mSign[0] = mInvDir[0] < 0;
96  mSign[1] = mInvDir[1] < 0;
97  mSign[2] = mInvDir[2] < 0;
98  return *this;
99  }
100 
102  {
103  mTimeSpan.t0 = t0;
104  return *this;
105  }
106 
108  {
109  mTimeSpan.t1 = t1;
110  return *this;
111  }
112 
114  RealT t0 = Delta<RealT>::value(),
115  RealT t1 = Maximum<RealT>::value())
116  {
117  assert(t0 > 0 && t1 > 0);
118  mTimeSpan.set(t0, t1);
119  return *this;
120  }
121 
123  {
124  mTimeSpan.scale(scale);
125  return *this;
126  }
127 
129  const Vec3Type& eye,
130  const Vec3Type& direction,
131  RealT t0 = Delta<RealT>::value(),
132  RealT t1 = Maximum<RealT>::value())
133  {
134  this->setEye(eye);
135  this->setDir(direction);
136  this->setTimes(t0, t1);
137  return *this;
138  }
139 
140  __hostdev__ const Vec3T& eye() const { return mEye; }
141 
142  __hostdev__ const Vec3T& dir() const { return mDir; }
143 
144  __hostdev__ const Vec3T& invDir() const { return mInvDir; }
145 
146  __hostdev__ RealT t0() const { return mTimeSpan.t0; }
147 
148  __hostdev__ RealT t1() const { return mTimeSpan.t1; }
149 
150  __hostdev__ int sign(int i) const { return mSign[i]; }
151 
152  /// @brief Return the position along the ray at the specified time.
153  __hostdev__ Vec3T operator()(RealT time) const
154  {
155 #if 1
156  return Vec3T(fmaf(time, mDir[0], mEye[0]),
157  fmaf(time, mDir[1], mEye[1]),
158  fmaf(time, mDir[2], mEye[2]));
159 #else
160  return mEye + mDir * time;
161 #endif
162  }
163 
164  /// @brief Return the starting point of the ray.
165  __hostdev__ Vec3T start() const { return (*this)(mTimeSpan.t0); }
166 
167  /// @brief Return the endpoint of the ray.
168  __hostdev__ Vec3T end() const { return (*this)(mTimeSpan.t1); }
169 
170  /// @brief Return the midpoint of the ray.
171  __hostdev__ Vec3T mid() const { return (*this)(mTimeSpan.mid()); }
172 
173  /// @brief Return @c true if t1 is larger than t0 by at least eps.
174  __hostdev__ bool valid(RealT eps = Delta<float>::value()) const { return mTimeSpan.valid(eps); }
175 
176  /// @brief Return @c true if @a time is within t0 and t1, both inclusive.
177  __hostdev__ bool test(RealT time) const { return mTimeSpan.test(time); }
178 
179  /// @brief Return a new Ray that is transformed with the specified map.
180  ///
181  /// @param map the map from which to construct the new Ray.
182  ///
183  /// @warning Assumes a linear map and a normalized direction.
184  ///
185  /// @details The requirement that the direction is normalized
186  /// follows from the transformation of t0 and t1 - and that fact that
187  /// we want applyMap and applyInverseMap to be inverse operations.
188  template<typename MapType>
189  __hostdev__ Ray applyMap(const MapType& map) const
190  {
191  const Vec3T eye = map.applyMap(mEye);
192  const Vec3T dir = map.applyJacobian(mDir);
193  const RealT length = dir.length(), invLength = RealT(1) / length;
194  RealT t1 = mTimeSpan.t1;
195  if (mTimeSpan.t1 < Maximum<RealT>::value()) {
196  t1 *= length;
197  }
198  return Ray(eye, dir * invLength, length * mTimeSpan.t0, t1);
199  }
200  template<typename MapType>
201  __hostdev__ Ray applyMapF(const MapType& map) const
202  {
203  const Vec3T eye = map.applyMapF(mEye);
204  const Vec3T dir = map.applyJacobianF(mDir);
205  const RealT length = dir.length(), invLength = RealT(1) / length;
206  RealT t1 = mTimeSpan.t1;
207  if (mTimeSpan.t1 < Maximum<RealT>::value()) {
208  t1 *= length;
209  }
210  return Ray(eye, dir * invLength, length * mTimeSpan.t0, t1);
211  }
212 
213  /// @brief Return a new Ray that is transformed with the inverse of the specified map.
214  ///
215  /// @param map the map from which to construct the new Ray by inverse mapping.
216  ///
217  /// @warning Assumes a linear map and a normalized direction.
218  ///
219  /// @details The requirement that the direction is normalized
220  /// follows from the transformation of t0 and t1 - and that fact that
221  /// we want applyMap and applyInverseMap to be inverse operations.
222  template<typename MapType>
223  __hostdev__ Ray applyInverseMap(const MapType& map) const
224  {
225  const Vec3T eye = map.applyInverseMap(mEye);
226  const Vec3T dir = map.applyInverseJacobian(mDir);
227  const RealT length = dir.length(), invLength = RealT(1) / length;
228  return Ray(eye, dir * invLength, length * mTimeSpan.t0, length * mTimeSpan.t1);
229  }
230  template<typename MapType>
231  __hostdev__ Ray applyInverseMapF(const MapType& map) const
232  {
233  const Vec3T eye = map.applyInverseMapF(mEye);
234  const Vec3T dir = map.applyInverseJacobianF(mDir);
235  const RealT length = dir.length(), invLength = RealT(1) / length;
236  return Ray(eye, dir * invLength, length * mTimeSpan.t0, length * mTimeSpan.t1);
237  }
238 
239  /// @brief Return a new ray in world space, assuming the existing
240  /// ray is represented in the index space of the specified grid.
241  template<typename GridType>
243  {
244  const Vec3T eye = grid.indexToWorldF(mEye);
245  const Vec3T dir = grid.indexToWorldDirF(mDir);
246  const RealT length = dir.length(), invLength = RealT(1) / length;
247  RealT t1 = mTimeSpan.t1;
248  if (mTimeSpan.t1 < Maximum<RealT>::value()) {
249  t1 *= length;
250  }
251  return Ray(eye, dir * invLength, length * mTimeSpan.t0, t1);
252  }
253 
254  /// @brief Return a new ray in index space, assuming the existing
255  /// ray is represented in the world space of the specified grid.
256  template<typename GridType>
258  {
259  const Vec3T eye = grid.worldToIndexF(mEye);
260  const Vec3T dir = grid.worldToIndexDirF(mDir);
261  const RealT length = dir.length(), invLength = RealT(1) / length;
262  RealT t1 = mTimeSpan.t1;
263  if (mTimeSpan.t1 < Maximum<RealT>::value()) {
264  t1 *= length;
265  }
266  return Ray(eye, dir * invLength, length * mTimeSpan.t0, t1);
267  }
268 
269  /// @brief Return true if this ray intersects the specified sphere.
270  ///
271  /// @param center The center of the sphere in the same space as this ray.
272  /// @param radius The radius of the sphere in the same units as this ray.
273  /// @param t0 The first intersection point if an intersection exists.
274  /// @param t1 The second intersection point if an intersection exists.
275  ///
276  /// @note If the return value is true, i.e. a hit, and t0 =
277  /// this->t0() or t1 == this->t1() only one true intersection exist.
278  __hostdev__ bool intersects(const Vec3T& center, RealT radius, RealT& t0, RealT& t1) const
279  {
280  const Vec3T origin = mEye - center;
281  const RealT A = mDir.lengthSqr();
282  const RealT B = 2 * mDir.dot(origin);
283  const RealT C = origin.lengthSqr() - radius * radius;
284  const RealT D = B * B - 4 * A * C;
285 
286  if (D < 0) {
287  return false;
288  }
289  const RealT Q = RealT(-0.5) * (B < 0 ? (B + Sqrt(D)) : (B - Sqrt(D)));
290 
291  t0 = Q / A;
292  t1 = C / Q;
293 
294  if (t0 > t1) {
295  RealT tmp = t0;
296  t0 = t1;
297  t1 = tmp;
298  }
299  if (t0 < mTimeSpan.t0) {
300  t0 = mTimeSpan.t0;
301  }
302  if (t1 > mTimeSpan.t1) {
303  t1 = mTimeSpan.t1;
304  }
305  return t0 <= t1;
306  }
307 
308  /// @brief Return true if this ray intersects the specified sphere.
309  ///
310  /// @param center The center of the sphere in the same space as this ray.
311  /// @param radius The radius of the sphere in the same units as this ray.
312  __hostdev__ bool intersects(const Vec3T& center, RealT radius) const
313  {
314  RealT t0, t1;
315  return this->intersects(center, radius, t0, t1) > 0;
316  }
317 
318  /// @brief Return true if this ray intersects the specified sphere.
319  ///
320  /// @note For intersection this ray is clipped to the two intersection points.
321  ///
322  /// @param center The center of the sphere in the same space as this ray.
323  /// @param radius The radius of the sphere in the same units as this ray.
324  __hostdev__ bool clip(const Vec3T& center, RealT radius)
325  {
326  RealT t0, t1;
327  const bool hit = this->intersects(center, radius, t0, t1);
328  if (hit) {
329  mTimeSpan.set(t0, t1);
330  }
331  return hit;
332  }
333 #if 0
334  /// @brief Return true if the Ray intersects the specified
335  /// axisaligned bounding box.
336  ///
337  /// @param bbox Axis-aligned bounding box in the same space as the Ray.
338  /// @param t0 If an intersection is detected this is assigned
339  /// the time for the first intersection point.
340  /// @param t1 If an intersection is detected this is assigned
341  /// the time for the second intersection point.
342  template<typename BBoxT>
343  __hostdev__ bool intersects(const BBoxT& bbox, RealT& t0, RealT& t1) const
344  {
345  t0 = (bbox[ mSign[0]][0] - mEye[0]) * mInvDir[0];
346  RealT t2 = (bbox[1-mSign[1]][1] - mEye[1]) * mInvDir[1];
347  if (t0 > t2) return false;
348  t1 = (bbox[1-mSign[0]][0] - mEye[0]) * mInvDir[0];
349  RealT t3 = (bbox[ mSign[1]][1] - mEye[1]) * mInvDir[1];
350  if (t3 > t1) return false;
351  if (t3 > t0) t0 = t3;
352  if (t2 < t1) t1 = t2;
353  t3 = (bbox[ mSign[2]][2] - mEye[2]) * mInvDir[2];
354  if (t3 > t1) return false;
355  t2 = (bbox[1-mSign[2]][2] - mEye[2]) * mInvDir[2];
356  if (t0 > t2) return false;
357  if (t3 > t0) t0 = t3;
358  if (mTimeSpan.t1 < t0) return false;
359  if (t2 < t1) t1 = t2;
360  if (mTimeSpan.t0 > t1) return false;
361  if (mTimeSpan.t0 > t0) t0 = mTimeSpan.t0;
362  if (mTimeSpan.t1 < t1) t1 = mTimeSpan.t1;
363  return true;
364  /*
365  mTimeSpan.get(_t0, _t1);
366  double t0 = _t0, t1 = _t1;
367  for (int i = 0; i < 3; ++i) {
368  //if (abs(mDir[i])<1e-3) continue;
369  double a = (double(bbox.min()[i]) - mEye[i]) * mInvDir[i];
370  double b = (double(bbox.max()[i]) - mEye[i]) * mInvDir[i];
371  if (a > b) {
372  double tmp = a;
373  a = b;
374  b = tmp;
375  }
376  if (a > t0) t0 = a;
377  if (b < t1) t1 = b;
378  if (t0 > t1) {
379  //if (gVerbose) printf("Missed BBOX: (%i,%i,%i) -> (%i,%i,%i) t0=%f t1=%f\n",
380  // bbox.min()[0], bbox.min()[1], bbox.min()[2],
381  // bbox.max()[0], bbox.max()[1], bbox.max()[2], t0, t1);
382  return false;
383  }
384  }
385  _t0 = t0; _t1 = t1;
386  return true;
387  */
388  }
389 #else
390  /// @brief Returns true if this ray intersects an index bounding box.
391  /// If the return value is true t0 and t1 are set to the intersection
392  /// times along the ray.
393  ///
394  /// @warning Intersection with a CoordBBox internally converts to a floating-point bbox
395  /// which imples that the max is padded with one voxel, i.e. bbox.max += 1! This
396  /// avoids gaps between neighboring CoordBBox'es, say from neighboring tree nodes.
397  __hostdev__ bool intersects(const CoordBBox& bbox, RealT& t0, RealT& t1) const
398  {
399  mTimeSpan.get(t0, t1);
400  for (int i = 0; i < 3; ++i) {
401  RealT a = RealT(bbox.min()[i]), b = RealT(bbox.max()[i] + 1);
402  if (a >= b) { // empty bounding box
403  return false;
404  }
405  a = (a - mEye[i]) * mInvDir[i];
406  b = (b - mEye[i]) * mInvDir[i];
407  if (a > b) {
408  RealT tmp = a;
409  a = b;
410  b = tmp;
411  }
412  if (a > t0) {
413  t0 = a;
414  }
415  if (b < t1) {
416  t1 = b;
417  }
418  if (t0 > t1) {
419  return false;
420  }
421  }
422  return true;
423  }
424  /// @brief Returns true if this ray intersects a floating-point bounding box.
425  /// If the return value is true t0 and t1 are set to the intersection
426  /// times along the ray.
427  template<typename OtherVec3T>
428  __hostdev__ bool intersects(const BBox<OtherVec3T>& bbox, RealT& t0, RealT& t1) const
429  {
430  static_assert(is_floating_point<typename OtherVec3T::ValueType>::value, "Ray::intersects: Expected a floating point coordinate");
431  mTimeSpan.get(t0, t1);
432  for (int i = 0; i < 3; ++i) {
433  RealT a = RealT(bbox.min()[i]), b = RealT(bbox.max()[i]);
434  if (a >= b) { // empty bounding box
435  return false;
436  }
437  a = (a - mEye[i]) * mInvDir[i];
438  b = (b - mEye[i]) * mInvDir[i];
439  if (a > b) {
440  RealT tmp = a;
441  a = b;
442  b = tmp;
443  }
444  if (a > t0) {
445  t0 = a;
446  }
447  if (b < t1) {
448  t1 = b;
449  }
450  if (t0 > t1) {
451  return false;
452  }
453  }
454  return true;
455  }
456 #endif
457 
458  /// @brief Return true if this ray intersects the specified bounding box.
459  ///
460  /// @param bbox Axis-aligned bounding box in the same space as this ray.
461  ///
462  /// @warning If @a bbox is of the type CoordBBox it is converted to a floating-point
463  /// bounding box, which imples that the max is padded with one voxel, i.e.
464  /// bbox.max += 1! This avoids gaps between neighboring CoordBBox'es, say
465  /// from neighboring tree nodes.
466  template<typename BBoxT>
467  __hostdev__ bool intersects(const BBoxT& bbox) const
468  {
469 #if 1
470  RealT t0, t1;
471  return this->intersects(bbox, t0, t1);
472 #else
473  //BBox<Vec3T> bbox(Vec3T(_bbox[0][0]-1e-4,_bbox[0][1]-1e-4,_bbox[0][2]-1e-4),
474  // Vec3T(_bbox[1][0]+1e-4,_bbox[1][1]+1e-4,_bbox[1][2]+1e-4));
475  RealT t0 = (bbox[mSign[0]][0] - mEye[0]) * mInvDir[0];
476  RealT t2 = (bbox[1 - mSign[1]][1] - mEye[1]) * mInvDir[1];
477  if (t0 > t2) return false;
478  RealT t1 = (bbox[1 - mSign[0]][0] - mEye[0]) * mInvDir[0];
479  RealT t3 = (bbox[mSign[1]][1] - mEye[1]) * mInvDir[1];
480  if (t3 > t1) return false;
481  if (t3 > t0) t0 = t3;
482  if (t2 < t1) t1 = t2;
483  t3 = (bbox[mSign[2]][2] - mEye[2]) * mInvDir[2];
484  if (t3 > t1) return false;
485  t2 = (bbox[1 - mSign[2]][2] - mEye[2]) * mInvDir[2];
486  if (t0 > t2) return false;
487  //if (t3 > t0) t0 = t3;
488  //if (mTimeSpan.t1 < t0) return false;
489  //if (t2 < t1) t1 = t2;
490  //return mTimeSpan.t0 < t1;
491  return true;
492 #endif
493  }
494 
495  /// @brief Return true if this ray intersects the specified bounding box.
496  ///
497  /// @param bbox Axis-aligned bounding box in the same space as this ray.
498  ///
499  /// @warning If @a bbox is of the type CoordBBox it is converted to a floating-point
500  /// bounding box, which imples that the max is padded with one voxel, i.e.
501  /// bbox.max += 1! This avoids gaps between neighboring CoordBBox'es, say
502  /// from neighboring tree nodes.
503  ///
504  /// @note For intersection this ray is clipped to the two intersection points.
505  template<typename BBoxT>
506  __hostdev__ bool clip(const BBoxT& bbox)
507  {
508  RealT t0, t1;
509  const bool hit = this->intersects(bbox, t0, t1);
510  if (hit) {
511  mTimeSpan.set(t0, t1);
512  }
513  return hit;
514  }
515 
516  /// @brief Return true if the Ray intersects the plane specified
517  /// by a normal and distance from the origin.
518  ///
519  /// @param normal Normal of the plane.
520  /// @param distance Distance of the plane to the origin.
521  /// @param t Time of intersection, if one exists.
522  __hostdev__ bool intersects(const Vec3T& normal, RealT distance, RealT& t) const
523  {
524  const RealT cosAngle = mDir.dot(normal);
525  if (isApproxZero(cosAngle)) {
526  return false; // ray is parallel to plane
527  }
528  t = (distance - mEye.dot(normal)) / cosAngle;
529  return this->test(t);
530  }
531 
532  /// @brief Return true if the Ray intersects the plane specified
533  /// by a normal and point.
534  ///
535  /// @param normal Normal of the plane.
536  /// @param point Point in the plane.
537  /// @param t Time of intersection, if one exists.
538  __hostdev__ bool intersects(const Vec3T& normal, const Vec3T& point, RealT& t) const
539  {
540  return this->intersects(normal, point.dot(normal), t);
541  }
542 
543 private:
544  Vec3T mEye, mDir, mInvDir;
545  TimeSpan mTimeSpan;
546  int mSign[3];
547 }; // end of Ray class
548 
549 } // namespace nanovdb
550 
551 #endif // NANOVDB_RAY_HAS_BEEN_INCLUDED
__hostdev__ Vec3T start() const
Return the starting point of the ray.
Definition: Ray.h:165
RealT t0
Definition: Ray.h:27
T lengthSqr() const
Definition: NanoVDB.h:1583
__hostdev__ bool intersects(const Vec3T &center, RealT radius) const
Return true if this ray intersects the specified sphere.
Definition: Ray.h:312
Vec3Type Vec3T
Definition: Ray.h:23
__hostdev__ const Vec3T & dir() const
Definition: Ray.h:142
__hostdev__ bool intersects(const Vec3T &normal, RealT distance, RealT &t) const
Return true if the Ray intersects the plane specified by a normal and distance from the origin...
Definition: Ray.h:522
__hostdev__ RealT t0() const
Definition: Ray.h:146
__hostdev__ Ray applyMapF(const MapType &map) const
Definition: Ray.h:201
__hostdev__ bool intersects(const Vec3T &center, RealT radius, RealT &t0, RealT &t1) const
Return true if this ray intersects the specified sphere.
Definition: Ray.h:278
__hostdev__ Ray applyInverseMapF(const MapType &map) const
Definition: Ray.h:231
__hostdev__ Ray & setMaxTime(RealT t1)
Definition: Ray.h:107
__hostdev__ Ray & setEye(const Vec3Type &eye)
Definition: Ray.h:83
__hostdev__ bool test(RealT time) const
Return true if time is within t0 and t1, both inclusive.
Definition: Ray.h:177
__hostdev__ Vec3T mid() const
Return the midpoint of the ray.
Definition: Ray.h:171
__hostdev__ bool test(RealT t) const
Return true if time is inclusive.
Definition: Ray.h:60
__hostdev__ Vec3T end() const
Return the endpoint of the ray.
Definition: Ray.h:168
RealT RealType
Definition: Ray.h:21
__hostdev__ const Vec3T & eye() const
Definition: Ray.h:140
Implements a light-weight self-contained VDB data-structure in a single file! In other words...
Definition: NanoVDB.h:247
__hostdev__ Ray(const Vec3Type &eye=Vec3Type(0, 0, 0), const Vec3Type &direction=Vec3Type(1, 0, 0), RealT t0=Delta< RealT >::value(), RealT t1=Maximum< RealT >::value())
Definition: Ray.h:63
Definition: Ray.h:25
__hostdev__ Ray applyMap(const MapType &map) const
Return a new Ray that is transformed with the specified map.
Definition: Ray.h:189
__hostdev__ const Vec3T & invDir() const
Definition: Ray.h:144
A simple vector class with three components, similar to openvdb::math::Vec3.
Definition: NanoVDB.h:1298
Definition: Ray.h:18
__hostdev__ RealT t1() const
Definition: Ray.h:148
__hostdev__ bool intersects(const BBox< OtherVec3T > &bbox, RealT &t0, RealT &t1) const
Returns true if this ray intersects a floating-point bounding box. If the return value is true t0 and...
Definition: Ray.h:428
T length() const
Definition: NanoVDB.h:1587
__hostdev__ Ray worldToIndexF(const GridType &grid) const
Return a new ray in index space, assuming the existing ray is represented in the world space of the s...
Definition: Ray.h:257
Delta for small floating-point offsets.
Definition: NanoVDB.h:1035
__hostdev__ Vec3T operator()(RealT time) const
Return the position along the ray at the specified time.
Definition: Ray.h:153
Vec3< RealT > Vec3Type
Definition: Ray.h:22
bool isApproxZero(const Type &x)
Definition: NanoVDB.h:1083
__hostdev__ RealT mid() const
Return the midpoint of the ray.
Definition: Ray.h:51
__hostdev__ TimeSpan()
Default constructor.
Definition: Ray.h:29
__hostdev__ Ray & setDir(const Vec3Type &dir)
Definition: Ray.h:89
__hostdev__ bool intersects(const Vec3T &normal, const Vec3T &point, RealT &t) const
Return true if the Ray intersects the plane specified by a normal and point.
Definition: Ray.h:538
__hostdev__ bool clip(const BBoxT &bbox)
Return true if this ray intersects the specified bounding box.
Definition: Ray.h:506
__hostdev__ int sign(int i) const
Definition: Ray.h:150
__hostdev__ bool valid(RealT eps=Delta< float >::value()) const
Return true if t1 is larger than t0 by at least eps.
Definition: Ray.h:174
__hostdev__ Ray & offsetEye(RealT offset)
Definition: Ray.h:75
__hostdev__ bool intersects(const BBoxT &bbox) const
Return true if this ray intersects the specified bounding box.
Definition: Ray.h:467
__hostdev__ Ray & reset(const Vec3Type &eye, const Vec3Type &direction, RealT t0=Delta< RealT >::value(), RealT t1=Maximum< RealT >::value())
Definition: Ray.h:128
Maximum floating-point values.
Definition: NanoVDB.h:1051
T dot(const Vec3T &v) const
Definition: NanoVDB.h:1575
GridType
List of types that are currently supported by NanoVDB.
Definition: NanoVDB.h:317
__hostdev__ Ray indexToWorldF(const GridType &grid) const
Return a new ray in world space, assuming the existing ray is represented in the index space of the s...
Definition: Ray.h:242
RealT t1
Definition: Ray.h:27
float Sqrt(float x)
Return the square root of a floating-point value.
Definition: NanoVDB.h:1233
__hostdev__ bool valid(RealT eps=Delta< RealT >::value()) const
Return true if t1 is larger than t0 by at least eps.
Definition: Ray.h:49
__hostdev__ Ray & setTimes(RealT t0=Delta< RealT >::value(), RealT t1=Maximum< RealT >::value())
Definition: Ray.h:113
__hostdev__ void scale(RealT s)
Multiplies both times.
Definition: Ray.h:53
__hostdev__ Ray & scaleTimes(RealT scale)
Definition: Ray.h:122
__hostdev__ Ray applyInverseMap(const MapType &map) const
Return a new Ray that is transformed with the inverse of the specified map.
Definition: Ray.h:223
__hostdev__ Ray & setMinTime(RealT t0)
Definition: Ray.h:101
#define __hostdev__
Definition: NanoVDB.h:213
__hostdev__ TimeSpan(RealT _t0, RealT _t1)
Constructor.
Definition: Ray.h:31
C++11 implementation of std::is_floating_point.
Definition: NanoVDB.h:462
__hostdev__ bool intersects(const CoordBBox &bbox, RealT &t0, RealT &t1) const
Returns true if this ray intersects an index bounding box. If the return value is true t0 and t1 are ...
Definition: Ray.h:397
__hostdev__ bool clip(const Vec3T &center, RealT radius)
Return true if this ray intersects the specified sphere.
Definition: Ray.h:324