From 9d9028c9793b7b7862fdb6a332e9657ca962799e Mon Sep 17 00:00:00 2001 From: Seth Hillbrand Date: Mon, 10 Jun 2024 12:37:27 -0700 Subject: [PATCH] Handle unsigned VECTOR2 casts The previous overflow handling code casted the int_min value into an unsigned, meaning that the min value and max value were almost the same, clamping the output to unreasonable values. Updated code handles floating points first, then does integer casting through int64_t --- libs/kimath/include/math/vector2d.h | 51 +++++++++++++++++++++-------- 1 file changed, 38 insertions(+), 13 deletions(-) diff --git a/libs/kimath/include/math/vector2d.h b/libs/kimath/include/math/vector2d.h index 5e2a1f31bf..5c4cd71123 100644 --- a/libs/kimath/include/math/vector2d.h +++ b/libs/kimath/include/math/vector2d.h @@ -87,13 +87,26 @@ public: template VECTOR2( const VECTOR2& aVec ) { - if( std::is_same::value ) + if( std::is_floating_point() ) { - CastingType minI = static_cast( std::numeric_limits::min() ); - CastingType maxI = static_cast( std::numeric_limits::max() ); + x = static_cast( aVec.x ); + y = static_cast( aVec.y ); + } + else if( std::is_floating_point() ) + { + CastingType minI = static_cast( std::numeric_limits::min() ); + CastingType maxI = static_cast( std::numeric_limits::max() ); - x = static_cast( Clamp( minI, aVec.x, maxI ) ); - y = static_cast( Clamp( minI, aVec.y, maxI ) ); + x = static_cast( Clamp( minI, aVec.x, maxI ) ); + y = static_cast( Clamp( minI, aVec.y, maxI ) ); + } + else if( std::is_integral() && std::is_integral() ) + { + int64_t minI = static_cast( std::numeric_limits::min() ); + int64_t maxI = static_cast( std::numeric_limits::max() ); + + x = static_cast( Clamp( minI, static_cast( aVec.x ), maxI ) ); + y = static_cast( Clamp( minI, static_cast(aVec.y), maxI ) ); } else { @@ -110,20 +123,32 @@ public: } /// Cast a vector to another specialized subclass. Beware of rounding issues. - template - VECTOR2 operator()() const + template + VECTOR2 operator()() const { - if( std::is_same::value ) + if( std::is_floating_point::value ) { - T minI = static_cast( std::numeric_limits::min() ); - T maxI = static_cast( std::numeric_limits::max() ); + return VECTOR2( static_cast( x ), static_cast( y ) ); + } + else if( std::is_floating_point() ) + { + T minI = static_cast( std::numeric_limits::min() ); + T maxI = static_cast( std::numeric_limits::max() ); + return VECTOR2( static_cast( Clamp( minI, x, maxI ) ), + static_cast( Clamp( minI, y, maxI ) ) ); + } + else if( std::is_integral() && std::is_integral() ) + { + int64_t minI = static_cast( std::numeric_limits::min() ); + int64_t maxI = static_cast( std::numeric_limits::max() ); - return VECTOR2( static_cast( Clamp( minI, x, maxI ) ), - static_cast( Clamp( minI, y, maxI ) ) ); + return VECTOR2( + static_cast( Clamp( minI, static_cast( x ), maxI ) ), + static_cast( Clamp( minI, static_cast( y ), maxI ) ) ); } else { - return VECTOR2( static_cast( x ), static_cast( y ) ); + return VECTOR2( static_cast( x ), static_cast( y ) ); } }