summaryrefslogtreecommitdiffstats
path: root/Common/interface
diff options
context:
space:
mode:
authorassiduous <assiduous@diligentgraphics.com>2020-04-11 00:02:02 +0000
committerassiduous <assiduous@diligentgraphics.com>2020-04-11 00:02:02 +0000
commit0ba14879e0e2beb18113276d11edeb23dc2c7d6e (patch)
treee6397b5257d550d507b5ce59f33edc4aebd72f62 /Common/interface
parentAdded FastRand class (diff)
downloadDiligentCore-0ba14879e0e2beb18113276d11edeb23dc2c7d6e.tar.gz
DiligentCore-0ba14879e0e2beb18113276d11edeb23dc2c7d6e.zip
MathLib: added FastFloor and FastCeil functions
Diffstat (limited to 'Common/interface')
-rw-r--r--Common/interface/BasicMath.hpp81
-rw-r--r--Common/interface/FastRand.hpp2
-rw-r--r--Common/interface/FilteringTools.hpp2
3 files changed, 82 insertions, 3 deletions
diff --git a/Common/interface/BasicMath.hpp b/Common/interface/BasicMath.hpp
index 867c91cd..757244e1 100644
--- a/Common/interface/BasicMath.hpp
+++ b/Common/interface/BasicMath.hpp
@@ -1942,6 +1942,86 @@ inline Uint32 F4Color_To_RGBA8Unorm(const float4& f4Color)
return RGBA8U;
}
+
+// At least on MSVC std::floor is an actual function call into ucrtbase.dll.
+// For floats/doubles that fit into Int64 representable range we can do much better.
+template <typename T>
+T FastFloor(T x)
+{
+ auto i = static_cast<Int64>(x);
+ auto flr = static_cast<T>(i);
+ // x flr floor(x) flr <= x
+ // +1.0 -> 1.0 1.0 true
+ // +0.5 -> 0.0 0.0 true
+ // 0.0 -> 0.0 0.0 true
+ // -0.5 -> 0.0 -1.0 false
+ // -1.0 -> -1.0 -1.0 true
+
+ return flr <= x ? flr : flr - 1;
+}
+
+template <typename T>
+T FastCeil(T x)
+{
+ return -FastFloor(-x);
+}
+
+
+template <typename T>
+Diligent::Vector2<T> FastFloor(const Diligent::Vector2<T>& vec)
+{
+ return Diligent::Vector2<T>{
+ FastFloor(vec.x),
+ FastFloor(vec.y)};
+}
+
+template <typename T>
+Diligent::Vector3<T> FastFloor(const Diligent::Vector3<T>& vec)
+{
+ return Diligent::Vector3<T>{
+ FastFloor(vec.x),
+ FastFloor(vec.y),
+ FastFloor(vec.z)};
+}
+
+template <typename T>
+Diligent::Vector4<T> FastFloor(const Diligent::Vector4<T>& vec)
+{
+ return Diligent::Vector4<T>{
+ FastFloor(vec.x),
+ FastFloor(vec.y),
+ FastFloor(vec.z),
+ FastFloor(vec.w)};
+}
+
+
+template <typename T>
+Diligent::Vector2<T> FastCeil(const Diligent::Vector2<T>& vec)
+{
+ return Diligent::Vector2<T>{
+ FastCeil(vec.x),
+ FastCeil(vec.y)};
+}
+
+template <typename T>
+Diligent::Vector3<T> FastCeil(const Diligent::Vector3<T>& vec)
+{
+ return Diligent::Vector3<T>{
+ FastCeil(vec.x),
+ FastCeil(vec.y),
+ FastCeil(vec.z)};
+}
+
+template <typename T>
+Diligent::Vector4<T> FastCeil(const Diligent::Vector4<T>& vec)
+{
+ return Diligent::Vector4<T>{
+ FastCeil(vec.x),
+ FastCeil(vec.y),
+ FastCeil(vec.z),
+ FastCeil(vec.w)};
+}
+
} // namespace Diligent
@@ -2003,7 +2083,6 @@ Diligent::Vector4<T> min(const Diligent::Vector4<T>& Left, const Diligent::Vecto
std::min(Left.w, Right.w));
}
-
template <typename T>
Diligent::Vector2<T> floor(const Diligent::Vector2<T>& vec)
{
diff --git a/Common/interface/FastRand.hpp b/Common/interface/FastRand.hpp
index 2494fc83..546da633 100644
--- a/Common/interface/FastRand.hpp
+++ b/Common/interface/FastRand.hpp
@@ -93,7 +93,7 @@ public:
Range{_Max - _Min + 1}
{
VERIFY_EXPR(_Max > _Min);
- VERIFY(Range < FastRand::Max / 8, "Range is too large");
+ VERIFY(Range <= FastRand::Max, "Range is too large");
}
Type operator()()
diff --git a/Common/interface/FilteringTools.hpp b/Common/interface/FilteringTools.hpp
index e256f88d..73871093 100644
--- a/Common/interface/FilteringTools.hpp
+++ b/Common/interface/FilteringTools.hpp
@@ -100,7 +100,7 @@ template <TEXTURE_ADDRESS_MODE AddressMode, bool IsNormalizedCoord>
LinearTexFilterSampleInfo GetLinearTexFilterSampleInfo(Uint32 Width, float u)
{
float x = IsNormalizedCoord ? u * static_cast<float>(Width) : u;
- float x0 = std::floor(x - 0.5f);
+ float x0 = FastFloor(x - 0.5f);
// clang-format off
LinearTexFilterSampleInfo SampleInfo