| @@ -15,8 +15,6 @@ | |||||
| src/lol/math/geometry.h | src/lol/math/geometry.h | ||||
| src/lol/math/interp.h (but what is it?) | src/lol/math/interp.h (but what is it?) | ||||
| src/numeric.h | |||||
| ## headers to keep in the engine | ## headers to keep in the engine | ||||
| @@ -21,6 +21,9 @@ | |||||
| #include <cstdio> | #include <cstdio> | ||||
| #include <algorithm> | #include <algorithm> | ||||
| #include <type_traits> | #include <type_traits> | ||||
| #if defined __cpp_lib_int_pow2 | |||||
| #include <bit> | |||||
| #endif | |||||
| #include <stdint.h> | #include <stdint.h> | ||||
| @@ -126,6 +129,24 @@ template<typename T, typename T2 = LOL_T_FLOATING_POINT> | |||||
| return mix(a, b, x); | return mix(a, b, x); | ||||
| } | } | ||||
| // Round up to next power of two | |||||
| template<typename T, typename T2=LOL_T_INTEGRAL> | |||||
| [[nodiscard]] static inline T2 bit_ceil(T x) | |||||
| { | |||||
| #if defined __cpp_lib_int_pow2 | |||||
| return std::bit_ceil(x); | |||||
| #else | |||||
| x = x - 1; | |||||
| if constexpr (sizeof(x) > 4) x |= uint64_t(x) >> 32; | |||||
| if constexpr (sizeof(x) > 2) x |= uint64_t(x) >> 16; | |||||
| if constexpr (sizeof(x) > 1) x |= uint64_t(x) >> 8; | |||||
| x |= uint64_t(x) >> 4; | |||||
| x |= uint64_t(x) >> 2; | |||||
| x |= uint64_t(x) >> 1; | |||||
| return x + 1; | |||||
| #endif | |||||
| } | |||||
| // C++ doesn't define fabs() or fmod() for all types; we add these for | // C++ doesn't define fabs() or fmod() for all types; we add these for | ||||
| // convenience to avoid adding complexity to vector.h. | // convenience to avoid adding complexity to vector.h. | ||||
| template<typename T, typename T2 = LOL_T_SIGNED> | template<typename T, typename T2 = LOL_T_SIGNED> | ||||
| @@ -1,122 +0,0 @@ | |||||
| // | |||||
| // Lol Engine | |||||
| // | |||||
| // Copyright © 2010—2020 Sam Hocevar <sam@hocevar.net> | |||||
| // | |||||
| // Lol Engine is free software. It comes without any warranty, to | |||||
| // the extent permitted by applicable law. You can redistribute it | |||||
| // and/or modify it under the terms of the Do What the Fuck You Want | |||||
| // to Public License, Version 2, as published by the WTFPL Task Force. | |||||
| // See http://www.wtfpl.net/ for more details. | |||||
| // | |||||
| #pragma once | |||||
| #include <lol/math> | |||||
| // | |||||
| // Interpolator classes | |||||
| // -------------------- | |||||
| // | |||||
| namespace lol | |||||
| { | |||||
| template<typename T, int N = 16> class TimeInterp | |||||
| { | |||||
| public: | |||||
| inline TimeInterp() | |||||
| : m_precision(0.f), | |||||
| m_accum(0.f), | |||||
| m_pos(-N) | |||||
| {} | |||||
| inline ~TimeInterp() {} | |||||
| void SetPrecision(float seconds) | |||||
| { | |||||
| m_precision = seconds; | |||||
| } | |||||
| void Set(float seconds, T const &val) | |||||
| { | |||||
| m_accum += seconds; | |||||
| if (m_accum < m_precision) | |||||
| return; | |||||
| m_accum = 0.f; | |||||
| if (m_pos < 0) | |||||
| { | |||||
| if (m_pos > -N) | |||||
| seconds += m_key[m_pos + N - 1]; | |||||
| m_key[m_pos + N] = seconds; | |||||
| m_val[m_pos + N] = val; | |||||
| ++m_pos; | |||||
| } | |||||
| else | |||||
| { | |||||
| if (m_pos > 0) | |||||
| seconds += m_key[m_pos - 1]; | |||||
| m_key[m_pos] = seconds; | |||||
| m_val[m_pos] = val; | |||||
| m_pos = (m_pos + 1) % N; | |||||
| } | |||||
| } | |||||
| T Get(float seconds) | |||||
| { | |||||
| if (m_pos == -N) | |||||
| return T(); | |||||
| if (m_pos == 1 - N) | |||||
| return m_val[0]; | |||||
| seconds += m_accum; | |||||
| int start = max(0, m_pos); | |||||
| int a = 0; | |||||
| int b = min(m_pos + N - 1, N - 1); | |||||
| while (a + 1 < b) | |||||
| { | |||||
| int c = (a + b) / 2; | |||||
| if (GetTime((start + c) % N) >= seconds) | |||||
| b = c; | |||||
| else | |||||
| a = c; | |||||
| } | |||||
| float ka = GetTime((start + a) % N); | |||||
| float kb = GetTime((start + b) % N); | |||||
| float u = (seconds - ka) / (kb - ka); | |||||
| return (1.f - u) * m_val[(start + a) % N] + u * m_val[(start + b) % N]; | |||||
| } | |||||
| inline void Reset() | |||||
| { | |||||
| m_pos = -N; | |||||
| } | |||||
| private: | |||||
| inline float GetTime(int i) | |||||
| { | |||||
| float k = m_key[i % N]; | |||||
| if (m_pos >= 0 && i >= m_pos) | |||||
| k -= m_key[N - 1]; | |||||
| if (m_pos != 0) | |||||
| k -= m_key[(m_pos + N - 1) % N]; | |||||
| return k; | |||||
| } | |||||
| float m_key[N]; | |||||
| T m_val[N]; | |||||
| float m_precision, m_accum; | |||||
| /* If m_pos < 0, the value indicates how many free slots | |||||
| * there are. */ | |||||
| int m_pos; | |||||
| }; | |||||
| } /* namespace lol */ | |||||
| @@ -1,81 +0,0 @@ | |||||
| // | |||||
| // Lol Engine | |||||
| // | |||||
| // Copyright © 2010—2020 Sam Hocevar <sam@hocevar.net> | |||||
| // | |||||
| // Lol Engine is free software. It comes without any warranty, to | |||||
| // the extent permitted by applicable law. You can redistribute it | |||||
| // and/or modify it under the terms of the Do What the Fuck You Want | |||||
| // to Public License, Version 2, as published by the WTFPL Task Force. | |||||
| // See http://www.wtfpl.net/ for more details. | |||||
| // | |||||
| #pragma once | |||||
| // | |||||
| // Various math utility functions | |||||
| // —————————————————————————————— | |||||
| // | |||||
| #include <lol/math> // lol::lerp, lol::clamp | |||||
| #include <cstdlib> | |||||
| #include <stdint.h> | |||||
| namespace lol | |||||
| { | |||||
| /* Next power of two. */ | |||||
| template <typename T> static inline T PotUp(T val) | |||||
| { | |||||
| val = val - 1; | |||||
| if (sizeof(val) > 4) val = val | ((uint64_t)val >> 32); | |||||
| if (sizeof(val) > 2) val = val | ((uint64_t)val >> 16); | |||||
| if (sizeof(val) > 1) val = val | ((uint64_t)val >> 8); | |||||
| val = val | ((uint64_t)val >> 4); | |||||
| val = val | ((uint64_t)val >> 2); | |||||
| val = val | ((uint64_t)val >> 1); | |||||
| return val + 1; | |||||
| } | |||||
| //Damp for float | |||||
| template <typename T1, typename T2, typename Tf> static inline T1 damp(const T1 &a, const T2 &b, const Tf &x, const Tf &dt) | |||||
| { | |||||
| if (dt <= .0f) | |||||
| return a; | |||||
| return lol::lerp(a, b, dt / (dt + x)); | |||||
| } | |||||
| //SmoothClamp clamps x in [a - sd, b + sd] and returns a value in [a, b] that is smoothed at the borders. | |||||
| static inline float SmoothClamp(float &x, float a, float b, float sd) | |||||
| { | |||||
| if (b < a) | |||||
| Swap(a, b); | |||||
| float tx = x; | |||||
| float ta = a - sd; | |||||
| float tb = b + sd; | |||||
| if (sd > 0.f) | |||||
| { | |||||
| if ((b - a) < 2.f * sd) | |||||
| sd = .5f * (b - a); | |||||
| if (tx < a + sd && tx > a - sd) | |||||
| { | |||||
| float t = (tx - a) / sd; | |||||
| t = 0.25f * (t + 1.0f) * (t + 1.0f); | |||||
| tx = a + t * sd; | |||||
| } | |||||
| else if (tx < b + sd && tx > b - sd) | |||||
| { | |||||
| float t = -(tx - b) / sd; | |||||
| t = 0.25f * (t + 1.0f) * (t + 1.0f); | |||||
| tx = b - t * sd; | |||||
| } | |||||
| } | |||||
| x = lol::clamp(x, ta, tb); | |||||
| return lol::clamp(tx, a, b); | |||||
| } | |||||
| } /* namespace lol */ | |||||