MathUtils-Impl.h
Go to the documentation of this file.
1 /*************************************************************************
2 > File Name: MathUtils.cpp
3 > Project Name: CubbyFlow
4 > Author: Chan-Ho Chris Ohk
5 > Purpose: Mathematics util functions for CubbyFlow.
6 > Created Time: 2017/02/27
7 > Copyright (c) 2018, Chan-Ho Chris Ohk
8 *************************************************************************/
9 #ifndef CUBBYFLOW_MATH_UTILS_IMPL_H
10 #define CUBBYFLOW_MATH_UTILS_IMPL_H
11 
12 #include <Core/Utils/Constants.h>
13 
14 #include <algorithm>
15 #include <cmath>
16 
17 namespace CubbyFlow
18 {
19  template <typename T>
20  inline bool Similar(T x, T y, T eps)
21  {
22  return (std::abs(x - y) <= eps);
23  }
24 
25  template <typename T>
26  inline T Sign(T x)
27  {
28  if (x >= 0)
29  {
30  return 1;
31  }
32  else
33  {
34  return -1;
35  }
36  }
37 
38  template <typename T>
39  inline T AbsMin(T x, T y)
40  {
41  return (x * x < y * y) ? x : y;
42  }
43 
44  template <typename T>
45  inline T AbsMax(T x, T y)
46  {
47  return (x * x > y * y) ? x : y;
48  }
49 
50  template <typename T>
51  inline T AbsMinN(const T* x, size_t n)
52  {
53  T m = x[0];
54 
55  for (size_t i = 1; i < n; i++)
56  {
57  m = AbsMin(m, x[i]);
58  }
59 
60  return m;
61  }
62 
63  template <typename T>
64  inline T AbsMaxN(const T* x, size_t n)
65  {
66  T m = x[0];
67 
68  for (size_t i = 1; i < n; i++)
69  {
70  m = AbsMax(m, x[i]);
71  }
72 
73  return m;
74  }
75 
76  template <typename T>
77  inline size_t ArgMin2(T x, T y)
78  {
79  return (x < y) ? 0 : 1;
80  }
81 
82  template <typename T>
83  inline size_t ArgMax2(T x, T y)
84  {
85  return (x > y) ? 0 : 1;
86  }
87 
88  template <typename T>
89  inline size_t ArgMin3(T x, T y, T z)
90  {
91  if (x < y)
92  {
93  return (x < z) ? 0 : 2;
94  }
95 
96  return (y < z) ? 1 : 2;
97  }
98 
99  template <typename T>
100  inline size_t ArgMax3(T x, T y, T z)
101  {
102  if (x > y)
103  {
104  return (x > z) ? 0 : 2;
105  }
106 
107  return (y > z) ? 1 : 2;
108  }
109 
110  template <typename T>
111  inline T Square(T x)
112  {
113  return x * x;
114  }
115 
116  template <typename T>
117  inline T Cubic(T x)
118  {
119  return x * x * x;
120  }
121 
122  template <typename T>
123  inline T Clamp(T val, T low, T high)
124  {
125  if (val < low)
126  {
127  return low;
128  }
129 
130  if (val > high)
131  {
132  return high;
133  }
134 
135  return val;
136  }
137 
138  template <typename T>
139  inline T DegreesToRadians(T angleInDegrees)
140  {
141  return angleInDegrees * PI<T>() / 180;
142  }
143 
144  template <typename T>
145  inline T RadiansToDegrees(T angleInRadians)
146  {
147  return angleInRadians * 180 / PI<T>();
148  }
149 
150  template<typename T>
151  inline void GetBarycentric(T x, ssize_t iLow, ssize_t iHigh, ssize_t* i, T* f)
152  {
153  T s = std::floor(x);
154  *i = static_cast<ssize_t>(s);
155 
156  ssize_t offset = -iLow;
157  iLow += offset;
158  iHigh += offset;
159 
160  if (iLow == iHigh)
161  {
162  *i = iLow;
163  *f = 0;
164  }
165  else if (*i < iLow)
166  {
167  *i = iLow;
168  *f = 0;
169  }
170  else if (*i > iHigh - 1)
171  {
172  *i = iHigh - 1;
173  *f = 1;
174  }
175  else
176  {
177  *f = static_cast<T>(x - s);
178  }
179 
180  *i -= offset;
181  }
182 
183  template<typename S, typename T>
184  inline S Lerp(const S& value0, const S& value1, T f)
185  {
186  return (1 - f) * value0 + f * value1;
187  }
188 
189  template<typename S, typename T>
190  inline S BiLerp(
191  const S& f00, const S& f10,
192  const S& f01, const S& f11,
193  T tx, T ty)
194  {
195  return Lerp(Lerp(f00, f10, tx), Lerp(f01, f11, tx), ty);
196  }
197 
198  template<typename S, typename T>
199  inline S TriLerp(
200  const S& f000, const S& f100,
201  const S& f010, const S& f110,
202  const S& f001, const S& f101,
203  const S& f011, const S& f111,
204  T tx, T ty, T fz)
205  {
206  return Lerp(
207  BiLerp(f000, f100, f010, f110, tx, ty),
208  BiLerp(f001, f101, f011, f111, tx, ty),
209  fz);
210  }
211 
212  template <typename S, typename T>
213  inline S CatmullRom(const S& f0, const S& f1, const S& f2, const S& f3, T f)
214  {
215  S d1 = (f2 - f0) / 2;
216  S d2 = (f3 - f1) / 2;
217  S D1 = f2 - f1;
218 
219  S a3 = d1 + d2 - 2 * D1;
220  S a2 = 3 * D1 - 2 * d1 - d2;
221  S a1 = d1;
222  S a0 = f1;
223 
224  return a3 * Cubic(f) + a2 * Square(f) + a1 * f + a0;
225  }
226 
227  template <typename T>
228  inline T MonotonicCatmullRom(const T& f0, const T& f1, const T& f2, const T& f3, T f)
229  {
230  T d1 = (f2 - f0) / 2;
231  T d2 = (f3 - f1) / 2;
232  T D1 = f2 - f1;
233 
234  if (std::fabs(D1) < std::numeric_limits<double>::epsilon())
235  {
236  d1 = d2 = 0;
237  }
238 
239  if (Sign(D1) != Sign(d1))
240  {
241  d1 = 0;
242  }
243 
244  if (Sign(D1) != Sign(d2))
245  {
246  d2 = 0;
247  }
248 
249  T a3 = d1 + d2 - 2 * D1;
250  T a2 = 3 * D1 - 2 * d1 - d2;
251  T a1 = d1;
252  T a0 = f1;
253 
254  return a3 * Cubic(f) + a2 * Square(f) + a1 * f + a0;
255  }
256 }
257 
258 #endif
T AbsMin(T x, T y)
Returns the absolute minimum value among the two inputs.
Definition: MathUtils-Impl.h:39
S Lerp(const S &value0, const S &value1, T f)
Computes linear interpolation.
Definition: MathUtils-Impl.h:184
T AbsMaxN(const T *x, size_t n)
Returns absolute maximum among n-elements.
Definition: MathUtils-Impl.h:64
size_t ArgMin2(T x, T y)
Definition: MathUtils-Impl.h:77
T Square(T x)
Returns the square of x.
Definition: MathUtils-Impl.h:111
size_t ArgMax3(T x, T y, T z)
Definition: MathUtils-Impl.h:100
size_t ArgMax2(T x, T y)
Definition: MathUtils-Impl.h:83
S CatmullRom(const S &f0, const S &f1, const S &f2, const S &f3, T f)
Computes Catmull-Rom interpolation.
Definition: MathUtils-Impl.h:213
T AbsMinN(const T *x, size_t n)
Returns absolute minimum among n-elements.
Definition: MathUtils-Impl.h:51
Definition: pybind11Utils.h:24
T Clamp(T val, T low, T high)
Returns the clamped value.
Definition: MathUtils-Impl.h:123
S BiLerp(const S &f00, const S &f10, const S &f01, const S &f11, T tx, T ty)
Computes bilinear interpolation.
Definition: MathUtils-Impl.h:190
T Cubic(T x)
Returns the cubic of x.
Definition: MathUtils-Impl.h:117
S TriLerp(const S &f000, const S &f100, const S &f010, const S &f110, const S &f001, const S &f101, const S &f011, const S &f111, T tx, T ty, T fz)
Computes trilinear interpolation.
Definition: MathUtils-Impl.h:199
bool Similar(T x, T y, T eps)
Returns true if x and y are similar.
Definition: MathUtils-Impl.h:20
T MonotonicCatmullRom(const T &f0, const T &f1, const T &f2, const T &f3, T f)
Computes monotonic Catmull-Rom interpolation.
Definition: MathUtils-Impl.h:228
T AbsMax(T x, T y)
Returns the absolute maximum value among the two inputs.
Definition: MathUtils-Impl.h:45
T Sign(T x)
Returns the sign of the value.
Definition: MathUtils-Impl.h:26
size_t ArgMin3(T x, T y, T z)
Definition: MathUtils-Impl.h:89
T DegreesToRadians(T angleInDegrees)
Converts degrees to radians.
Definition: MathUtils-Impl.h:139
T RadiansToDegrees(T angleInRadians)
Converts radians to degrees.
Definition: MathUtils-Impl.h:145
void GetBarycentric(T x, ssize_t iLow, ssize_t iHigh, ssize_t *i, T *f)
Gets the barycentric coordinate.
Definition: MathUtils-Impl.h:151