Skip to content

Commit

Permalink
Fix const, add more tests
Browse files Browse the repository at this point in the history
  • Loading branch information
AbitTheGray authored and Groovounet committed Jan 23, 2025
1 parent 8ca503e commit cd4dfd0
Show file tree
Hide file tree
Showing 7 changed files with 459 additions and 186 deletions.
57 changes: 14 additions & 43 deletions glm/gtx/range.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,54 +22,29 @@
#endif

#include "../gtc/type_ptr.hpp"
#include "../gtc/vec1.hpp"
#include "type_trait.hpp"

namespace glm
{
/// @addtogroup gtx_range
/// @{

# if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(push)
# pragma warning(disable : 4100) // unreferenced formal parameter
# endif

template<typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(vec<1, T, Q> const& v)
{
return v.length();
}

template<typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(vec<2, T, Q> const& v)
{
return v.length();
}

template<typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(vec<3, T, Q> const& v)
{
return v.length();
}

template<typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(vec<4, T, Q> const& v)
{
return v.length();
}

template<typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(qua<T, Q> const& v)
{
return v.length();
}
#if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(push)
# pragma warning(disable : 4100) // unreferenced formal parameter
#endif

/// @warning This is not same as `type<genType>::components`, calling this returns total elements (for mat4 returns 16 instead of 4).
template<typename genType>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(genType const& m)
/*GLM_DEPRECATED*/ GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(genType const& v)
{
return m.length() * m[0].length();
return type<std::remove_cv<genType>::type>::elements;
}

#if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(pop)
#endif

template<typename genType>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR typename genType::value_type const * begin(genType const& v)
{
Expand All @@ -79,7 +54,7 @@ namespace glm
template<typename genType>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR typename genType::value_type const * end(genType const& v)
{
return begin(v) + components(v);
return begin(v) + type<std::remove_cv<genType>::type>::elements;
}

template<typename genType>
Expand All @@ -91,12 +66,8 @@ namespace glm
template<typename genType>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR typename genType::value_type * end(genType& v)
{
return begin(v) + components(v);
return begin(v) + type<std::remove_cv<genType>::type>::elements;
}

# if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(pop)
# endif

/// @}
}//namespace glm
157 changes: 49 additions & 108 deletions glm/gtx/span.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,27 +20,29 @@
# pragma message("GLM: GLM_GTX_span extension included")
#endif

#if !(GLM_LANG & GLM_LANG_CXX11)
// This requirement is due to `std::enable_if`
// `std::enable_if` support (and few more)
// Required for all functions below
#if !(GLM_LANG & GLM_LANG_CXX11_FLAG)
# error "GLM_GTX_span requiers at least C++11, using C++20 or C++23 is recommended for full functionality"
#endif

// GLM_MESSAGES info
#if GLM_MESSAGES == GLM_ENABLE && !defined(GLM_EXT_INCLUDED)
# if (GLM_LANG & GLM_LANG_CXX20) && defined(__cpp_lib_span) && __cpp_lib_span >= 202002L
# if (GLM_LANG & GLM_LANG_CXX20_FLAG) && defined(__cpp_lib_span) && __cpp_lib_span >= 202002L
# pragma message("GLM: GLM_GTX_span extension will include std::span")
# endif
# if (GLM_LANG & GLM_LANG_CXX23) && defined(__cpp_lib_mdspan) && __cpp_lib_mdspan >= 202207L
# if (GLM_LANG & GLM_LANG_CXX23_FLAG) && defined(__cpp_lib_mdspan) && __cpp_lib_mdspan >= 202207L
# pragma message("GLM: GLM_GTX_span extension will include std::mdspan")
# endif
#endif

#include "../gtc/type_precision.hpp"
#include "../gtc/type_ptr.hpp"
#include "type_trait.hpp"

#include <valarray>
#include <type_traits>

#if GLM_LANG & GLM_LANG_CXX20
// Version-specific includes
#if GLM_LANG & GLM_LANG_CXX20_FLAG
// Feature testing
# include <version>

Expand All @@ -60,141 +62,80 @@ namespace glm
/// @addtogroup gtx_span
/// @{

# if (GLM_LANG & GLM_LANG_CXX20_FLAG)
template<typename T>
struct is_vec : std::false_type {};
template<length_t L, typename T, qualifier Q>
struct is_vec<vec<L, T, Q>> : std::true_type {};

template<typename T>
struct is_quat : std::false_type {};
template<typename T, qualifier Q>
struct is_quat<qua<T, Q>> : std::true_type {};

template<typename T>
struct is_mat : std::false_type {};
template<length_t L1, length_t L2, typename T, qualifier Q>
struct is_mat<mat<L1, L2, T, Q>> : std::true_type {};

#if (GLM_LANG & GLM_LANG_CXX17)
template<typename T>
inline constexpr bool is_vec_v = is_vec<T>::value;
template<typename T>
inline constexpr bool is_quat_v = is_quat<T>::value;
template<typename T>
inline constexpr bool is_mat_v = is_mat<T>::value;
#endif

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value>::type>
#endif
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components()
{
return T::length();
}
#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_mat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_mat<T>::value>::type>
#endif
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components()
{
return T::length() * T::col_type::length();
}
# if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(push)
# pragma warning(disable : 4100) // unreferenced formal parameter
# endif

/// Utility function if you don't have the type and dont use `decltype` (it is from C++11 so this function won't exist for earlier anyway)
#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value>::type>
#endif
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR length_t components(T const&)
{
return components<T>();
}
# if GLM_COMPILER & GLM_COMPILER_VC
# pragma warning(pop)
requires (type<std::remove_cvref_t<T>>::elements > 0)
# else
template<typename T, typename = typename std::enable_if<
(
type<
typename std::remove_reference<
typename std::remove_cv<T>::type
>::type
>::elements > 0
)>::type>
# endif

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value || is_mat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value || is_mat<T>::value>::type>
#endif
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR std::valarray<typename T::value_type> valarray(T const& v)
{
return std::valarray<typename T::value_type>(value_ptr(v), components<T>());
return std::valarray<typename T::value_type>(value_ptr(v), type<T>::elements);
}

#if (GLM_LANG & GLM_LANG_CXX20) && defined(__cpp_lib_span) && __cpp_lib_span >= 202002L
#if (GLM_LANG & GLM_LANG_CXX20_FLAG) && defined(__cpp_lib_span) && __cpp_lib_span >= 202002L

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value || is_mat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value || is_mat<T>::value>::type>
#endif
requires (type<std::remove_cvref_t<T>>::elements > 0)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR std::span<typename T::value_type> span(T & v)
{
return std::span<typename T::value_type>(value_ptr(v), components<T>());
using TN = std::remove_cvref_t<T>;
return std::span<typename T::value_type>(value_ptr(v), type<TN>::elements);
}

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value || is_mat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value || is_mat<T>::value>::type>
#endif
requires (type<std::remove_cvref_t<T>>::elements > 0)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR std::span<const typename T::value_type> span(T const& v)
{
return std::span<const typename T::value_type>(value_ptr(v), components<T>());
using TN = std::remove_cvref_t<T>;
return std::span<const typename T::value_type>(value_ptr(v), type<TN>::elements);
}

#endif

#if (GLM_LANG & GLM_LANG_CXX23) && defined(__cpp_lib_mdspan) && __cpp_lib_mdspan >= 202207L
#if (GLM_LANG & GLM_LANG_CXX23_FLAG) && defined(__cpp_lib_mdspan) && __cpp_lib_mdspan >= 202207L

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value>::type>
#endif
requires (type<std::remove_cvref_t<T>>::rows == 1)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR std::mdspan<typename T::value_type> span(T & v)
{
return std::mdspan<typename T::value_type>(value_ptr(v), components<T>());
using TN = std::remove_cvref_t<T>;
static_assert(type<TN>::cols >= 1);
return std::mdspan<typename T::value_type>(value_ptr(v), type<TN>::cols);
}

#if (GLM_LANG & GLM_LANG_CXX20)
template<typename T>
requires is_vec<T>::value || is_quat<T>::value
#else
template<typename T, typename = typename std::enable_if<is_vec<T>::value || is_quat<T>::value>::type>
#endif
requires (type<std::remove_cvref_t<T>>::rows == 1)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR std::mdspan<const typename T::value_type> span(T const& v)
{
return std::mdspan<const typename T::value_type>(value_ptr(v), components<T>());
using TN = std::remove_cvref_t<T>;
static_assert(type<TN>::cols >= 1);
return std::mdspan<const typename T::value_type>(value_ptr(v), type<TN>::cols);
}

template<length_t L1, length_t L2, typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR auto mdspan(mat<L1, L2, T, Q> & m)
template<typename T>
requires (type<std::remove_cvref_t<T>>::rows > 1)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR auto mdspan(T & m)
{
return std::mdspan<T>(value_ptr(m), L1, L2);
using TN = std::remove_cvref_t<T>;
static_assert(type<TN>::cols >= 1);
return std::mdspan<typename T::value_type>(value_ptr(m), type<TN>::cols, type<TN>::rows);
}

template<length_t L1, length_t L2, typename T, qualifier Q>
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR auto mdspan(mat<L1, L2, T, Q> const& m)
template<typename T>
requires (type<std::remove_cvref_t<T>>::rows > 1)
GLM_NODISCARD GLM_FUNC_QUALIFIER GLM_CONSTEXPR auto mdspan(T const& m)
{
return std::mdspan<const T>(value_ptr(m), L1, L2);
using TN = std::remove_cvref_t<T>;
static_assert(type<TN>::cols >= 1);
return std::mdspan<const typename T::value_type>(value_ptr(m), type<TN>::cols, type<TN>::rows);
}

#endif
Expand Down
18 changes: 18 additions & 0 deletions glm/gtx/type_trait.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,12 +31,20 @@ namespace glm
template<typename T>
struct type
{
#if GLM_LANG & GLM_LANG_CXX11_FLAG
// with C++20, you can use std::remove_cvref for all of those
// with C++11, you can use std::remove_cv for the first two
static_assert(!std::is_const<T>::value); // use std::remove_const
static_assert(!std::is_volatile<T>::value); // use std::remove_volatile
static_assert(!std::is_reference<T>::value); // use std::remove_reference
#endif
static bool const is_vec = false;
static bool const is_mat = false;
static bool const is_quat = false;
static length_t const components = 0;
static length_t const cols = 0;
static length_t const rows = 0;
static length_t const elements = cols * rows;
};

template<length_t L, typename T, qualifier Q>
Expand All @@ -46,6 +54,9 @@ namespace glm
static bool const is_mat = false;
static bool const is_quat = false;
static length_t const components = L;
static length_t const cols = L;
static length_t const rows = 1;
static length_t const elements = cols * rows;
};

template<length_t C, length_t R, typename T, qualifier Q>
Expand All @@ -57,6 +68,7 @@ namespace glm
static length_t const components = C;
static length_t const cols = C;
static length_t const rows = R;
static length_t const elements = cols * rows;
};

template<typename T, qualifier Q>
Expand All @@ -66,6 +78,9 @@ namespace glm
static bool const is_mat = false;
static bool const is_quat = true;
static length_t const components = 4;
static length_t const cols = components;
static length_t const rows = 1;
static length_t const elements = cols * rows;
};

template<typename T, qualifier Q>
Expand All @@ -75,6 +90,9 @@ namespace glm
static bool const is_mat = false;
static bool const is_quat = true;
static length_t const components = 8;
static length_t const cols = components;
static length_t const rows = 1;
static length_t const elements = cols * rows;
};

/// @}
Expand Down
Loading

0 comments on commit cd4dfd0

Please sign in to comment.