Browse Source

Math: renamed {de,}normalize() to {,un}pack() in a new Packing.h header.

To be more consistent with GLSL naming. Also, the original naming was
quite misleading, as normalize() is used in GLSL for something
completely different.

If building with deprecated APIs, the Functions.h header includes the
new Packing.h header and the {de,}normalize() functions are defined as
deprecated aliases to the new functions. This will be removed at some
point in the future.
pull/190/head
Vladimír Vondruš 9 years ago
parent
commit
dd2058cee3
  1. 8
      doc/matrix-vector.dox
  2. 1
      src/Magnum/Math/CMakeLists.txt
  3. 54
      src/Magnum/Math/Color.h
  4. 89
      src/Magnum/Math/Functions.h
  5. 135
      src/Magnum/Math/Packing.h
  6. 1
      src/Magnum/Math/Test/CMakeLists.txt
  7. 10
      src/Magnum/Math/Test/ColorTest.cpp
  8. 180
      src/Magnum/Math/Test/FunctionsTest.cpp
  9. 226
      src/Magnum/Math/Test/PackingTest.cpp
  10. 10
      src/Magnum/Test/FramebufferGLTest.cpp
  11. 94
      src/Magnum/Test/MeshGLTest.cpp

8
doc/matrix-vector.dox

@ -222,14 +222,14 @@ auto c = Vector3i{a}; // {2, 0, -5}
auto d = Vector3d{a}; // {2.2, 0.25, -5.1}
@endcode
For normalizing and denormalizing there are @ref Math::normalize() and
@ref Math::denormalize() functions:
For packing and unpacking there are @ref Math::pack() and @ref Math::unpack()
functions:
@code
Color3 a{0.8f, 1.0f, 0.3f};
auto b = Math::denormalize<Color3ub>(a); // {204, 255, 76}
auto b = Math::unpack<Color3ub>(a); // {204, 255, 76}
Color3ub c{64, 127, 89};
auto d = Math::normalize<Color3>(c); // {0.251, 0.498, 0.349}
auto d = Math::pack<Color3>(c); // {0.251, 0.498, 0.349}
@endcode
See @ref matrix-vector-componentwise "below" for more information about other

1
src/Magnum/Math/CMakeLists.txt

@ -41,6 +41,7 @@ set(MagnumMath_HEADERS
Matrix3.h
Matrix4.h
Quaternion.h
Packing.h
Range.h
RectangularMatrix.h
Swizzle.h

54
src/Magnum/Math/Color.h

@ -31,8 +31,8 @@
#include <tuple>
#include "Magnum/Math/Functions.h"
#include "Magnum/Math/Matrix.h"
#include "Magnum/Math/Packing.h"
#include "Magnum/Math/Vector4.h"
namespace Magnum { namespace Math {
@ -67,7 +67,7 @@ template<class T> typename std::enable_if<std::is_floating_point<T>::value, Colo
}
}
template<class T> inline typename std::enable_if<std::is_integral<T>::value, Color3<T>>::type fromHsv(const typename Color3<T>::Hsv& hsv) {
return denormalize<Color3<T>>(fromHsv<typename Color3<T>::FloatingPointType>(hsv));
return pack<Color3<T>>(fromHsv<typename Color3<T>::FloatingPointType>(hsv));
}
/* Internal hue computing function */
@ -104,13 +104,13 @@ template<class T> inline T value(typename std::enable_if<std::is_floating_point<
/* Hue, saturation, value for integral types */
template<class T> inline Deg<typename Color3<T>::FloatingPointType> hue(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type color) {
return hue<typename Color3<T>::FloatingPointType>(normalize<Color3<typename Color3<T>::FloatingPointType>>(color));
return hue<typename Color3<T>::FloatingPointType>(unpack<Color3<typename Color3<T>::FloatingPointType>>(color));
}
template<class T> inline typename Color3<T>::FloatingPointType saturation(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type& color) {
return saturation<typename Color3<T>::FloatingPointType>(normalize<Color3<typename Color3<T>::FloatingPointType>>(color));
return saturation<typename Color3<T>::FloatingPointType>(unpack<Color3<typename Color3<T>::FloatingPointType>>(color));
}
template<class T> inline typename Color3<T>::FloatingPointType value(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type color) {
return normalize<typename Color3<T>::FloatingPointType>(color.max());
return unpack<typename Color3<T>::FloatingPointType>(color.max());
}
/* Convert color to HSV */
@ -121,7 +121,7 @@ template<class T> inline typename Color3<T>::Hsv toHsv(typename std::enable_if<s
return typename Color3<T>::Hsv(hue<typename Color3<T>::FloatingPointType>(color, max, delta), max != T(0) ? delta/max : T(0), max);
}
template<class T> inline typename Color3<T>::Hsv toHsv(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type color) {
return toHsv<typename Color3<T>::FloatingPointType>(normalize<Color3<typename Color3<T>::FloatingPointType>>(color));
return toHsv<typename Color3<T>::FloatingPointType>(unpack<Color3<typename Color3<T>::FloatingPointType>>(color));
}
/* sRGB -> RGB conversion */
@ -133,18 +133,18 @@ template<class T> typename std::enable_if<std::is_floating_point<T>::value, Colo
return {fromSrgb<T>(srgbAlpha.rgb()), srgbAlpha.a()};
}
template<class T> inline typename std::enable_if<std::is_integral<T>::value, Color3<T>>::type fromSrgb(const Vector3<typename Color3<T>::FloatingPointType>& srgb) {
return denormalize<Color3<T>>(fromSrgb<typename Color3<T>::FloatingPointType>(srgb));
return pack<Color3<T>>(fromSrgb<typename Color3<T>::FloatingPointType>(srgb));
}
template<class T> inline typename std::enable_if<std::is_integral<T>::value, Color4<T>>::type fromSrgbAlpha(const Vector4<typename Color4<T>::FloatingPointType>& srgbAlpha) {
return {fromSrgb<T>(srgbAlpha.rgb()), denormalize<T>(srgbAlpha.a())};
return {fromSrgb<T>(srgbAlpha.rgb()), pack<T>(srgbAlpha.a())};
}
template<class T, class Integral> inline Color3<T> fromSrgbIntegral(const Vector3<Integral>& srgb) {
static_assert(std::is_integral<Integral>::value, "only conversion from different integral type is supported");
return fromSrgb<T>(normalize<Vector3<typename Color3<T>::FloatingPointType>>(srgb));
return fromSrgb<T>(unpack<Vector3<typename Color3<T>::FloatingPointType>>(srgb));
}
template<class T, class Integral> inline Color4<T> fromSrgbAlphaIntegral(const Vector4<Integral>& srgbAlpha) {
static_assert(std::is_integral<Integral>::value, "only conversion from different integral type is supported");
return fromSrgbAlpha<T>(normalize<Vector4<typename Color4<T>::FloatingPointType>>(srgbAlpha));
return fromSrgbAlpha<T>(unpack<Vector4<typename Color4<T>::FloatingPointType>>(srgbAlpha));
}
/* RGB -> sRGB conversion */
@ -156,18 +156,18 @@ template<class T> Vector4<typename Color4<T>::FloatingPointType> toSrgbAlpha(typ
return {toSrgb<T>(rgba.rgb()), rgba.a()};
}
template<class T> inline Vector3<typename Color3<T>::FloatingPointType> toSrgb(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type rgb) {
return toSrgb<typename Color3<T>::FloatingPointType>(normalize<Color3<typename Color3<T>::FloatingPointType>>(rgb));
return toSrgb<typename Color3<T>::FloatingPointType>(unpack<Color3<typename Color3<T>::FloatingPointType>>(rgb));
}
template<class T> inline Vector4<typename Color4<T>::FloatingPointType> toSrgbAlpha(typename std::enable_if<std::is_integral<T>::value, const Color4<T>&>::type rgba) {
return {toSrgb<T>(rgba.rgb()), normalize<typename Color3<T>::FloatingPointType>(rgba.a())};
return {toSrgb<T>(rgba.rgb()), unpack<typename Color3<T>::FloatingPointType>(rgba.a())};
}
template<class T, class Integral> inline Vector3<Integral> toSrgbIntegral(const Color3<T>& rgb) {
static_assert(std::is_integral<Integral>::value, "only conversion from different integral type is supported");
return denormalize<Vector3<Integral>>(toSrgb<T>(rgb));
return pack<Vector3<Integral>>(toSrgb<T>(rgb));
}
template<class T, class Integral> inline Vector4<Integral> toSrgbAlphaIntegral(const Color4<T>& rgba) {
static_assert(std::is_integral<Integral>::value, "only conversion from different integral type is supported");
return denormalize<Vector4<Integral>>(toSrgbAlpha<T>(rgba));
return pack<Vector4<Integral>>(toSrgbAlpha<T>(rgba));
}
/* CIE XYZ -> RGB conversion */
@ -180,7 +180,7 @@ template<class T> typename std::enable_if<std::is_floating_point<T>::value, Colo
Vector3<T>{T(-1974)/T(3959), T(36519)/T(878810), T(705)/T(667)}}*xyz;
}
template<class T> inline typename std::enable_if<std::is_integral<T>::value, Color3<T>>::type fromXyz(const Vector3<typename Color3<T>::FloatingPointType>& xyz) {
return denormalize<Color3<T>>(fromXyz<typename Color3<T>::FloatingPointType>(xyz));
return pack<Color3<T>>(fromXyz<typename Color3<T>::FloatingPointType>(xyz));
}
/* RGB -> CIE XYZ conversion */
@ -193,7 +193,7 @@ template<class T> Vector3<typename Color3<T>::FloatingPointType> toXyz(typename
Vector3<T>{T(12673)/T(70218), T(12673)/T(175545), T(1001167)/T(1053270)}})*rgb;
}
template<class T> inline Vector3<typename Color3<T>::FloatingPointType> toXyz(typename std::enable_if<std::is_integral<T>::value, const Color3<T>&>::type rgb) {
return toXyz<typename Color3<T>::FloatingPointType>(normalize<Color3<typename Color3<T>::FloatingPointType>>(rgb));
return toXyz<typename Color3<T>::FloatingPointType>(unpack<Color3<typename Color3<T>::FloatingPointType>>(rgb));
}
/* Value for full channel (1.0f for floats, 255 for unsigned byte) */
@ -216,11 +216,11 @@ linear RGB using @ref fromSrgb(), calculation done on the linear representation
and then converted back to sRGB using @ref toSrgb().
Note that constructor conversion between different types (like in @ref Vector
classes) doesn't do any (de)normalization, you should use @ref normalize() and
@ref denormalize() instead, for example:
classes) doesn't do any (de)normalization, you should use @ref pack) and
@ref unpack() instead, for example:
@code
Color3 a(1.0f, 0.5f, 0.75f);
auto b = denormalize<Color3ub>(a); // b == {255, 127, 191}
auto b = pack<Color3ub>(a); // b == {255, 127, 191}
@endcode
Conversion from and to HSV is done always using floating-point types, so hue
@ -451,9 +451,9 @@ template<class T> class Color3: public Vector3<T> {
/**
* @copydoc Vector::Vector(const Vector<size, U>&)
*
* @attention This function doesn't do any (de)normalization, use
* @ref normalize() and @ref denormalize() instead.
* See class documentation for more information.
* @attention This function doesn't do any (un)packing, use @ref pack()
* and @ref unpack() instead. See class documentation for more
* information.
*/
template<class U> constexpr explicit Color3(const Vector<3, U>& other) noexcept: Vector3<T>(other) {}
@ -846,9 +846,9 @@ class Color4: public Vector4<T> {
/**
* @copydoc Vector::Vector(const Vector<size, U>&)
*
* @attention This function doesn't do any (de)normalization, use
* @ref normalize() and @ref denormalize() instead.
* See @ref Color3 class documentation for more information.
* @attention This function doesn't do any (un)packing, use @ref pack)
* and @ref unpack() instead. See @ref Color3 class documentation
* for more information.
*/
template<class U> constexpr explicit Color4(const Vector<4, U>& other) noexcept: Vector4<T>(other) {}
@ -1064,7 +1064,7 @@ Color3 a = 0x33b27f_rgbf; // {0.2f, 0.698039f, 0.498039f}
@see @link operator""_rgbaf() @endlink, @link operator""_rgb() @endlink
*/
inline Color3<Float> operator "" _rgbf(unsigned long long value) {
return Math::normalize<Color3<Float>>(Color3<UnsignedByte>{UnsignedByte(value >> 16), UnsignedByte(value >> 8), UnsignedByte(value)});
return Math::unpack<Color3<Float>>(Color3<UnsignedByte>{UnsignedByte(value >> 16), UnsignedByte(value >> 8), UnsignedByte(value)});
}
/** @relatesalso Magnum::Math::Color3
@ -1099,7 +1099,7 @@ Color4 a = 0x33b27fcc_rgbaf; // {0.2f, 0.698039f, 0.498039f, 0.8f}
@see @link operator""_rgbf() @endlink, @link operator""_rgba() @endlink
*/
inline Color4<Float> operator "" _rgbaf(unsigned long long value) {
return Math::normalize<Color4<Float>>(Color4<UnsignedByte>{UnsignedByte(value >> 24), UnsignedByte(value >> 16), UnsignedByte(value >> 8), UnsignedByte(value)});
return Math::unpack<Color4<Float>>(Color4<UnsignedByte>{UnsignedByte(value >> 24), UnsignedByte(value >> 16), UnsignedByte(value >> 8), UnsignedByte(value)});
}
/** @relatesalso Magnum::Math::Color4

89
src/Magnum/Math/Functions.h

@ -30,7 +30,6 @@
*/
#include <cmath>
#include <limits>
#include <type_traits>
#include <utility>
@ -535,89 +534,15 @@ template<std::size_t size, class T> inline Vector<size, T> fma(const Vector<size
}
#endif
/**
@brief Normalize integral value
Converts integral value from full range of given *unsigned* integral type to
value in range @f$ [0, 1] @f$ or from *signed* integral to range @f$ [-1, 1] @f$.
@note For best precision, resulting `FloatingPoint` type should be always
larger that `Integral` type (e.g. @ref Magnum::Float "Float" from
@ref Magnum::Short "Short", @ref Magnum::Double "Double" from
@ref Magnum::Int "Int" and similarly for vector types).
@attention To ensure the integral type is correctly detected when using
literals, this function should be called with both template parameters
explicit, e.g.:
@code
// Literal type is (signed) char, but we assumed unsigned char, a != 1.0f
Float a = Math::normalize<Float>('\xFF');
// b = 1.0f
Float b = Math::normalize<Float, UnsignedByte>('\xFF');
@endcode
@see @ref denormalize()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class FloatingPoint, class Integral> inline FloatingPoint normalize(const Integral& value);
#else
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_arithmetic<Integral>::value && std::is_unsigned<Integral>::value, FloatingPoint>::type normalize(Integral value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"Math::normalize(): normalization must be done from integral to floating-point type");
return value/FloatingPoint(std::numeric_limits<Integral>::max());
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_arithmetic<Integral>::value && std::is_signed<Integral>::value, FloatingPoint>::type normalize(Integral value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"Math::normalize(): normalization must be done from integral to floating-point type");
return Math::max(value/FloatingPoint(std::numeric_limits<Integral>::max()), FloatingPoint(-1));
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_unsigned<typename Integral::Type>::value, FloatingPoint>::type normalize(const Integral& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"Math::normalize(): normalization must be done from integral to floating-point type");
return FloatingPoint(value)/typename FloatingPoint::Type(std::numeric_limits<typename Integral::Type>::max());
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_signed<typename Integral::Type>::value, FloatingPoint>::type normalize(const Integral& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"Math::normalize(): normalization must be done from integral to floating-point type");
return Math::max(FloatingPoint(value)/typename FloatingPoint::Type(std::numeric_limits<typename Integral::Type>::max()), FloatingPoint(-1));
}
#endif
/**
@brief Denormalize floating-point value
Converts floating-point value in range @f$ [0, 1] @f$ to full range of given
*unsigned* integral type or range @f$ [-1, 1] @f$ to full range of given *signed*
integral type.
@note For best precision, `FloatingPoint` type should be always larger that
resulting `Integral` type (e.g. @ref Magnum::Float "Float" to
@ref Magnum::Short "Short", @ref Magnum::Double "Double" to @ref Magnum::Int "Int"
and similarly for vector types).
@attention Return value for floating point numbers outside the normalized
range is undefined.
@see @ref normalize()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class Integral, class FloatingPoint> inline Integral denormalize(const FloatingPoint& value);
#else
template<class Integral, class FloatingPoint> inline typename std::enable_if<std::is_arithmetic<FloatingPoint>::value, Integral>::type denormalize(FloatingPoint value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"Math::denormalize(): denormalization must be done from floating-point to integral type");
return Integral(value*std::numeric_limits<Integral>::max());
}
template<class Integral, class FloatingPoint> inline typename std::enable_if<std::is_arithmetic<typename Integral::Type>::value, Integral>::type denormalize(const FloatingPoint& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"Math::denormalize(): denormalization must be done from floating-point to integral type");
return Integral(value*std::numeric_limits<typename Integral::Type>::max());
}
#endif
/*@}*/
}}
#ifdef MAGNUM_BUILD_DEPRECATED
/* In order to make the deprecated normalize() / denormalize() functions
available in the original header. The Packing.h header depends on this file
so it needs to be included after it. */
#include "Magnum/Math/Packing.h"
#endif
#endif

135
src/Magnum/Math/Packing.h

@ -0,0 +1,135 @@
#ifndef Magnum_Math_Packing_h
#define Magnum_Math_Packing_h
/*
This file is part of Magnum.
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016
Vladimír Vondruš <mosra@centrum.cz>
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the "Software"),
to deal in the Software without restriction, including without limitation
the rights to use, copy, modify, merge, publish, distribute, sublicense,
and/or sell copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included
in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.
*/
#include <limits>
#include "Magnum/Math/Functions.h"
namespace Magnum { namespace Math {
/**
@brief Unpack integral value into a floating-point representation
Converts integral value from full range of given *unsigned* integral type to
value in range @f$ [0, 1] @f$ or from *signed* integral to range @f$ [-1, 1] @f$.
@note For best precision, resulting `FloatingPoint` type should be always
larger that `Integral` type (e.g. @ref Magnum::Float "Float" from
@ref Magnum::Short "Short", @ref Magnum::Double "Double" from
@ref Magnum::Int "Int" and similarly for vector types).
@attention To ensure the integral type is correctly detected when using
literals, this function should be called with both template parameters
explicit, e.g.:
@code
// Literal type is (signed) char, but we assumed unsigned char, a != 1.0f
Float a = Math::unpack<Float>('\xFF');
// b = 1.0f
Float b = Math::unpack<Float, UnsignedByte>('\xFF');
@endcode
@see @ref pack()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class FloatingPoint, class Integral> inline FloatingPoint unpack(const Integral& value);
#else
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_arithmetic<Integral>::value && std::is_unsigned<Integral>::value, FloatingPoint>::type unpack(Integral value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"unpacking must be done from integral to floating-point type");
return value/FloatingPoint(std::numeric_limits<Integral>::max());
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_arithmetic<Integral>::value && std::is_signed<Integral>::value, FloatingPoint>::type unpack(Integral value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"unpacking must be done from integral to floating-point type");
return Math::max(value/FloatingPoint(std::numeric_limits<Integral>::max()), FloatingPoint(-1.0));
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_unsigned<typename Integral::Type>::value, FloatingPoint>::type unpack(const Integral& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"unpacking must be done from integral to floating-point type");
return FloatingPoint(value)/typename FloatingPoint::Type(std::numeric_limits<typename Integral::Type>::max());
}
template<class FloatingPoint, class Integral> inline typename std::enable_if<std::is_signed<typename Integral::Type>::value, FloatingPoint>::type unpack(const Integral& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"unpacking must be done from integral to floating-point type");
return Math::max(FloatingPoint(value)/typename FloatingPoint::Type(std::numeric_limits<typename Integral::Type>::max()), FloatingPoint(-1.0));
}
#endif
#ifdef MAGNUM_BUILD_DEPRECATED
/** @copybrief unpack()
* @deprecated Use @ref unpack() instead.
*/
template<class FloatingPoint, class Integral> CORRADE_DEPRECATED("use unpack() instead") inline FloatingPoint normalize(const Integral& value) {
return unpack<FloatingPoint, Integral>(value);
}
#endif
/**
@brief Pack floating-point value into an integer representation
Converts floating-point value in range @f$ [0, 1] @f$ to full range of given
*unsigned* integral type or range @f$ [-1, 1] @f$ to full range of given *signed*
integral type.
@note For best precision, `FloatingPoint` type should be always larger that
resulting `Integral` type (e.g. @ref Magnum::Float "Float" to
@ref Magnum::Short "Short", @ref Magnum::Double "Double" to @ref Magnum::Int "Int"
and similarly for vector types).
@attention Return value for floating point numbers outside the normalized
range is undefined.
@see @ref unpack()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class Integral, class FloatingPoint> inline Integral pack(const FloatingPoint& value);
#else
template<class Integral, class FloatingPoint> inline typename std::enable_if<std::is_arithmetic<FloatingPoint>::value, Integral>::type pack(FloatingPoint value) {
static_assert(std::is_floating_point<FloatingPoint>::value && std::is_integral<Integral>::value,
"packing must be done from floating-point to integral type");
return Integral(value*std::numeric_limits<Integral>::max());
}
template<class Integral, class FloatingPoint> inline typename std::enable_if<std::is_arithmetic<typename Integral::Type>::value, Integral>::type pack(const FloatingPoint& value) {
static_assert(std::is_floating_point<typename FloatingPoint::Type>::value && std::is_integral<typename Integral::Type>::value,
"packing must be done from floating-point to integral type");
return Integral(value*std::numeric_limits<typename Integral::Type>::max());
}
#endif
#ifdef MAGNUM_BUILD_DEPRECATED
/** @copybrief pack()
* @deprecated Use @ref pack() instead.
*/
template<class Integral, class FloatingPoint> CORRADE_DEPRECATED("use pack() instead") inline Integral denormalize(const FloatingPoint& value) {
return pack<Integral, FloatingPoint>(value);
}
#endif
}}
#endif

1
src/Magnum/Math/Test/CMakeLists.txt

@ -26,6 +26,7 @@
corrade_add_test(MathBoolVectorTest BoolVectorTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathConstantsTest ConstantsTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathFunctionsTest FunctionsTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathPackingTest PackingTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathTagsTest TagsTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathTypeTraitsTest TypeTraitsTest.cpp LIBRARIES MagnumMathTestLib)

10
src/Magnum/Math/Test/ColorTest.cpp

@ -75,7 +75,7 @@ struct ColorTest: Corrade::TestSuite::Tester {
void constructOneValue();
void constructParts();
void constructConversion();
void constructNormalization();
void constructPacking();
void constructCopy();
void convert();
@ -121,7 +121,7 @@ ColorTest::ColorTest() {
&ColorTest::constructOneValue,
&ColorTest::constructParts,
&ColorTest::constructConversion,
&ColorTest::constructNormalization,
&ColorTest::constructPacking,
&ColorTest::constructCopy,
&ColorTest::convert,
@ -264,13 +264,13 @@ void ColorTest::constructConversion() {
CORRADE_VERIFY((std::is_nothrow_constructible<Color4, Color4ub>::value));
}
void ColorTest::constructNormalization() {
void ColorTest::constructPacking() {
constexpr Color3 a(1.0f, 0.5f, 0.75f);
auto b = Math::denormalize<Color3ub>(a);
auto b = Math::pack<Color3ub>(a);
CORRADE_COMPARE(b, Color3ub(255, 127, 191));
constexpr Color4 c(1.0f, 0.5f, 0.75f, 0.25f);
auto d = Math::denormalize<Color4ub>(c);
auto d = Math::pack<Color4ub>(c);
CORRADE_COMPARE(d, Color4ub(255, 127, 191, 63));
}

180
src/Magnum/Math/Test/FunctionsTest.cpp

@ -58,14 +58,6 @@ struct FunctionsTest: Corrade::TestSuite::Tester {
void lerpBool();
void lerpInverted();
void fma();
void normalizeUnsigned();
void normalizeSigned();
void denormalizeUnsigned();
void denormalizeSigned();
void renormalizeUnsinged();
void renormalizeSinged();
void normalizeTypeDeduction();
void logIntegral();
void log2();
@ -110,14 +102,6 @@ FunctionsTest::FunctionsTest() {
&FunctionsTest::lerpBool,
&FunctionsTest::lerpInverted,
&FunctionsTest::fma,
&FunctionsTest::normalizeUnsigned,
&FunctionsTest::normalizeSigned,
&FunctionsTest::denormalizeUnsigned,
&FunctionsTest::denormalizeSigned,
&FunctionsTest::renormalizeUnsinged,
&FunctionsTest::renormalizeSinged,
&FunctionsTest::normalizeTypeDeduction,
&FunctionsTest::logIntegral,
&FunctionsTest::log2,
@ -292,170 +276,6 @@ void FunctionsTest::fma() {
Vector3(6.75f, 3.25f, -0.4f));
}
void FunctionsTest::normalizeUnsigned() {
CORRADE_COMPARE((Math::normalize<Float, UnsignedByte>(0)), 0.0f);
CORRADE_COMPARE((Math::normalize<Float, UnsignedByte>(255)), 1.0f);
CORRADE_COMPARE((Math::normalize<Double, UnsignedInt>(0)), 0.0);
CORRADE_COMPARE((Math::normalize<Double, UnsignedInt>(std::numeric_limits<UnsignedInt>::max())), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE((Math::normalize<long double, UnsignedLong>(0)), 0.0);
CORRADE_COMPARE((Math::normalize<long double, UnsignedLong>(std::numeric_limits<UnsignedLong>::max())), 1.0);
#endif
CORRADE_COMPARE((Math::normalize<Float, UnsignedShort>(0)), 0.0f);
CORRADE_COMPARE((Math::normalize<Float, UnsignedShort>(std::numeric_limits<UnsignedShort>::max())), 1.0f);
CORRADE_COMPARE((Math::normalize<Float, UnsignedShort>(8192)), 0.125002f);
CORRADE_COMPARE((Math::normalize<Float, UnsignedShort>(49152)), 0.750011f);
CORRADE_COMPARE(Math::normalize<Vector3>(Vector3ub(0, 127, 255)), Vector3(0.0f, 0.498039f, 1.0f));
}
void FunctionsTest::normalizeSigned() {
CORRADE_COMPARE((Math::normalize<Float, Byte>(127)), 1.0f);
CORRADE_COMPARE((Math::normalize<Float, Byte>(0)), 0.0f);
CORRADE_COMPARE((Math::normalize<Float, Byte>(-128)), -1.0f);
CORRADE_COMPARE((Math::normalize<Float, Short>(std::numeric_limits<Short>::min())), -1.0f);
CORRADE_COMPARE((Math::normalize<Float, Short>(0)), 0.0f);
CORRADE_COMPARE((Math::normalize<Float, Short>(std::numeric_limits<Short>::max())), 1.0f);
CORRADE_COMPARE((Math::normalize<Double, Int>(std::numeric_limits<Int>::min())), -1.0);
CORRADE_COMPARE((Math::normalize<Double, Int>(0)), 0.0);
CORRADE_COMPARE((Math::normalize<Double, Int>(std::numeric_limits<Int>::max())), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE((Math::normalize<long double, Long>(std::numeric_limits<Long>::min())), -1.0);
CORRADE_COMPARE((Math::normalize<long double, Long>(0)), 0.0);
CORRADE_COMPARE((Math::normalize<long double, Long>(std::numeric_limits<Long>::max())), 1.0);
#endif
CORRADE_COMPARE((Math::normalize<Float, Short>(16384)), 0.500015f);
CORRADE_COMPARE((Math::normalize<Float, Short>(-16384)), -0.500015f);
CORRADE_COMPARE(Math::normalize<Vector3>(Vector3b(0, -127, 64)), Vector3(0.0f, -1.0f, 0.503937f));
}
void FunctionsTest::denormalizeUnsigned() {
CORRADE_COMPARE(Math::denormalize<UnsignedByte>(0.0f), 0);
CORRADE_COMPARE(Math::denormalize<UnsignedByte>(1.0f), 255);
CORRADE_COMPARE(Math::denormalize<UnsignedShort>(0.0f), 0);
CORRADE_COMPARE(Math::denormalize<UnsignedShort>(1.0f), std::numeric_limits<UnsignedShort>::max());
CORRADE_COMPARE(Math::denormalize<UnsignedInt>(0.0), 0);
CORRADE_COMPARE(Math::denormalize<UnsignedInt>(1.0), std::numeric_limits<UnsignedInt>::max());
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::denormalize<UnsignedLong>(0.0l), 0);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::denormalize<UnsignedLong>(1.0l), std::numeric_limits<UnsignedLong>::max());
}
#endif
CORRADE_COMPARE(Math::denormalize<UnsignedShort>(0.33f), 21626);
CORRADE_COMPARE(Math::denormalize<UnsignedShort>(0.66f), 43253);
CORRADE_COMPARE(Math::denormalize<Vector3ub>(Vector3(0.0f, 0.5f, 1.0f)), Vector3ub(0, 127, 255));
}
void FunctionsTest::denormalizeSigned() {
CORRADE_COMPARE(Math::denormalize<Byte>(-1.0f), -127);
CORRADE_COMPARE(Math::denormalize<Byte>(0.0f), 0);
CORRADE_COMPARE(Math::denormalize<Byte>(1.0f), 127);
CORRADE_COMPARE(Math::denormalize<Short>(-1.0f), std::numeric_limits<Short>::min()+1);
CORRADE_COMPARE(Math::denormalize<Short>(0.0f), 0);
CORRADE_COMPARE(Math::denormalize<Short>(1.0f), std::numeric_limits<Short>::max());
#ifndef MAGNUM_TARGET_GLES
CORRADE_COMPARE(Math::denormalize<Int>(-1.0), std::numeric_limits<Int>::min()+1);
CORRADE_COMPARE(Math::denormalize<Int>(0.0), 0);
CORRADE_COMPARE(Math::denormalize<Int>(1.0), std::numeric_limits<Int>::max());
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::denormalize<Long>(-1.0l), std::numeric_limits<Long>::min()+1);
}
CORRADE_COMPARE(Math::denormalize<Long>(0.0l), 0);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::denormalize<Long>(1.0l), std::numeric_limits<Long>::max());
}
#endif
CORRADE_COMPARE(Math::denormalize<Short>(-0.33f), -10813);
CORRADE_COMPARE(Math::denormalize<Short>(0.66f), 21626);
CORRADE_COMPARE(Math::denormalize<Vector3b>(Vector3(0.0f, -1.0f, 0.5f)), Vector3b(0, -127, 63));
}
void FunctionsTest::renormalizeUnsinged() {
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<UnsignedByte>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<UnsignedByte>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<UnsignedShort>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<UnsignedShort>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::normalize<Double>(Math::denormalize<UnsignedInt>(0.0)), 0.0);
CORRADE_COMPARE(Math::normalize<Double>(Math::denormalize<UnsignedInt>(1.0)), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::normalize<long double>(Math::denormalize<UnsignedLong>(0.0l)), 0.0l);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::normalize<long double>(Math::denormalize<UnsignedLong>(1.0l)), 1.0l);
}
#endif
}
void FunctionsTest::renormalizeSinged() {
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Byte>(-1.0f)), -1.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Byte>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Byte>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Short>(-1.0f)), -1.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Short>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::normalize<Float>(Math::denormalize<Short>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::normalize<Double>(Math::denormalize<Int>(-1.0)), -1.0);
CORRADE_COMPARE(Math::normalize<Double>(Math::denormalize<Int>(0.0)), 0.0);
CORRADE_COMPARE(Math::normalize<Double>(Math::denormalize<Int>(1.0)), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::normalize<long double>(Math::denormalize<Long>(-1.0l)), -1.0l);
CORRADE_COMPARE(Math::normalize<long double>(Math::denormalize<Long>(0.0l)), 0.0l);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::normalize<long double>(Math::denormalize<Long>(1.0l)), 1.0l);
}
#endif
}
void FunctionsTest::normalizeTypeDeduction() {
if(std::is_signed<char>::value)
CORRADE_COMPARE(Math::normalize<Float>('\x7F'), 1.0f);
else {
/* Raspberry Pi `char` is unsigned (huh) */
CORRADE_VERIFY(std::is_unsigned<char>::value);
CORRADE_COMPARE(Math::normalize<Float>('\x7F'), 0.498039f);
}
CORRADE_COMPARE((Math::normalize<Float, Byte>('\x7F')), 1.0f);
}
void FunctionsTest::logIntegral() {
CORRADE_COMPARE(Math::log(2, 256), 8ul);
CORRADE_COMPARE(Math::log(256, 2), 0ul);

226
src/Magnum/Math/Test/PackingTest.cpp

@ -0,0 +1,226 @@
/*
This file is part of Magnum.
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016
Vladimír Vondruš <mosra@centrum.cz>
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the "Software"),
to deal in the Software without restriction, including without limitation
the rights to use, copy, modify, merge, publish, distribute, sublicense,
and/or sell copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included
in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.
*/
#include <Corrade/TestSuite/Tester.h>
#include "Magnum/Math/Packing.h"
#include "Magnum/Math/Vector3.h"
namespace Magnum { namespace Math { namespace Test {
struct PackingTest: Corrade::TestSuite::Tester {
explicit PackingTest();
void unpackUnsigned();
void unpackSigned();
void packUnsigned();
void packSigned();
void reunpackUnsinged();
void reunpackSinged();
void unpackTypeDeduction();
};
typedef Math::Vector3<Float> Vector3;
typedef Math::Vector3<UnsignedByte> Vector3ub;
typedef Math::Vector3<Byte> Vector3b;
PackingTest::PackingTest() {
addTests({&PackingTest::unpackUnsigned,
&PackingTest::unpackSigned,
&PackingTest::packUnsigned,
&PackingTest::packSigned,
&PackingTest::reunpackUnsinged,
&PackingTest::reunpackSinged,
&PackingTest::unpackTypeDeduction});
}
void PackingTest::unpackUnsigned() {
CORRADE_COMPARE((Math::unpack<Float, UnsignedByte>(0)), 0.0f);
CORRADE_COMPARE((Math::unpack<Float, UnsignedByte>(255)), 1.0f);
CORRADE_COMPARE((Math::unpack<Double, UnsignedInt>(0)), 0.0);
CORRADE_COMPARE((Math::unpack<Double, UnsignedInt>(std::numeric_limits<UnsignedInt>::max())), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE((Math::unpack<long double, UnsignedLong>(0)), 0.0);
CORRADE_COMPARE((Math::unpack<long double, UnsignedLong>(std::numeric_limits<UnsignedLong>::max())), 1.0);
#endif
CORRADE_COMPARE((Math::unpack<Float, UnsignedShort>(0)), 0.0f);
CORRADE_COMPARE((Math::unpack<Float, UnsignedShort>(std::numeric_limits<UnsignedShort>::max())), 1.0f);
CORRADE_COMPARE((Math::unpack<Float, UnsignedShort>(8192)), 0.125002f);
CORRADE_COMPARE((Math::unpack<Float, UnsignedShort>(49152)), 0.750011f);
CORRADE_COMPARE(Math::unpack<Vector3>(Vector3ub(0, 127, 255)), Vector3(0.0f, 0.498039f, 1.0f));
}
void PackingTest::unpackSigned() {
CORRADE_COMPARE((Math::unpack<Float, Byte>(127)), 1.0f);
CORRADE_COMPARE((Math::unpack<Float, Byte>(0)), 0.0f);
CORRADE_COMPARE((Math::unpack<Float, Byte>(-128)), -1.0f);
CORRADE_COMPARE((Math::unpack<Float, Short>(std::numeric_limits<Short>::min())), -1.0f);
CORRADE_COMPARE((Math::unpack<Float, Short>(0)), 0.0f);
CORRADE_COMPARE((Math::unpack<Float, Short>(std::numeric_limits<Short>::max())), 1.0f);
CORRADE_COMPARE((Math::unpack<Double, Int>(std::numeric_limits<Int>::min())), -1.0);
CORRADE_COMPARE((Math::unpack<Double, Int>(0)), 0.0);
CORRADE_COMPARE((Math::unpack<Double, Int>(std::numeric_limits<Int>::max())), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE((Math::unpack<long double, Long>(std::numeric_limits<Long>::min())), -1.0);
CORRADE_COMPARE((Math::unpack<long double, Long>(0)), 0.0);
CORRADE_COMPARE((Math::unpack<long double, Long>(std::numeric_limits<Long>::max())), 1.0);
#endif
CORRADE_COMPARE((Math::unpack<Float, Short>(16384)), 0.500015f);
CORRADE_COMPARE((Math::unpack<Float, Short>(-16384)), -0.500015f);
CORRADE_COMPARE(Math::unpack<Vector3>(Vector3b(0, -127, 64)), Vector3(0.0f, -1.0f, 0.503937f));
}
void PackingTest::packUnsigned() {
CORRADE_COMPARE(Math::pack<UnsignedByte>(0.0f), 0);
CORRADE_COMPARE(Math::pack<UnsignedByte>(1.0f), 255);
CORRADE_COMPARE(Math::pack<UnsignedShort>(0.0f), 0);
CORRADE_COMPARE(Math::pack<UnsignedShort>(1.0f), std::numeric_limits<UnsignedShort>::max());
CORRADE_COMPARE(Math::pack<UnsignedInt>(0.0), 0);
CORRADE_COMPARE(Math::pack<UnsignedInt>(1.0), std::numeric_limits<UnsignedInt>::max());
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::pack<UnsignedLong>(0.0l), 0);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::pack<UnsignedLong>(1.0l), std::numeric_limits<UnsignedLong>::max());
}
#endif
CORRADE_COMPARE(Math::pack<UnsignedShort>(0.33f), 21626);
CORRADE_COMPARE(Math::pack<UnsignedShort>(0.66f), 43253);
CORRADE_COMPARE(Math::pack<Vector3ub>(Vector3(0.0f, 0.5f, 1.0f)), Vector3ub(0, 127, 255));
}
void PackingTest::packSigned() {
CORRADE_COMPARE(Math::pack<Byte>(-1.0f), -127);
CORRADE_COMPARE(Math::pack<Byte>(0.0f), 0);
CORRADE_COMPARE(Math::pack<Byte>(1.0f), 127);
CORRADE_COMPARE(Math::pack<Short>(-1.0f), std::numeric_limits<Short>::min()+1);
CORRADE_COMPARE(Math::pack<Short>(0.0f), 0);
CORRADE_COMPARE(Math::pack<Short>(1.0f), std::numeric_limits<Short>::max());
#ifndef MAGNUM_TARGET_GLES
CORRADE_COMPARE(Math::pack<Int>(-1.0), std::numeric_limits<Int>::min()+1);
CORRADE_COMPARE(Math::pack<Int>(0.0), 0);
CORRADE_COMPARE(Math::pack<Int>(1.0), std::numeric_limits<Int>::max());
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::pack<Long>(-1.0l), std::numeric_limits<Long>::min()+1);
}
CORRADE_COMPARE(Math::pack<Long>(0.0l), 0);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::pack<Long>(1.0l), std::numeric_limits<Long>::max());
}
#endif
CORRADE_COMPARE(Math::pack<Short>(-0.33f), -10813);
CORRADE_COMPARE(Math::pack<Short>(0.66f), 21626);
CORRADE_COMPARE(Math::pack<Vector3b>(Vector3(0.0f, -1.0f, 0.5f)), Vector3b(0, -127, 63));
}
void PackingTest::reunpackUnsinged() {
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<UnsignedByte>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<UnsignedByte>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<UnsignedShort>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<UnsignedShort>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::unpack<Double>(Math::pack<UnsignedInt>(0.0)), 0.0);
CORRADE_COMPARE(Math::unpack<Double>(Math::pack<UnsignedInt>(1.0)), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::unpack<long double>(Math::pack<UnsignedLong>(0.0l)), 0.0l);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::unpack<long double>(Math::pack<UnsignedLong>(1.0l)), 1.0l);
}
#endif
}
void PackingTest::reunpackSinged() {
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Byte>(-1.0f)), -1.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Byte>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Byte>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Short>(-1.0f)), -1.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Short>(0.0f)), 0.0f);
CORRADE_COMPARE(Math::unpack<Float>(Math::pack<Short>(1.0f)), 1.0f);
CORRADE_COMPARE(Math::unpack<Double>(Math::pack<Int>(-1.0)), -1.0);
CORRADE_COMPARE(Math::unpack<Double>(Math::pack<Int>(0.0)), 0.0);
CORRADE_COMPARE(Math::unpack<Double>(Math::pack<Int>(1.0)), 1.0);
#ifndef MAGNUM_TARGET_WEBGL
CORRADE_COMPARE(Math::unpack<long double>(Math::pack<Long>(-1.0l)), -1.0l);
CORRADE_COMPARE(Math::unpack<long double>(Math::pack<Long>(0.0l)), 0.0l);
{
#ifdef CORRADE_MSVC2015_COMPATIBILITY
CORRADE_EXPECT_FAIL("Long double (de)normalization is broken on MSVC <= 2015.");
#endif
CORRADE_COMPARE(Math::unpack<long double>(Math::pack<Long>(1.0l)), 1.0l);
}
#endif
}
void PackingTest::unpackTypeDeduction() {
if(std::is_signed<char>::value)
CORRADE_COMPARE(Math::unpack<Float>('\x7F'), 1.0f);
else {
/* Raspberry Pi `char` is unsigned (huh) */
CORRADE_VERIFY(std::is_unsigned<char>::value);
CORRADE_COMPARE(Math::unpack<Float>('\x7F'), 0.498039f);
}
CORRADE_COMPARE((Math::unpack<Float, Byte>('\x7F')), 1.0f);
}
}}}
CORRADE_TEST_MAIN(Magnum::Math::Test::PackingTest)

10
src/Magnum/Test/FramebufferGLTest.cpp

@ -1119,8 +1119,8 @@ void FramebufferGLTest::read() {
CORRADE_COMPARE(framebuffer.checkStatus(FramebufferTarget::Read), Framebuffer::Status::Complete);
CORRADE_COMPARE(framebuffer.checkStatus(FramebufferTarget::Draw), Framebuffer::Status::Complete);
Renderer::setClearColor(Math::normalize<Color4>(Color4ub(128, 64, 32, 17)));
Renderer::setClearDepth(Math::normalize<Float, UnsignedShort>(48352));
Renderer::setClearColor(Math::unpack<Color4>(Color4ub(128, 64, 32, 17)));
Renderer::setClearDepth(Math::unpack<Float, UnsignedShort>(48352));
Renderer::setClearStencil(67);
framebuffer.clear(FramebufferClear::Color|FramebufferClear::Depth|FramebufferClear::Stencil);
@ -1198,8 +1198,8 @@ void FramebufferGLTest::readBuffer() {
CORRADE_COMPARE(framebuffer.checkStatus(FramebufferTarget::Read), Framebuffer::Status::Complete);
CORRADE_COMPARE(framebuffer.checkStatus(FramebufferTarget::Draw), Framebuffer::Status::Complete);
Renderer::setClearColor(Math::normalize<Color4>(Color4ub(128, 64, 32, 17)));
Renderer::setClearDepth(Math::normalize<Float, UnsignedShort>(48352));
Renderer::setClearColor(Math::unpack<Color4>(Color4ub(128, 64, 32, 17)));
Renderer::setClearDepth(Math::unpack<Float, UnsignedShort>(48352));
Renderer::setClearStencil(67);
framebuffer.clear(FramebufferClear::Color|FramebufferClear::Depth|FramebufferClear::Stencil);
@ -1742,7 +1742,7 @@ void FramebufferGLTest::blit() {
CORRADE_COMPARE(b.checkStatus(FramebufferTarget::Draw), Framebuffer::Status::Complete);
/* Clear first with some color and second with another */
Renderer::setClearColor(Math::normalize<Color4>(Color4ub(128, 64, 32, 17)));
Renderer::setClearColor(Math::unpack<Color4>(Color4ub(128, 64, 32, 17)));
a.clear(FramebufferClear::Color);
Renderer::setClearColor({});
b.clear(FramebufferClear::Color);

94
src/Magnum/Test/MeshGLTest.cpp

@ -590,7 +590,7 @@ void MeshGLTest::addVertexBufferInt() {
void MeshGLTest::addVertexBufferFloat() {
typedef Attribute<0, Float> Attribute;
const Float data[] = { 0.0f, -0.7f, Math::normalize<Float, UnsignedByte>(96) };
const Float data[] = { 0.0f, -0.7f, Math::unpack<Float, UnsignedByte>(96) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -619,7 +619,7 @@ void MeshGLTest::addVertexBufferDouble() {
typedef Attribute<0, Double> Attribute;
const Double data[] = { 0.0, -0.7, Math::normalize<Double, UnsignedShort>(45828) };
const Double data[] = { 0.0, -0.7, Math::unpack<Double, UnsignedShort>(45828) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -692,7 +692,7 @@ void MeshGLTest::addVertexBufferVectorNi() {
void MeshGLTest::addVertexBufferVectorN() {
typedef Attribute<0, Vector3> Attribute;
const Vector3 data[] = { {}, {0.0f, -0.9f, 1.0f}, Math::normalize<Vector3>(Color3ub(96, 24, 156)) };
const Vector3 data[] = { {}, {0.0f, -0.9f, 1.0f}, Math::unpack<Vector3>(Color3ub(96, 24, 156)) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -723,7 +723,7 @@ void MeshGLTest::addVertexBufferVectorNd() {
const Vector4d data[] = {
{}, {0.0, -0.9, 1.0, 1.25},
Math::normalize<Vector4d>(Math::Vector4<UnsignedShort>(315, 65201, 2576, 12))
Math::unpack<Vector4d>(Math::Vector4<UnsignedShort>(315, 65201, 2576, 12))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -748,7 +748,7 @@ void MeshGLTest::addVertexBufferMatrixNxN() {
const Matrix3x3 data[] = {
{},
Matrix3x3::fromDiagonal({0.0f, -0.9f, 1.0f}),
Matrix3x3::fromDiagonal(Math::normalize<Vector3>(Color3ub(96, 24, 156)))
Matrix3x3::fromDiagonal(Math::unpack<Vector3>(Color3ub(96, 24, 156)))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -777,7 +777,7 @@ void MeshGLTest::addVertexBufferMatrixNxNd() {
const Matrix3x3d data[] = {
{},
Matrix3x3d::fromDiagonal({0.0, -0.9, 1.0}),
Matrix3x3d::fromDiagonal(Math::normalize<Vector3d>(Math::Vector3<UnsignedShort>(315, 65201, 2576)))
Matrix3x3d::fromDiagonal(Math::unpack<Vector3d>(Math::Vector3<UnsignedShort>(315, 65201, 2576)))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -813,7 +813,7 @@ void MeshGLTest::addVertexBufferMatrixMxN() {
const Matrix3x4 data[] = {
{},
Matrix3x4::fromDiagonal({0.0f, -0.9f, 1.0f}),
Matrix3x4::fromDiagonal(Math::normalize<Vector3>(Color3ub(96, 24, 156)))
Matrix3x4::fromDiagonal(Math::unpack<Vector3>(Color3ub(96, 24, 156)))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -843,7 +843,7 @@ void MeshGLTest::addVertexBufferMatrixMxNd() {
const Matrix3x4d data[] = {
{},
Matrix3x4d::fromDiagonal({0.0f, -0.9f, 1.0f}),
Matrix3x4d::fromDiagonal(Math::normalize<Vector3d>(Math::Vector3<UnsignedShort>(315, 65201, 2576)))
Matrix3x4d::fromDiagonal(Math::unpack<Vector3d>(Math::Vector3<UnsignedShort>(315, 65201, 2576)))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1000,7 +1000,7 @@ void MeshGLTest::addVertexBufferFloatWithHalfFloat() {
void MeshGLTest::addVertexBufferFloatWithDouble() {
typedef Attribute<0, Float> Attribute;
const Double data[] = { 0.0, -0.7, Math::normalize<Double, UnsignedByte>(186) };
const Double data[] = { 0.0, -0.7, Math::unpack<Double, UnsignedByte>(186) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1082,7 +1082,7 @@ void MeshGLTest::addVertexBufferLessVectorComponents() {
const Vector3 data[] = {
{}, {0.0f, -0.9f, 1.0f},
Math::normalize<Vector3>(Color3ub(96, 24, 156))
Math::unpack<Vector3>(Color3ub(96, 24, 156))
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1241,14 +1241,14 @@ void MeshGLTest::addVertexBufferMultiple() {
1.0f, -0.5f,
/* Second attribute */
Math::normalize<Float, UnsignedByte>(64),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(56),
Math::normalize<Float, UnsignedByte>(15),
Math::normalize<Float, UnsignedByte>(164),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(97),
Math::normalize<Float, UnsignedByte>(28)
Math::unpack<Float, UnsignedByte>(64),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(56),
Math::unpack<Float, UnsignedByte>(15),
Math::unpack<Float, UnsignedByte>(164),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(97),
Math::unpack<Float, UnsignedByte>(28)
};
Buffer buffer;
@ -1283,14 +1283,14 @@ void MeshGLTest::addVertexBufferMultipleGaps() {
1.0f, -0.5f, 0.0f, 0.0f,
/* Second attribute */
Math::normalize<Float, UnsignedByte>(64),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(56), 0.0f,
Math::normalize<Float, UnsignedByte>(15),
Math::normalize<Float, UnsignedByte>(164),
Math::normalize<Float, UnsignedByte>(17), 0.0f,
Math::normalize<Float, UnsignedByte>(97),
Math::normalize<Float, UnsignedByte>(28), 0.0f, 0.0f
Math::unpack<Float, UnsignedByte>(64),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(56), 0.0f,
Math::unpack<Float, UnsignedByte>(15),
Math::unpack<Float, UnsignedByte>(164),
Math::unpack<Float, UnsignedByte>(17), 0.0f,
Math::unpack<Float, UnsignedByte>(97),
Math::unpack<Float, UnsignedByte>(28), 0.0f, 0.0f
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1321,14 +1321,14 @@ namespace {
0.0f, /* Offset */
/* First vertex */
Math::normalize<Float, UnsignedByte>(64),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(56),
Math::normalize<Float, UnsignedByte>(15),
Math::normalize<Float, UnsignedByte>(164),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(97),
Math::normalize<Float, UnsignedByte>(28),
Math::unpack<Float, UnsignedByte>(64),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(56),
Math::unpack<Float, UnsignedByte>(15),
Math::unpack<Float, UnsignedByte>(164),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(97),
Math::unpack<Float, UnsignedByte>(28),
/* Second vertex */
0.3f, 0.1f, 0.5f,
@ -1351,14 +1351,14 @@ namespace {
0.0f, 0.0f,
/* Third vertex */
Math::normalize<Float, UnsignedByte>(64),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(56),
Math::normalize<Float, UnsignedByte>(15),
Math::normalize<Float, UnsignedByte>(164),
Math::normalize<Float, UnsignedByte>(17),
Math::normalize<Float, UnsignedByte>(97),
Math::normalize<Float, UnsignedByte>(28),
Math::unpack<Float, UnsignedByte>(64),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(56),
Math::unpack<Float, UnsignedByte>(15),
Math::unpack<Float, UnsignedByte>(164),
Math::unpack<Float, UnsignedByte>(17),
Math::unpack<Float, UnsignedByte>(97),
Math::unpack<Float, UnsignedByte>(28),
/* Fourth vertex */
0.3f, 0.1f, 0.5f,
@ -1502,7 +1502,7 @@ void MeshGLTest::setInstanceCount() {
typedef Attribute<0, Float> Attribute;
const Float data[] = { 0.0f, -0.7f, Math::normalize<Float, UnsignedByte>(96) };
const Float data[] = { 0.0f, -0.7f, Math::unpack<Float, UnsignedByte>(96) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1582,7 +1582,7 @@ void MeshGLTest::setInstanceCountBaseInstance() {
typedef Attribute<0, Float> Attribute;
const Float data[] = { 0.0f, -0.7f, Math::normalize<Float, UnsignedByte>(96) };
const Float data[] = { 0.0f, -0.7f, Math::unpack<Float, UnsignedByte>(96) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1732,7 +1732,7 @@ void MeshGLTest::addVertexBufferInstancedFloat() {
/* Base vertex is ignored for instanced arrays */
-0.7f, /* First instance */
0.3f, /* Second instance */
Math::normalize<Float, UnsignedByte>(96) /* Third instance */
Math::unpack<Float, UnsignedByte>(96) /* Third instance */
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1808,7 +1808,7 @@ void MeshGLTest::addVertexBufferInstancedDouble() {
/* Base vertex is ignored for instanced arrays */
-0.7, /* First instance */
0.3, /* Second instance */
Math::normalize<Double, UnsignedShort>(45828) /* Third instance */
Math::unpack<Double, UnsignedShort>(45828) /* Third instance */
};
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);
@ -1885,7 +1885,7 @@ void MeshGLTest::multiDraw() {
typedef Attribute<0, Float> Attribute;
const Float data[] = { 0.0f, -0.7f, Math::normalize<Float, UnsignedByte>(96) };
const Float data[] = { 0.0f, -0.7f, Math::unpack<Float, UnsignedByte>(96) };
Buffer buffer;
buffer.setData(data, BufferUsage::StaticDraw);

Loading…
Cancel
Save