diff --git a/include/bx/inline/math.inl b/include/bx/inline/math.inl index e1e93d4..06a0ec4 100644 --- a/include/bx/inline/math.inl +++ b/include/bx/inline/math.inl @@ -97,6 +97,11 @@ namespace bx return ffloor(_f + 0.5f); } + inline float fceil(float _a) + { + return -ffloor(-_a); + } + inline float flerp(float _a, float _b, float _t) { return _a + (_b - _a) * _t; @@ -132,9 +137,14 @@ namespace bx return 1.0f/fsqrt(_a); } + inline float ftrunc(float _a) + { + return float(int(_a) ); + } + inline float ffract(float _a) { - return _a - ffloor(_a); + return _a - ftrunc(_a); } inline float fmod(float _a, float _b) diff --git a/include/bx/math.h b/include/bx/math.h index 1afdace..fecbc88 100644 --- a/include/bx/math.h +++ b/include/bx/math.h @@ -140,6 +140,9 @@ namespace bx /// float frsqrt(float _a); + /// + float ftrunc(float _a); + /// float ffract(float _a); diff --git a/src/math.cpp b/src/math.cpp index b5c89c9..2c402ec 100644 --- a/src/math.cpp +++ b/src/math.cpp @@ -67,14 +67,20 @@ namespace bx return ::sqrtf(_a); } - float ffloor(float _f) + float ffloor(float _a) { - return ::floorf(_f); - } + if (_a < 0.0f) + { + const float fr = ffract(-_a); + float result = -_a - fr; - float fceil(float _f) - { - return ::ceilf(_f); + return -(0.0f != fr + ? result + 1.0f + : result) + ; + } + + return _a - ffract(_a); } void mtxLookAtImpl(float* _result, const float* _eye, const float* _view, const float* _up) diff --git a/tests/math_test.cpp b/tests/math_test.cpp index 6c0cb53..7fa7bc5 100644 --- a/tests/math_test.cpp +++ b/tests/math_test.cpp @@ -32,18 +32,26 @@ TEST_CASE("flog2", "") flog2_test(256.0f); } -TEST_CASE("fmod", "") -{ - REQUIRE(389.0f == bx::fmod(1389.0f, 1000.0f) ); - REQUIRE(bx::isNan(bx::fmod(0.0f, 0.0f) ) ); -} -TEST_CASE("fabs", "") +TEST_CASE("libm", "") { REQUIRE(1389.0f == bx::fabs(-1389.0f) ); REQUIRE(1389.0f == bx::fabs( 1389.0f) ); REQUIRE( 0.0f == bx::fabs(-0.0f) ); REQUIRE( 0.0f == bx::fabs( 0.0f) ); + + REQUIRE(389.0f == bx::fmod(1389.0f, 1000.0f) ); + REQUIRE(bx::isNan(bx::fmod(0.0f, 0.0f) ) ); + + REQUIRE( 13.0f == bx::ffloor( 13.89f) ); + REQUIRE(-14.0f == bx::ffloor(-13.89f) ); + REQUIRE( 14.0f == bx::fceil( 13.89f) ); + REQUIRE(-13.0f == bx::fceil( -13.89f) ); + + REQUIRE( 13.0f == bx::ftrunc( 13.89f) ); + REQUIRE(-13.0f == bx::ftrunc(-13.89f) ); + REQUIRE(bx::fequal( 0.89f, bx::ffract( 13.89f), 0.000001f) ); + REQUIRE(bx::fequal(-0.89f, bx::ffract(-13.89f), 0.000001f) ); } TEST_CASE("ToBits", "")