[Bf-blender-cvs] [25f67f3d93b] bli-math-basic-types: Use `vec_base` directly in vector operations

Hans Goudey noreply at git.blender.org
Wed Feb 16 16:34:07 CET 2022


Commit: 25f67f3d93b49a1903724670fd4b051a2c8bc19d
Author: Hans Goudey
Date:   Tue Feb 15 11:50:01 2022 -0600
Branches: bli-math-basic-types
https://developer.blender.org/rB25f67f3d93b49a1903724670fd4b051a2c8bc19d

Use `vec_base` directly in vector operations

===================================================================

M	source/blender/blenlib/BLI_math_base.hh
M	source/blender/blenlib/BLI_math_vec_types.hh
M	source/blender/blenlib/BLI_math_vector.hh
M	source/blender/blenlib/intern/delaunay_2d.cc

===================================================================

diff --git a/source/blender/blenlib/BLI_math_base.hh b/source/blender/blenlib/BLI_math_base.hh
index 89a3fd3b826..bb88770ce2f 100644
--- a/source/blender/blenlib/BLI_math_base.hh
+++ b/source/blender/blenlib/BLI_math_base.hh
@@ -21,97 +21,85 @@
 
 namespace blender::math {
 
-/* To avoid being overly specific about what a "basic" type is, for now simply allow anything that
- * isn't a `vec_base` type. In the future, if another implementation of these functions is needed,
- * this would have to become more specific. */
-#define BLI_ENABLE_IF_BASE(T) BLI_ENABLE_IF((!is_math_vec_type<T>))
-
-#ifdef WITH_GMP
-#  define BLI_ENABLE_IF_FLT(T) \
-    BLI_ENABLE_IF_BASE(T), \
-        BLI_ENABLE_IF((std::is_floating_point_v<T> || std::is_same_v<T, mpq_class>))
-#else
-#  define BLI_ENABLE_IF_FLT(T) BLI_ENABLE_IF_BASE(T), BLI_ENABLE_IF((std::is_floating_point_v<T>))
-#endif
-
-#define BLI_ENABLE_IF_INT(T) BLI_ENABLE_IF_BASE(T), BLI_ENABLE_IF((std::is_integral_v<T>))
-
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline bool is_zero(const T &a)
+template<typename T> inline bool is_zero(const T &a)
 {
   return a == T(0);
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline bool is_any_zero(const T &a)
+template<typename T> inline bool is_any_zero(const T &a)
 {
   return is_zero(a);
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline T abs(const T &a)
+template<typename T> inline T abs(const T &a)
 {
   return std::abs(a);
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline T min(const T &a, const T &b)
+template<typename T> inline T min(const T &a, const T &b)
 {
   return std::min(a, b);
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline T max(const T &a, const T &b)
+template<typename T> inline T max(const T &a, const T &b)
 {
   return std::max(a, b);
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)> inline T clamp(const T &a, const T &min, const T &max)
+template<typename T> inline T clamp(const T &a, const T &min, const T &max)
 {
   return std::clamp(a, min, max);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T mod(const T &a, const T &b)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T mod(const T &a, const T &b)
 {
   return std::fmod(a, b);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T safe_mod(const T &a, const T &b)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T safe_mod(const T &a, const T &b)
 {
   return (b != 0) ? std::fmod(a, b) : 0;
 }
 
-template<typename T, BLI_ENABLE_IF_BASE(T)>
-inline void min_max(const T &vector, T &min_vec, T &max_vec)
+template<typename T> inline void min_max(const T &vector, T &min_vec, T &max_vec)
 {
   min_vec = min(vector, min_vec);
   max_vec = max(vector, max_vec);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T safe_divide(const T &a, const T &b)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))>
+inline T safe_divide(const T &a, const T &b)
 {
   return (b != 0) ? a / b : T(0.0f);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T floor(const T &a)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T floor(const T &a)
 {
   return std::floor(a);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T ceil(const T &a)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T ceil(const T &a)
 {
   return std::ceil(a);
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T fract(const T &a)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T fract(const T &a)
 {
   return a - std::floor(a);
 }
 
-template<typename T, typename FactorT, BLI_ENABLE_IF_FLT(T), BLI_ENABLE_IF_FLT(FactorT)>
+template<typename T,
+         typename FactorT,
+         BLI_ENABLE_IF((math_is_float<T>)),
+         BLI_ENABLE_IF((math_is_float<T>))>
 inline T interpolate(const T &a, const T &b, const FactorT &t)
 {
   return a * (1 - t) + b * t;
 }
 
-template<typename T, BLI_ENABLE_IF_FLT(T)> inline T midpoint(const T &a, const T &b)
+template<typename T, BLI_ENABLE_IF((math_is_float<T>))> inline T midpoint(const T &a, const T &b)
 {
-  return (a + b) * 0.5;
+  return (a + b) * T(0.5);
 }
 
 #undef BLI_ENABLE_IF_BASE
diff --git a/source/blender/blenlib/BLI_math_vec_types.hh b/source/blender/blenlib/BLI_math_vec_types.hh
index b8a208f0a0d..a11e3907fcb 100644
--- a/source/blender/blenlib/BLI_math_vec_types.hh
+++ b/source/blender/blenlib/BLI_math_vec_types.hh
@@ -14,6 +14,10 @@
 
 #include "BLI_utildefines.h"
 
+#ifdef WITH_GMP
+#  include "BLI_math_mpq.hh"
+#endif
+
 namespace blender {
 
 /* clang-format off */
@@ -60,10 +64,10 @@ template<typename T> uint64_t vector_hash(const T &vec)
   return result;
 }
 
-template<typename T> inline bool is_any_zero(const T &a)
+template<typename T, int Size> inline bool is_any_zero(const vec_struct_base<T, Size> &a)
 {
-  for (int i = 0; i < T::type_length; i++) {
-    if (a[i] == T::base_type(0)) {
+  for (int i = 0; i < Size; i++) {
+    if (a[i] == T(0)) {
       return true;
     }
   }
@@ -265,16 +269,6 @@ template<typename T, int Size> struct vec_base : public vec_struct_base<T, Size>
   } \
   return *this;
 
-  bool is_any_zero() const
-  {
-    for (int i = 0; i < Size; i++) {
-      if ((*this)[i] == T(0)) {
-        return true;
-      }
-    }
-    return false;
-  }
-
   /** Arithmetic operators. */
 
   friend vec_base operator+(const vec_base &a, const vec_base &b)
@@ -377,7 +371,7 @@ template<typename T, int Size> struct vec_base : public vec_struct_base<T, Size>
 
   vec_base &operator/=(T b)
   {
-    BLI_assert(!b.is_any_zero());
+    BLI_assert(b != T(0));
     BLI_VEC_OP_IMPL_SELF(i, (*this)[i] /= b);
   }
 
@@ -589,15 +583,13 @@ using double2 = vec_base<double, 2>;
 using double3 = vec_base<double, 3>;
 using double4 = vec_base<double, 4>;
 
-template<typename T> constexpr bool is_math_vec_type = false;
-template<typename BaseType, int Size>
-constexpr bool is_math_vec_type<vec_base<BaseType, Size>> = true;
+template<typename T>
+inline constexpr bool math_is_float = (std::is_floating_point_v<T>
+#ifdef WITH_GMP
+                                       || std::is_same_v<T, mpq_class>
+#endif
+);
 
-static_assert(is_math_vec_type<int2>);
-static_assert(is_math_vec_type<uint4>);
-static_assert(is_math_vec_type<float2>);
-static_assert(is_math_vec_type<vec_base<float, 20>>);
-static_assert(!is_math_vec_type<int>);
-static_assert(!is_math_vec_type<float>);
+template<typename T> inline constexpr bool math_is_integral = std::is_integral_v<T>;
 
 }  // namespace blender
diff --git a/source/blender/blenlib/BLI_math_vector.hh b/source/blender/blenlib/BLI_math_vector.hh
index 32cc15e44a4..a34888f8ad0 100644
--- a/source/blender/blenlib/BLI_math_vector.hh
+++ b/source/blender/blenlib/BLI_math_vector.hh
@@ -15,10 +15,6 @@
 #include "BLI_span.hh"
 #include "BLI_utildefines.h"
 
-#ifdef WITH_GMP
-#  include "BLI_math_mpq.hh"
-#endif
-
 namespace blender::math {
 
 #ifndef NDEBUG
@@ -33,288 +29,293 @@ namespace blender::math {
 #  define BLI_ASSERT_UNIT(v) (void)(v)
 #endif
 
-#define bT typename T::base_type
-
-template<typename T>
-inline constexpr bool is_float_vector = (std::is_floating_point_v<typename T::base_type>
-#ifdef WITH_GMP
-                                         || std::is_same_v<typename T::base_type, mpq_class>
-#endif
-);
-
-template<typename T>
-inline constexpr bool is_integral_vector = std::is_integral_v<typename T::base_type>;
-
-/* In this file, only implement math functions for the vector types. This allows other
- * files to use overloading to implement the same functions with different types. */
-#define BLI_ENABLE_IF_VEC(T) BLI_ENABLE_IF((is_math_vec_type<T>))
-
-#define BLI_ENABLE_IF_FLT_VEC(T) BLI_ENABLE_IF_VEC(T), BLI_ENABLE_IF((is_float_vector<T>))
-
-#define BLI_ENABLE_IF_INT_VEC(T) BLI_ENABLE_IF_VEC(T), BLI_ENABLE_IF((is_integral_vector<T>))
-
-template<typename T, BLI_ENABLE_IF_VEC(T)> inline bool is_zero(const T &a)
+template<typename T, int Size> inline bool is_zero(const vec_base<T, Size> &a)
 {
-  for (int i = 0; i < T::type_length; i++) {
-    if (a[i] != bT(0)) {
+  for (int i = 0; i < Size; i++) {
+    if (a[i] != T(0)) {
       return false;
     }
   }
   return true;
 }
 
-template<typename T, BLI_ENABLE_IF_VEC(T)> inline T abs(const T &a)
+template<typename T, int Size> inline vec_base<T, Size> abs(const vec_base<T, Size> &a)
 {
-  T result;
-  for (int i = 0; i < T::type_length; i++) {
+  vec_base<T, Size> result;
+  for (int i = 0; i < Size; i++) {
     result[i] = a[i] >= 0 ? a[i] : -a[i];
   }
   return result;
 }
 
-template<typename T, BLI_ENABLE_IF_VEC(T)> inline T min(const T &a, const T &b)
+template<typename T, int Size>
+inline vec_base<T, Size> min(const vec_base<T, Size> &a, const vec_base<T, Size> &b)
 {
-  T result;
-  for (int i = 0; i < T::type_length; i++) {
+  vec_base<T, Size> result;
+  for (int i = 0; i < Size; i++) {
     result[i] = a[i] < b[i] ? a[i] : b[i];
   }
   return result;
 }
 
-template<typename T, BLI_ENABLE_IF_VEC(T)> inline T max(const T &a, const T &b)
+template<typename T, int Size>
+inline vec_base<T, Size> max(const vec_base<T, Size> &a, const vec_base<T, Size> &b)
 {
-  T result;
-  for (int i = 0; i < T::type_length; i++) {
+  vec_base<T, Size> result;
+  for (int i = 0; i < Size; i++) {
     result[i] = a[i] > b[i] ? a[i] : b[i];
   }
   return result;
 }
 
-template<typename T, BLI_ENABLE_IF_VEC(T)>
-inline T clamp(const T &a, const T &min_v, const T &max_v)
+template<typename T, int Size>
+inline T clamp(const vec_base<T, Size> &a,
+               const vec_base<T, Size> &min,
+               const vec_base<T, Size> &max)
 {
-  T result = a;
-  for (int i = 0; i < T::type_length; i++) {
-    CLAMP(result[i], min_v[i], max_v[i]);
+  vec_base<T, Size> result = a;
+  for (int i = 0; i < Size; i++) {
+    std::clamp(result[i], min[i], max[i]);
   }
   return result;
 }
 
-template<typename T, BLI_ENABLE_IF_VEC(T)>
-inline T clamp(const T &a, const bT &min_v, const bT &max_v)
+template<typename T, int Size>
+inline vec_base<T, Size> clamp(const vec_base<T, Size> &a, const T &min, const T &max)
 {
-  T result = a;
-  for (int i = 0; i < T::type_length; i++) {
-    CLAMP(result[i], min_v, max_v);
+  vec_base<T, Size> result = a;
+  for (int i = 0; i < Size; i++) {
+  

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list