File indexing completed on 2025-09-17 09:13:46
0001 #ifndef BVH_V2_RAY_H
0002 #define BVH_V2_RAY_H
0003
0004 #include "bvh/v2/vec.h"
0005
0006 namespace bvh::v2 {
0007
0008 struct Octant {
0009 uint32_t value = 0;
0010 static constexpr size_t max_dim = sizeof(value) * CHAR_BIT;
0011
0012 uint32_t operator [] (size_t i) const { return (value >> i) & uint32_t{1}; }
0013 };
0014
0015 template <typename T, size_t N>
0016 struct Ray {
0017 Vec<T, N> org, dir;
0018 T tmin, tmax;
0019
0020 Ray() = default;
0021 BVH_ALWAYS_INLINE Ray(
0022 const Vec<T, N>& org,
0023 const Vec<T, N>& dir,
0024 T tmin = 0,
0025 T tmax = std::numeric_limits<T>::max())
0026 : org(org), dir(dir), tmin(tmin), tmax(tmax)
0027 {}
0028
0029 template <bool SafeInverse = false>
0030 BVH_ALWAYS_INLINE Vec<T, N> get_inv_dir() const {
0031 return Vec<T, N>::generate([&] (size_t i) {
0032 return SafeInverse ? safe_inverse(dir[i]) : static_cast<T>(1) / dir[i];
0033 });
0034 }
0035
0036 BVH_ALWAYS_INLINE Octant get_octant() const {
0037 static_assert(N <= Octant::max_dim);
0038 Octant octant;
0039 static_for<0, N>([&] (size_t i) {
0040 octant.value |= std::signbit(dir[i]) * (uint32_t{1} << i);
0041 });
0042 return octant;
0043 }
0044
0045
0046 BVH_ALWAYS_INLINE static Vec<T, N> pad_inv_dir(const Vec<T, N>& inv_dir) {
0047 return Vec<T, N>::generate([&] (size_t i) { return add_ulp_magnitude(inv_dir[i], 2); });
0048 }
0049 };
0050
0051 }
0052
0053 #endif