1#ifndef TATOOINE_AXIS_ALIGNED_BOUNDING_BOX_H
2#define TATOOINE_AXIS_ALIGNED_BOUNDING_BOX_H
20template <
typename AABB,
typename Real, std::
size_t NumDimensions>
28 return *
dynamic_cast<AABB const*
>(
this);
36 enum Quadrant { right, left, middle };
39 auto quadrant = make_array<Quadrant, NumDimensions>();
40 auto which_plane = std::size_t(0);
41 auto max_t = make_array<Real, NumDimensions>();
42 auto candidate_plane = make_array<Real, NumDimensions>();
46 for (std::size_t i = 0; i < NumDimensions; i++)
49 candidate_plane[i] =
aabb.
min(i);
53 candidate_plane[i] =
aabb.
max(i);
66 for (std::size_t i = 0; i < NumDimensions; i++)
67 if (quadrant[i] != middle && r.
direction(i) != 0) {
75 for (std::size_t i = 1; i < NumDimensions; i++)
76 if (max_t[which_plane] < max_t[i]) {
81 if (max_t[which_plane] < 0) {
84 for (std::size_t i = 0; i < NumDimensions; i++)
85 if (which_plane != i) {
91 coord(i) = candidate_plane[i];
100template <
typename Real, std::
size_t NumDimensions>
103 axis_aligned_bounding_box<Real, NumDimensions>, Real, NumDimensions> {
104 static_assert(is_arithmetic<Real>);
135 template <
typename Real0,
typename Real1>
140 template <
typename Real0,
typename Real1>
145 template <
typename Tensor0,
typename Tensor1,
typename Real0,
typename Real1>
151 auto constexpr min() const -> auto const& {
return m_min; }
153 auto constexpr min(std::size_t i)
const ->
auto const& {
return m_min(i); }
154 auto constexpr min(std::size_t i) ->
auto& {
return m_min(i); }
156 auto constexpr max() const -> auto const& {
return m_max; }
158 auto constexpr max(std::size_t i)
const ->
auto const& {
return m_max(i); }
159 auto constexpr max(std::size_t i) ->
auto& {
return m_max(i); }
165 template <std::size_t... Is>
166 auto constexpr area(std::index_sequence<Is...> )
const {
168 return (ext(Is) * ...);
172 return area(std::make_index_sequence<NumDimensions>{});
176 template <std::size_t... Is>
177 auto constexpr volume(std::index_sequence<Is...> )
const {
178 return (
extent(Is) * ...);
187 auto constexpr center(std::size_t
const i)
const {
192 for (std::size_t i = 0; i < NumDimensions; ++i) {
206 requires(NumDimensions == 2) {
215 auto const f0 = x1 - x0;
216 auto const f1 = x3 - x0;
224 auto const p0 =
dot(x0, axis);
225 auto const p1 =
dot(x1, axis);
226 auto const p2 =
dot(x2, axis);
227 auto const p3 =
dot(x3, axis);
235 e.x() * std::abs(
dot(u0, axis)) + e.y() * std::abs(
dot(u1, axis));
257 requires(NumDimensions == 2) {
260 auto const x0_centered = x0 - c;
261 auto const x1_centered = x1 - c;
262 auto const x2_centered = x2 - c;
263 constexpr auto u0 =
vec_type {1, 0};
264 constexpr auto u1 =
vec_type {0, 1};
267 auto const p0 =
dot(x0_centered, axis);
268 auto const p1 =
dot(x1_centered, axis);
269 auto const p2 =
dot(x2_centered, axis);
277 e.x() * std::abs(
dot(u0, axis)) + e.y() * std::abs(
dot(u1, axis));
304 requires(NumDimensions == 3) {
312 auto const f0 = x1 - x0;
313 auto const f1 = x2 - x1;
314 auto const f2 = x0 - x2;
321 auto const p0 =
dot(x0, axis);
322 auto const p1 =
dot(x1, axis);
323 auto const p2 =
dot(x2, axis);
324 auto r = e.x() * std::abs(
dot(u0, axis)) +
325 e.y() * std::abs(
dot(u1, axis)) +
326 e.z() * std::abs(
dot(u2, axis));
375 requires(NumDimensions == 3) {
384 auto const f0 = x1 - x0;
385 auto const f1 = x2 - x1;
386 auto const f2 = x0 - x2;
387 auto const f3 = x3 - x1;
388 auto const f4 = x2 - x3;
389 auto const f5 = x3 - x0;
396 auto const p0 =
dot(x0, axis);
397 auto const p1 =
dot(x1, axis);
398 auto const p2 =
dot(x2, axis);
399 auto const p3 =
dot(x3, axis);
400 auto r = e.x() * std::abs(
dot(u0, axis)) +
401 e.y() * std::abs(
dot(u1, axis)) +
402 e.z() * std::abs(
dot(u2, axis));
493 for (std::size_t i = 0; i < NumDimensions; ++i) {
494 m_min(i) = std::numeric_limits<Real>::max();
495 m_max(i) = -std::numeric_limits<Real>::max();
500 Real
const max)
const {
502 for (std::size_t i = 0; i < NumDimensions; ++i) {
506 addeddim.
m_min(NumDimensions) =
min;
507 addeddim.
m_max(NumDimensions) =
max;
511 template <
typename RandomEngine = std::mt19937_64>
513 std::random_device{}()})
const {
515 for (std::size_t i = 0; i < NumDimensions; ++i) {
516 std::uniform_real_distribution<Real> distribution{
m_min(i),
m_max(i)};
517 p(i) = distribution(random_engine);
525 std::vector<vec<real_type, 3>> positions;
526 std::vector<std::vector<std::size_t>> indices;
536 indices.push_back({0, 1, 2, 3, 0});
537 indices.push_back({4, 5, 6, 7, 4});
538 indices.push_back({0, 4});
539 indices.push_back({1, 5});
540 indices.push_back({2, 6});
541 indices.push_back({3, 7});
542 f.write_points(positions);
543 f.write_lines(indices);
546template <std::
size_t NumDimensions>
548template <
typename Real>
550template <
typename Real>
552template <
typename Real, std::
size_t NumDimensions>
565template <
typename Real0,
typename Real1, std::
size_t NumDimensions>
570template <
typename Real0,
typename Real1, std::
size_t NumDimensions>
575template <
typename Tensor0,
typename Tensor1,
typename Real0,
typename Real1,
576 std::size_t NumDimensions>
584template <
typename Real, std::
size_t NumDimensions>
588 out << std::scientific;
589 for (std::size_t i = 0; i < NumDimensions; ++i) {
591 if (bb.min(i) >= 0) {
594 out << bb.min(i) <<
" .. ";
595 if (bb.max(i) >= 0) {
598 out << bb.max(i) <<
" ]\n";
600 out << std::defaultfloat;
Definition: vtk_legacy.h:448
Definition: vtp_writer.h:3
Definition: algorithm.h:6
auto operator<<(std::ostream &out, linspace< Real > const &l) -> auto &
Definition: linspace.h:165
auto is_separating_axis(vec< Real, 2 > const &n, std::vector< vec< Real, 2 > > const &polygon0, std::vector< vec< Real, 2 > > const &polygon1)
Return true if n is a separating axis of polygon0 and polygon1.
Definition: separating_axis_theorem.h:12
constexpr auto max(A &&a, B &&b)
Definition: math.h:20
constexpr auto dot(base_tensor< Tensor0, T0, N > const &lhs, base_tensor< Tensor1, T1, N > const &rhs)
Definition: tensor_operations.h:120
constexpr auto min(A &&a, B &&b)
Definition: math.h:15
constexpr auto cross(base_tensor< Tensor0, T0, 3 > const &lhs, base_tensor< Tensor1, T1, 3 > const &rhs)
Definition: cross.h:9
Definition: axis_aligned_bounding_box.h:103
auto constexpr min(std::size_t i) const -> auto const &
Definition: axis_aligned_bounding_box.h:153
vec< Real, NumDimensions > vec_type
Definition: axis_aligned_bounding_box.h:108
auto constexpr is_inside(pos_type const &p) const
Definition: axis_aligned_bounding_box.h:191
~axis_aligned_bounding_box()=default
auto constexpr max() -> auto &
Definition: axis_aligned_bounding_box.h:157
constexpr axis_aligned_bounding_box()
Definition: axis_aligned_bounding_box.h:122
pos_type m_min
Definition: axis_aligned_bounding_box.h:118
auto constexpr max() const -> auto const &
Definition: axis_aligned_bounding_box.h:156
constexpr auto operator=(axis_aligned_bounding_box const &other) -> axis_aligned_bounding_box &=default
auto constexpr volume() const
Definition: axis_aligned_bounding_box.h:182
auto constexpr center() const
Definition: axis_aligned_bounding_box.h:186
auto constexpr area(std::index_sequence< Is... >) const
Definition: axis_aligned_bounding_box.h:166
auto constexpr center(std::size_t const i) const
Definition: axis_aligned_bounding_box.h:187
constexpr auto is_simplex_inside(vec< Real, 3 > x0, vec< Real, 3 > x1, vec< Real, 3 > x2, vec< Real, 3 > x3) const
Definition: axis_aligned_bounding_box.h:373
constexpr axis_aligned_bounding_box(vec< Real0, NumDimensions > &&min, vec< Real1, NumDimensions > &&max) noexcept
Definition: axis_aligned_bounding_box.h:136
auto constexpr max(std::size_t i) const -> auto const &
Definition: axis_aligned_bounding_box.h:158
auto constexpr min() const -> auto const &
Definition: axis_aligned_bounding_box.h:151
constexpr auto reset()
Definition: axis_aligned_bounding_box.h:492
constexpr auto add_dimension(Real const min, Real const max) const
Definition: axis_aligned_bounding_box.h:499
pos_type m_max
Definition: axis_aligned_bounding_box.h:119
constexpr axis_aligned_bounding_box(vec< Real0, NumDimensions > const &min, vec< Real1, NumDimensions > const &max)
Definition: axis_aligned_bounding_box.h:141
constexpr axis_aligned_bounding_box(axis_aligned_bounding_box &&other) noexcept=default
auto write_vtk(filesystem::path const &path)
Definition: axis_aligned_bounding_box.h:522
static constexpr auto num_dimensions() -> std::size_t
Definition: axis_aligned_bounding_box.h:111
constexpr axis_aligned_bounding_box(axis_aligned_bounding_box const &other)=default
auto constexpr volume(std::index_sequence< Is... >) const
Definition: axis_aligned_bounding_box.h:177
vec_type pos_type
Definition: axis_aligned_bounding_box.h:109
auto constexpr min(std::size_t i) -> auto &
Definition: axis_aligned_bounding_box.h:154
constexpr auto is_rectangle_inside(vec< Real, 2 > x0, vec< Real, 2 > x1, vec< Real, 2 > x2, vec< Real, 2 > x3) const
Definition: axis_aligned_bounding_box.h:204
constexpr auto operator+=(pos_type const &point)
Definition: axis_aligned_bounding_box.h:485
auto constexpr extent(std::size_t i) const
Definition: axis_aligned_bounding_box.h:162
static constexpr auto infinite()
Definition: axis_aligned_bounding_box.h:112
constexpr auto is_simplex_inside(vec< Real, 2 > const &x0, vec< Real, 2 > const &x1, vec< Real, 2 > const &x2) const
Definition: axis_aligned_bounding_box.h:254
auto constexpr min() -> auto &
Definition: axis_aligned_bounding_box.h:152
auto random_point(RandomEngine &&random_engine=RandomEngine{ std::random_device{}()}) const
Definition: axis_aligned_bounding_box.h:512
constexpr axis_aligned_bounding_box(base_tensor< Tensor0, Real0, NumDimensions > const &min, base_tensor< Tensor1, Real1, NumDimensions > const &max)
Definition: axis_aligned_bounding_box.h:146
auto constexpr max(std::size_t i) -> auto &
Definition: axis_aligned_bounding_box.h:159
constexpr auto is_simplex_inside(vec< Real, 3 > x0, vec< Real, 3 > x1, vec< Real, 3 > x2) const
Definition: axis_aligned_bounding_box.h:302
auto constexpr area() const
Definition: axis_aligned_bounding_box.h:171
auto constexpr extents() const
Definition: axis_aligned_bounding_box.h:161
constexpr auto operator=(axis_aligned_bounding_box &&other) noexcept -> axis_aligned_bounding_box &=default
Real real_type
Definition: axis_aligned_bounding_box.h:106
Definition: base_tensor.h:23
Definition: axis_aligned_bounding_box.h:21
auto check_intersection(ray_type const &r, Real const =0) const -> optional_intersection_type override
Definition: axis_aligned_bounding_box.h:33
auto as_aabb() const -> auto const &
Definition: axis_aligned_bounding_box.h:27
std::optional< intersection_type > optional_intersection_type
Definition: ray_intersectable.h:14
Definition: intersection.h:13
Definition: ray_intersectable.h:10
ray< real_type, NumDimensions > ray_type
Definition: ray_intersectable.h:15
std::optional< intersection_type > optional_intersection_type
Definition: ray_intersectable.h:14
intersection< real_type, NumDimensions > intersection_type
Definition: ray_intersectable.h:13
auto direction() -> auto &
Definition: ray.h:54
auto origin() -> auto &
Definition: ray.h:41
static auto constexpr num_components()
Definition: base_tensor.h:43
static auto constexpr ones()
Definition: vec.h:28
static auto constexpr zeros()
Definition: vec.h:26