32 #ifndef HERMES_HERMES_NUMERIC_INTERPOLATION_H
33 #define HERMES_HERMES_NUMERIC_INTERPOLATION_H
40 namespace hermes::interpolation {
47 return fmaxf(0.f, 1.f - a / (b * b));
54 return fmaxf(h * h / fmaxf(r2,
static_cast<f32>(1.0e-5)) - 1.0f, 0.0f);
63 return t * t * (3.f - 2 * t);
76 return t * t * (Vector2<T>(3.f, 3.f) - T(2) * t);
94 return x * (1.f - a) + y * a;
114 inline T bilerp(T x, T y,
const T &f00,
const T &f10,
const T &f11,
116 return lerp(y, lerp(x, f00, f10), lerp(x, f01, f11));
135 inline T trilerp(T tx, T ty, T tz,
const T &f000,
const T &f100,
const T &f010,
136 const T &f110,
const T &f001,
const T &f101,
const T &f011,
138 return lerp(bilerp(f000, f100, f010, f110, tx, ty),
139 bilerp(f001, f101, f011, f111, tx, ty), tz);
148 return (t <
static_cast<T
>(0.5)) ? a : b;
168 double Dk = fkp1 - fk;
169 double dk = (fkp1 - fkm1) * 0.5;
170 double dkp1 = (fkp2 - fk) * 0.5;
171 if (fabsf(Dk) < 1e-12)
183 double a2 = 3 * Dk - 2 * dk - dkp1;
184 double a3 = dk + dkp1 - 2 * Dk;
185 T ans = a3 * tmtk * tmtk * tmtk + a2 * tmtk * tmtk + a1 * tmtk + a0;
186 #ifdef HERMES_DEVICE_ENABLED
187 T m = fminf(fkm1, fminf(fk, fminf(fkp1, fkp2)));
188 T M = fmaxf(fkm1, fmaxf(fk, fmaxf(fkp1, fkp2)));
189 return fminf(M, fmaxf(m, ans));
191 T m = std::min(fkm1, std::min(fk, std::min(fkp1, fkp2)));
192 T M = std::max(fkm1, std::max(fk, std::max(fkp1, fkp2)));
193 return std::min(M, std::max(m, ans));
214 float monotonicCubicInterpolate(T f[4][4],
const point2 &t) {
216 for (
int d = 0; d < 4; d++)
217 v[d] = monotonicCubicInterpolate(f[0][d], f[1][d], f[2][d], f[3][d], t.
x);
218 return monotonicCubicInterpolate(v[0], v[1], v[2], v[3], t.
y);
231 static float monotonicCubicInterpolate(T f[4][4][4],
const point3 &t) {
233 for (
int dz = -1, iz = 0; dz <= 2; dz++, iz++)
234 for (
int dy = -1, iy = 0; dy <= 2; dy++, iy++)
235 v[iy][iz] = monotonicCubicInterpolate(
236 f[0][dy + 1][dz + 1], f[1][dy + 1][dz + 1], f[2][dy + 1][dz + 1],
237 f[3][dy + 1][dz + 1], t.x);
239 for (
int d = 0; d < 4; d++)
240 vv[d] = monotonicCubicInterpolate(v[0][d], v[1][d], v[2][d], v[3][d], t.y);
241 return monotonicCubicInterpolate(vv[0], vv[1], vv[2], vv[3], t.z);
252 template<
typename S,
typename T>
254 const S &f0,
const S &f1,
const S &f2,
const S &f3, T f) {
255 S d1 = (f2 - f0) / 2;
256 S d2 = (f3 - f1) / 2;
259 S a3 = d1 + d2 - 2 * D1;
260 S a2 = 3 * D1 - 2 * d1 - d2;
264 return a3 * CUBE(f) + a2 * SQR(f) + a1 * f + a0;
T y
1-th component
Definition: point.h:140
T x
0-th component
Definition: point.h:139
#define HERMES_DEVICE_CALLABLE
Specifies that the function can be called from both host and device sides.
Definition: defs.h:45
float f32
32 bit size floating point type
Definition: defs.h:78
HERMES_DEVICE_CALLABLE T monotonicCubicInterpolate(T fkm1, T fk, T fkp1, T fkp2, T tmtk)
Computes 1-dimension monotonic cubic interpolation.
Definition: interpolation.h:167
Set of multi-dimensional size representations.
static HERMES_DEVICE_CALLABLE T clamp(const T &n, const T &l, const T &u)
Clamps value to closed interval.
Definition: numeric.h:176
static HERMES_DEVICE_CALLABLE int sign(T a)
Computes sign.
Definition: numeric.h:202