ray: add ray-sphere intersection test
This commit is contained in:
parent
7e2baf6751
commit
8863ebafe9
25
ray.cpp
25
ray.cpp
@ -71,6 +71,31 @@ util::ray<S,T>::intersect (AABB<S,T> r) const
|
||||
}
|
||||
|
||||
|
||||
///----------------------------------------------------------------------------
|
||||
/// returns the smallest distance from ray origin to a sphere intersection
|
||||
///
|
||||
/// returns NaN on miss
|
||||
template <size_t S, typename T>
|
||||
T
|
||||
util::ray<S,T>::intersect (sphere<S,T> s) const
|
||||
{
|
||||
T b = dot (d, p - s.c);
|
||||
T c = dot (p - s.c, p - s.c) - s.r * s.r;
|
||||
|
||||
T D = b * b - c;
|
||||
if (D < 0)
|
||||
return std::numeric_limits<T>::quiet_NaN ();
|
||||
|
||||
auto t_ = std::sqrt (D);
|
||||
auto t0 = -b + t_;
|
||||
auto t1 = -b - t_;
|
||||
|
||||
return t1 >= 0 ? t1 :
|
||||
t0 >= 0 ? t0 :
|
||||
std::numeric_limits<T>::quiet_NaN ();
|
||||
}
|
||||
|
||||
|
||||
///----------------------------------------------------------------------------
|
||||
/// returns the closest parameter along the ray to a given point
|
||||
template <size_t S, typename T>
|
||||
|
7
ray.hpp
7
ray.hpp
@ -18,9 +18,11 @@
|
||||
#define __UTIL_RAY_HPP
|
||||
|
||||
#include "point.hpp"
|
||||
#include "vector.hpp"
|
||||
#include "plane.hpp"
|
||||
|
||||
#include "aabb.hpp"
|
||||
#include "plane.hpp"
|
||||
#include "sphere.hpp"
|
||||
#include "vector.hpp"
|
||||
|
||||
namespace util {
|
||||
template <size_t S, typename T>
|
||||
@ -30,6 +32,7 @@ namespace util {
|
||||
|
||||
T intersect (plane<S,T>) const;
|
||||
T intersect (AABB<S,T>) const;
|
||||
T intersect (sphere<S,T>) const;
|
||||
|
||||
T closest (point<S,T>) const;
|
||||
|
||||
|
11
test/ray.cpp
11
test/ray.cpp
@ -40,7 +40,16 @@ test_intersect_aabb (util::TAP::logger &tap)
|
||||
void
|
||||
test_intersect_sphere (util::TAP::logger &tap)
|
||||
{
|
||||
;
|
||||
const util::sphere3f s = {{0.f, 0.f, 0.f}, 1.f};
|
||||
|
||||
const util::ray3f r0 {{0.f, 2.f, 0.f}, {0.f, -1.f, 0.f}};
|
||||
tap.expect_eq (r0.intersect (s), 1.f, "ray-sphere simple");
|
||||
|
||||
const util::ray3f r1 {{0.f, 1.f, 0.f}, {0.f, 1.f, 0.f}};
|
||||
tap.expect_eq (r1.intersect (s), 0.f, "ray-sphere adjacent");
|
||||
|
||||
const util::ray3f r2 {{0.f, 2.f, 0.f}, {0.f, 1.f, 0.f}};
|
||||
tap.expect_nan (r2.intersect (s), "ray-sphere no-intersect");
|
||||
}
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user