Loading...
Searching...
No Matches
BoundingBox-Impl.hpp
Go to the documentation of this file.
1// This code is based on Jet framework.
2// Copyright (c) 2018 Doyub Kim
3// CubbyFlow is voxel-based fluid simulation engine for computer games.
4// Copyright (c) 2020 CubbyFlow Team
5// Core Part: Chris Ohk, Junwoo Hwang, Jihong Sin, Seungwoo Yoo
6// AI Part: Dongheon Cho, Minseo Kim
7// We are making my contributions/submissions to this project solely in our
8// personal capacity and are not conveying any rights to any intellectual
9// property of any third parties.
10
11#ifndef CUBBYFLOW_BOUNDING_BOX_IMPL_HPP
12#define CUBBYFLOW_BOUNDING_BOX_IMPL_HPP
13
14namespace CubbyFlow
15{
16template <typename T, size_t N>
18{
19 Reset();
20}
21
22template <typename T, size_t N>
24 const VectorType& point2)
25{
26 lowerCorner = Min(point1, point2);
27 upperCorner = Max(point1, point2);
28}
29
30template <typename T, size_t N>
32
33template <typename T, size_t N>
35
36template <typename T, size_t N>
38 default;
39
40template <typename T, size_t N>
42 default;
43
44template <typename T, size_t N>
46{
47 return upperCorner[0] - lowerCorner[0];
48}
49
50template <typename T, size_t N>
51template <typename U>
52std::enable_if_t<(N > 1), U> BoundingBox<T, N>::Height() const
53{
54 return upperCorner[1] - lowerCorner[1];
55}
56
57template <typename T, size_t N>
58template <typename U>
59std::enable_if_t<(N > 2), U> BoundingBox<T, N>::Depth() const
60{
61 return upperCorner[2] - lowerCorner[2];
62}
63
64template <typename T, size_t N>
66{
67 return upperCorner[axis] - lowerCorner[axis];
68}
69
70template <typename T, size_t N>
72{
73 for (size_t i = 0; i < N; ++i)
74 {
75 if (upperCorner[i] < other.lowerCorner[i] ||
76 lowerCorner[i] > other.upperCorner[i])
77 {
78 return false;
79 }
80 }
81
82 return true;
84
85template <typename T, size_t N>
88 for (size_t i = 0; i < N; ++i)
89 {
90 if (upperCorner[i] < point[i] || lowerCorner[i] > point[i])
91 {
92 return false;
93 }
94 }
95
96 return true;
97}
98
99template <typename T, size_t N>
101{
102 T min = 0;
103 T max = std::numeric_limits<T>::max();
104 const VectorType& rayInvDir = T(1) / ray.direction;
106 for (size_t i = 0; i < N; ++i)
107 {
108 T near = (lowerCorner[i] - ray.origin[i]) * rayInvDir[i];
109 T far = (upperCorner[i] - ray.origin[i]) * rayInvDir[i];
110
111 if (near > far)
113 std::swap(near, far);
114 }
116 min = near > min ? near : min;
117 max = far < max ? far : max;
119 if (min > max)
120 {
121 return false;
122 }
123 }
125 return true;
126}
127
128template <typename T, size_t N>
130 const RayType& ray) const
131{
133
134 T min = 0;
135 T max = std::numeric_limits<T>::max();
136 const VectorType& rayInvDir = T(1) / ray.direction;
137
138 for (size_t i = 0; i < N; ++i)
139 {
140 T near = (lowerCorner[i] - ray.origin[i]) * rayInvDir[i];
141 T far = (upperCorner[i] - ray.origin[i]) * rayInvDir[i];
143 if (near > far)
144 {
145 std::swap(near, far);
146 }
147
148 min = near > min ? near : min;
149 max = far < max ? far : max;
150
151 if (min > max)
152 {
153 intersection.isIntersecting = false;
154 return intersection;
155 }
156 }
157
158 intersection.isIntersecting = true;
159
160 if (Contains(ray.origin))
161 {
162 intersection.near = max;
163 intersection.far = std::numeric_limits<T>::max();
164 }
165 else
166 {
167 intersection.near = min;
168 intersection.far = max;
169 }
170
171 return intersection;
172}
173
174template <typename T, size_t N>
176{
177 return (upperCorner + lowerCorner) / static_cast<T>(2);
178}
179
180template <typename T, size_t N>
182{
183 return VectorType(upperCorner - lowerCorner).Length();
184}
185
186template <typename T, size_t N>
188{
189 return VectorType(upperCorner - lowerCorner).LengthSquared();
190}
191
192template <typename T, size_t N>
194{
195 lowerCorner = VectorType::MakeConstant(std::numeric_limits<T>::max());
196 upperCorner = VectorType::MakeConstant(-std::numeric_limits<T>::max());
197}
198
199template <typename T, size_t N>
201{
202 lowerCorner = Min(lowerCorner, point);
203 upperCorner = Max(upperCorner, point);
204}
205
206template <typename T, size_t N>
208{
209 lowerCorner = Min(lowerCorner, other.lowerCorner);
210 upperCorner = Max(upperCorner, other.upperCorner);
211}
212
213template <typename T, size_t N>
215{
216 lowerCorner -= delta;
217 upperCorner += delta;
218}
219
220template <typename T, size_t N>
222 size_t idx) const
223{
225 for (size_t i = 0; i < N; ++i)
226 {
227 ret[i] = lowerCorner[i] + (((ONE_SIZE << i) & idx) != 0) *
228 (upperCorner[i] - lowerCorner[i]);
229 }
230 return ret;
231}
232
233template <typename T, size_t N>
235 const VectorType& point) const
236{
237 return CubbyFlow::Clamp(point, lowerCorner, upperCorner);
238}
239
240template <typename T, size_t N>
242{
243 for (size_t i = 0; i < N; ++i)
244 {
245 if (lowerCorner[i] >= upperCorner[i])
246 {
247 return true;
248 }
249 }
250
251 return false;
252}
253
254template <typename T, size_t N>
255template <typename U>
257{
258 return BoundingBox<U, N>{ lowerCorner.template CastTo<U>(),
259 upperCorner.template CastTo<U>() };
260}
261} // namespace CubbyFlow
262
263#endif
N-D axis-aligned bounding box class.
Definition BoundingBox.hpp:47
T Width() const
Returns width of the box.
Definition BoundingBox-Impl.hpp:45
bool Contains(const VectorType &point) const
Returns true if the input vector is inside of this box.
Definition BoundingBox-Impl.hpp:86
bool Intersects(const RayType &ray) const
Returns true if the input ray is intersecting with this box.
Definition BoundingBox-Impl.hpp:100
BoundingBoxRayIntersection< T > ClosestIntersection(const RayType &ray) const
Definition BoundingBox-Impl.hpp:129
T Length(size_t axis)
Returns length of the box in given axis.
Definition BoundingBox-Impl.hpp:65
VectorType MidPoint() const
Returns the mid-point of this box.
Definition BoundingBox-Impl.hpp:175
VectorType Corner(size_t idx) const
Returns corner position. Index starts from x-first order.
Definition BoundingBox-Impl.hpp:221
T DiagonalLength() const
Returns diagonal length of this box.
Definition BoundingBox-Impl.hpp:181
void Reset()
Resets this box to initial state (min=infinite, max=-infinite).
Definition BoundingBox-Impl.hpp:193
bool IsEmpty() const
Returns true if the box is empty.
Definition BoundingBox-Impl.hpp:241
void Merge(const VectorType &point)
Merges this and other point.
Definition BoundingBox-Impl.hpp:200
BoundingBox & operator=(const BoundingBox &other)
Copy assignment operator.
void Expand(T delta)
Definition BoundingBox-Impl.hpp:214
T DiagonalLengthSquared() const
Returns squared diagonal length of this box.
Definition BoundingBox-Impl.hpp:187
BoundingBox()
Default constructor.
Definition BoundingBox-Impl.hpp:17
bool Overlaps(const BoundingBox &other) const
Returns true of this box and other box overlaps.
Definition BoundingBox-Impl.hpp:71
BoundingBox< U, N > CastTo() const
Returns box with different value type.
Definition BoundingBox-Impl.hpp:256
VectorType Clamp(const VectorType &point) const
Returns the clamped point.
Definition BoundingBox-Impl.hpp:234
ValueType Length() const
Definition MatrixExpression-Impl.hpp:278
ValueType Min() const
Definition MatrixExpression-Impl.hpp:99
ValueType LengthSquared() const
Definition MatrixExpression-Impl.hpp:286
ValueType Max() const
Definition MatrixExpression-Impl.hpp:120
Definition Matrix.hpp:30
Class for N-D ray.
Definition Ray.hpp:26
Definition pybind11Utils.hpp:22
constexpr size_t ONE_SIZE
One size_t.
Definition Constants.hpp:47
std::enable_if_t< std::is_arithmetic< T >::value, T > Clamp(T val, T low, T high)
Returns the clamped value.
Definition MathUtils-Impl.hpp:166
Matrix< T, Rows, 1 > Vector
Definition Matrix.hpp:648