From 40a5b898a2db9d4dbc0f410246d8ff493aeeb5e2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Vladim=C3=ADr=20Vondru=C5=A1?= Date: Thu, 31 May 2018 16:38:04 +0200 Subject: [PATCH] Math: ability to convert BoolVector from/to external representation. --- doc/changelog.dox | 2 ++ src/Magnum/Math/BoolVector.h | 10 ++++++ src/Magnum/Math/Test/BoolVectorTest.cpp | 43 ++++++++++++++++++++++++- 3 files changed, 54 insertions(+), 1 deletion(-) diff --git a/doc/changelog.dox b/doc/changelog.dox index 9dea725db..737aae7de 100644 --- a/doc/changelog.dox +++ b/doc/changelog.dox @@ -43,6 +43,8 @@ See also: @subsubsection changelog-lates-new-math Math library - Added @ref Math::Constants::piQuarter() +- Ability to convert @ref Math::BoolVector from and to external + representation @subsection changelog-latest-changes Changes and improvements diff --git a/src/Magnum/Math/BoolVector.h b/src/Magnum/Math/BoolVector.h index b8044f020..ad133882a 100644 --- a/src/Magnum/Math/BoolVector.h +++ b/src/Magnum/Math/BoolVector.h @@ -38,6 +38,8 @@ namespace Magnum { namespace Math { namespace Implementation { + template struct BoolVectorConverter; + /** @todo C++14: use std::make_index_sequence and std::integer_sequence */ template struct Sequence {}; @@ -100,9 +102,17 @@ template class BoolVector { template::value && size != 1, bool>::type> constexpr explicit BoolVector(T value) noexcept: BoolVector(typename Implementation::GenerateSequence::Type(), value ? FullSegmentMask : 0) {} #endif + /** @brief Construct boolean vector from external representation */ + template::from(std::declval()))> constexpr explicit BoolVector(const U& other) noexcept: BoolVector{Implementation::BoolVectorConverter::from(other)} {} + /** @brief Copy constructor */ constexpr /*implicit*/ BoolVector(const BoolVector&) noexcept = default; + /** @brief Convert boolean vector to external representation */ + template::to(std::declval>()))> constexpr explicit operator U() const { + return Implementation::BoolVectorConverter::to(*this); + } + /** * @brief Raw data * @return Array of DataSize length diff --git a/src/Magnum/Math/Test/BoolVectorTest.cpp b/src/Magnum/Math/Test/BoolVectorTest.cpp index cdf9618d7..e4e8d72ba 100644 --- a/src/Magnum/Math/Test/BoolVectorTest.cpp +++ b/src/Magnum/Math/Test/BoolVectorTest.cpp @@ -28,7 +28,27 @@ #include "Magnum/Math/BoolVector.h" -namespace Magnum { namespace Math { namespace Test { +struct BVec3 { + bool x, y, z; +}; + +namespace Magnum { namespace Math { + +namespace Implementation { + +template<> struct BoolVectorConverter<3, BVec3> { + constexpr static BoolVector<3> from(const BVec3& other) { + return (other.x << 0)|(other.y << 1)|(other.z << 2); + } + + constexpr static BVec3 to(const BoolVector<3>& other) { + return {other[0], other[1], other[2]}; + } +}; + +} + +namespace Test { struct BoolVectorTest: Corrade::TestSuite::Tester { explicit BoolVectorTest(); @@ -39,6 +59,8 @@ struct BoolVectorTest: Corrade::TestSuite::Tester { void constructOneValue(); void constructOneElement(); void constructCopy(); + void convert(); + void data(); void compare(); @@ -67,6 +89,8 @@ BoolVectorTest::BoolVectorTest() { &BoolVectorTest::constructOneValue, &BoolVectorTest::constructOneElement, &BoolVectorTest::constructCopy, + &BoolVectorTest::convert, + &BoolVectorTest::data, &BoolVectorTest::compare, @@ -145,6 +169,23 @@ void BoolVectorTest::constructCopy() { CORRADE_VERIFY(std::is_nothrow_copy_assignable::value); } +void BoolVectorTest::convert() { + constexpr BVec3 a{false, true, true}; + constexpr BoolVector<3> b{0x6}; + + constexpr BoolVector<3> c{a}; + CORRADE_COMPARE(c, b); + + constexpr BVec3 d(b); + CORRADE_COMPARE(d.x, a.x); + CORRADE_COMPARE(d.y, a.y); + CORRADE_COMPARE(d.z, a.z); + + /* Implicit conversion is not allowed */ + CORRADE_VERIFY(!(std::is_convertible>::value)); + CORRADE_VERIFY(!(std::is_convertible, BVec3>::value)); +} + void BoolVectorTest::data() { constexpr BoolVector19 a(0x08, 0x03, 0x04);