Browse Source

Math: move batch functionality to FunctionsBatch.h.

Avoids including a (relatively) large ArrayView in Functions.h. Yes,
we are now at a point where 500 lines matter.
pull/331/head
Vladimír Vondruš 7 years ago
parent
commit
c12680ec38
  1. 6
      doc/changelog.dox
  2. 1
      doc/snippets/MagnumMath.cpp
  3. 1
      src/Magnum/Math/CMakeLists.txt
  4. 97
      src/Magnum/Math/Functions.h
  5. 128
      src/Magnum/Math/FunctionsBatch.h
  6. 1
      src/Magnum/Math/Test/CMakeLists.txt
  7. 97
      src/Magnum/Math/Test/FunctionsBatchTest.cpp
  8. 51
      src/Magnum/Math/Test/FunctionsTest.cpp
  9. 1
      src/Magnum/Math/Test/RangeTest.cpp
  10. 2
      src/Magnum/MeshTools/CompressIndices.cpp

6
doc/changelog.dox

@ -317,6 +317,12 @@ See also:
up compile times. Backwards compatibility is not provided, when using
@ref Math types with @ref Corrade::Utility::Configuration or
@ref Corrade::Utility::Arguments you have to include the header explicitly
- Batch @ref Math::min(Containers::ArrayView<const T>),
@ref Math::max(Containers::ArrayView<const T>) and
@ref Math::minmax(Containers::ArrayView<const T>) were moved to a new
@ref Magnum/Math/FunctionsBatch.h header in order to speed up compile
times. Backwards compatibility is not provided, when using these functions
you have to include the header explicitly
- Removed all aliases to @ref GL library functionality in the root namespace
(and root include path) which were deprecated in 2018.04 and everything
related to this change:

1
doc/snippets/MagnumMath.cpp

@ -28,6 +28,7 @@
#include "Magnum/Magnum.h"
#include "Magnum/Math/Color.h"
#include "Magnum/Math/FunctionsBatch.h"
#include "Magnum/Math/Bezier.h"
#include "Magnum/Math/CubicHermite.h"
#include "Magnum/Math/DualComplex.h"

1
src/Magnum/Math/CMakeLists.txt

@ -38,6 +38,7 @@ set(MagnumMath_HEADERS
DualQuaternion.h
Frustum.h
Functions.h
FunctionsBatch.h
Half.h
Intersection.h
Math.h

97
src/Magnum/Math/Functions.h

@ -33,7 +33,6 @@
#include <cstdlib> /* std::div() */
#include <type_traits>
#include <utility>
#include <Corrade/Containers/ArrayView.h>
#include "Magnum/visibility.h"
#include "Magnum/Math/Vector.h"
@ -267,7 +266,8 @@ template<std::size_t size, class T> inline Vector<size, T> pow(const Vector<size
@brief Minimum
<em>NaN</em>s passed in @p value parameter are propagated.
@see @ref max(), @ref minmax(), @ref clamp(), @ref Vector::min()
@see @ref max(), @ref minmax(), @ref clamp(),
@ref min(Corrade::Containers::ArrayView<const T>), @ref Vector::min()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class T> inline T min(T value, T min);
@ -289,35 +289,12 @@ template<std::size_t size, class T> inline Vector<size, T> min(const Vector<size
return out;
}
/**
@brief Minimum of a range
If the range is empty, returns default-constructed value.
*/
template<class T> inline T min(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T out(range[0]);
for(std::size_t i = 1; i != range.size(); ++i)
out = min(out, range[i]);
return out;
}
/** @overload */
template<class T> inline T min(std::initializer_list<T> list) {
return min(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline T min(const T(&array)[size]) {
return min(Corrade::Containers::arrayView(array));
}
/**
@brief Maximum
<em>NaN</em>s passed in @p value parameter are propagated.
@see @ref min(), @ref minmax(), @ref clamp(), @ref Vector::max()
@see @ref min(), @ref minmax(), @ref clamp(),
@ref max(Corrade::Containers::ArrayView<const T>), @ref Vector::max()
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
template<class T> inline T max(T value, T max);
@ -339,34 +316,11 @@ template<std::size_t size, class T> inline Vector<size, T> max(const Vector<size
return out;
}
/**
@brief Maximum of a range
If the range is empty, returns default-constructed value.
*/
template<class T> inline T max(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T out(range[0]);
for(std::size_t i = 1; i != range.size(); ++i)
out = max(out, range[i]);
return out;
}
/** @overload */
template<class T> inline T max(std::initializer_list<T> list) {
return max(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline T max(const T(&array)[size]) {
return max(Corrade::Containers::arrayView(array));
}
/**
@brief Minimum and maximum of two values
@see @ref min(), @ref max(), @ref clamp(), @ref Vector::minmax(),
@see @ref min(), @ref max(), @ref clamp(),
@ref minmax(Corrade::Containers::ArrayView<const T>), @ref Vector::minmax(),
@ref Range::Range(const std::pair<VectorType, VectorType>&)
*/
#ifdef DOXYGEN_GENERATING_OUTPUT
@ -384,45 +338,6 @@ template<std::size_t size, class T> inline std::pair<Vector<size, T>, Vector<siz
}
#endif
namespace Implementation {
template<class T> inline typename std::enable_if<std::is_arithmetic<T>::value, void>::type minmax(T& min, T& max, T value) {
if(value < min)
min = value;
else if(value > max)
max = value;
}
template<std::size_t size, class T> inline void minmax(Vector<size, T>& min, Vector<size, T>& max, const Vector<size, T>& value) {
for(std::size_t i = 0; i != size; ++i)
minmax(min[i], max[i], value[i]);
}
}
/**
@brief Minimum and maximum of a range
If the range is empty, returns default-constructed values.
@see @ref Range::Range(const std::pair<VectorType, VectorType>&)
*/
template<class T> inline std::pair<T, T> minmax(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T min{range[0]}, max{range[0]};
for(std::size_t i = 1; i != range.size(); ++i)
Implementation::minmax(min, max, range[i]);
return {min, max};
}
/** @overload */
template<class T> inline std::pair<T, T> minmax(std::initializer_list<T> list) {
return minmax(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline std::pair<T, T> minmax(const T(&array)[size]) {
return minmax(Corrade::Containers::arrayView(array));
}
/**
@brief Clamp value

128
src/Magnum/Math/FunctionsBatch.h

@ -0,0 +1,128 @@
#ifndef Magnum_Math_FunctionsBatch_h
#define Magnum_Math_FunctionsBatch_h
/*
This file is part of Magnum.
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019
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.
*/
/** @file
* @brief Batch functions usable with scalar and vector types
*/
#include <Corrade/Containers/ArrayView.h>
#include "Magnum/Math/Functions.h"
namespace Magnum { namespace Math {
/**
@brief Minimum of a range
If the range is empty, returns default-constructed value.
@see @ref min(T, T)
*/
template<class T> inline T min(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T out(range[0]);
for(std::size_t i = 1; i != range.size(); ++i)
out = min(out, range[i]);
return out;
}
/** @overload */
template<class T> inline T min(std::initializer_list<T> list) {
return min(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline T min(const T(&array)[size]) {
return min(Corrade::Containers::arrayView(array));
}
/**
@brief Maximum of a range
If the range is empty, returns default-constructed value.
*/
template<class T> inline T max(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T out(range[0]);
for(std::size_t i = 1; i != range.size(); ++i)
out = max(out, range[i]);
return out;
}
/** @overload */
template<class T> inline T max(std::initializer_list<T> list) {
return max(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline T max(const T(&array)[size]) {
return max(Corrade::Containers::arrayView(array));
}
namespace Implementation {
template<class T> inline typename std::enable_if<std::is_arithmetic<T>::value, void>::type minmax(T& min, T& max, T value) {
if(value < min)
min = value;
else if(value > max)
max = value;
}
template<std::size_t size, class T> inline void minmax(Vector<size, T>& min, Vector<size, T>& max, const Vector<size, T>& value) {
for(std::size_t i = 0; i != size; ++i)
minmax(min[i], max[i], value[i]);
}
}
/**
@brief Minimum and maximum of a range
If the range is empty, returns default-constructed values.
@see @ref Range::Range(const std::pair<VectorType, VectorType>&)
*/
template<class T> inline std::pair<T, T> minmax(Corrade::Containers::ArrayView<const T> range) {
if(range.empty()) return {};
T min{range[0]}, max{range[0]};
for(std::size_t i = 1; i != range.size(); ++i)
Implementation::minmax(min, max, range[i]);
return {min, max};
}
/** @overload */
template<class T> inline std::pair<T, T> minmax(std::initializer_list<T> list) {
return minmax(Corrade::Containers::ArrayView<const T>{list.begin(), list.size()});
}
/** @overload */
template<class T, std::size_t size> inline std::pair<T, T> minmax(const T(&array)[size]) {
return minmax(Corrade::Containers::arrayView(array));
}
}}
#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(MathFunctionsBatchTest FunctionsBatchTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathHalfTest HalfTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathPackingTest PackingTest.cpp LIBRARIES MagnumMathTestLib)
corrade_add_test(MathTagsTest TagsTest.cpp LIBRARIES MagnumMathTestLib)

97
src/Magnum/Math/Test/FunctionsBatchTest.cpp

@ -0,0 +1,97 @@
/*
This file is part of Magnum.
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019
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/FunctionsBatch.h"
#include "Magnum/Math/Vector3.h"
namespace Magnum { namespace Math { namespace Test { namespace {
struct FunctionsBatchTest: Corrade::TestSuite::Tester {
explicit FunctionsBatchTest();
void minList();
void maxList();
void minmaxList();
};
typedef Math::Vector2<Float> Vector2;
typedef Math::Vector3<Int> Vector3i;
FunctionsBatchTest::FunctionsBatchTest() {
addTests({&FunctionsBatchTest::minList,
&FunctionsBatchTest::maxList,
&FunctionsBatchTest::minmaxList});
}
void FunctionsBatchTest::minList() {
CORRADE_COMPARE(Math::min({5, -2, 9}), -2);
CORRADE_COMPARE(Math::min({Vector3i(5, -3, 2),
Vector3i(-2, 14, 7),
Vector3i(9, -5, 18)}), Vector3i(-2, -5, 2));
CORRADE_COMPARE(Math::min(std::initializer_list<Vector3i>{}), Vector3i{});
const Int array[]{5, -2, 9};
CORRADE_COMPARE(Math::min(array), -2);
}
void FunctionsBatchTest::maxList() {
CORRADE_COMPARE(Math::max({5, -2, 9}), 9);
CORRADE_COMPARE(Math::max({Vector3i(5, -3, 2),
Vector3i(-2, 14, 7),
Vector3i(9, -5, 18)}), Vector3i(9, 14, 18));
CORRADE_COMPARE(Math::max(std::initializer_list<Vector3i>{}), Vector3i{});
const Int array[]{5, -2, 9};
CORRADE_COMPARE(Math::max(array), 9);
}
void FunctionsBatchTest::minmaxList() {
const auto expected = std::make_pair(-3.0f, 2.0f);
CORRADE_COMPARE(Math::minmax({-1.0f, 2.0f, -3.0f}), expected);
CORRADE_COMPARE(Math::minmax({-1.0f, -3.0f, 2.0f}), expected);
CORRADE_COMPARE(Math::minmax({2.0f, -1.0f, -3.0f}), expected);
CORRADE_COMPARE(Math::minmax({2.0f, -3.0f, -1.0f}), expected);
CORRADE_COMPARE(Math::minmax({-3.0f, 2.0f, -1.0f}), expected);
CORRADE_COMPARE(Math::minmax({-3.0f, -1.0f, 2.0f}), expected);
const std::pair<Vector2, Vector2> expectedVec{Vector2{-3.0f, -2.0f}, Vector2{2.0f, 3.0f}};
CORRADE_COMPARE(Math::minmax({Vector2{-1.0f, 3.0f}, Vector2{2.0f, 1.0f}, Vector2{-3.0f, -2.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-1.0f, 1.0f}, Vector2{-3.0f, 3.0f}, Vector2{2.0f, -2.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{2.0f, -2.0f}, Vector2{-1.0f, 1.0f}, Vector2{-3.0f, 3.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{2.0f, 1.0f}, Vector2{-3.0f, -2.0f}, Vector2{-1.0f, 3.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-3.0f, 3.0f}, Vector2{2.0f, -2.0f}, Vector2{-1.0f, 1.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-3.0f, -2.0f}, Vector2{-1.0f, 3.0f}, Vector2{2.0f, 1.0f}}), expectedVec);
const Float array[]{-1.0f, 2.0f, -3.0f};
CORRADE_COMPARE(Math::minmax(array), expected);
}
}}}}
CORRADE_TEST_MAIN(Magnum::Math::Test::FunctionsBatchTest)

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

@ -38,11 +38,8 @@ struct FunctionsTest: Corrade::TestSuite::Tester {
void pow();
void min();
void minList();
void max();
void maxList();
void minmax();
void minmaxList();
void clamp();
void nanPropagation();
@ -90,11 +87,8 @@ FunctionsTest::FunctionsTest() {
&FunctionsTest::pow,
&FunctionsTest::min,
&FunctionsTest::minList,
&FunctionsTest::max,
&FunctionsTest::maxList,
&FunctionsTest::minmax,
&FunctionsTest::minmaxList,
&FunctionsTest::clamp,
&FunctionsTest::nanPropagation,
@ -150,36 +144,12 @@ void FunctionsTest::min() {
CORRADE_COMPARE(Math::min(Vector3i{5, -3, 2}, 1), (Vector3i{1, -3, 1}));
}
void FunctionsTest::minList() {
CORRADE_COMPARE(Math::min({5, -2, 9}), -2);
CORRADE_COMPARE(Math::min({Vector3i(5, -3, 2),
Vector3i(-2, 14, 7),
Vector3i(9, -5, 18)}), Vector3i(-2, -5, 2));
CORRADE_COMPARE(Math::min(std::initializer_list<Vector3i>{}), Vector3i{});
const Int array[]{5, -2, 9};
CORRADE_COMPARE(Math::min(array), -2);
}
void FunctionsTest::max() {
CORRADE_COMPARE(Math::max(5, 9), 9);
CORRADE_COMPARE(Math::max(Vector3i(5, -3, 2), Vector3i(9, -5, 18)), Vector3i(9, -3, 18));
CORRADE_COMPARE(Math::max(Vector3i{5, -3, 2}, 3), (Vector3i{5, 3, 3}));
}
void FunctionsTest::maxList() {
CORRADE_COMPARE(Math::max({5, -2, 9}), 9);
CORRADE_COMPARE(Math::max({Vector3i(5, -3, 2),
Vector3i(-2, 14, 7),
Vector3i(9, -5, 18)}), Vector3i(9, 14, 18));
CORRADE_COMPARE(Math::max(std::initializer_list<Vector3i>{}), Vector3i{});
const Int array[]{5, -2, 9};
CORRADE_COMPARE(Math::max(array), 9);
}
void FunctionsTest::minmax() {
const auto expectedScalar = std::make_pair(-5.0f, 4.0f);
CORRADE_COMPARE(Math::minmax(-5.0f, 4.0f), expectedScalar);
@ -192,27 +162,6 @@ void FunctionsTest::minmax() {
CORRADE_COMPARE_AS(Math::minmax(b, a), expectedVector, std::pair<Vector3, Vector3>);
}
void FunctionsTest::minmaxList() {
const auto expected = std::make_pair(-3.0f, 2.0f);
CORRADE_COMPARE(Math::minmax({-1.0f, 2.0f, -3.0f}), expected);
CORRADE_COMPARE(Math::minmax({-1.0f, -3.0f, 2.0f}), expected);
CORRADE_COMPARE(Math::minmax({2.0f, -1.0f, -3.0f}), expected);
CORRADE_COMPARE(Math::minmax({2.0f, -3.0f, -1.0f}), expected);
CORRADE_COMPARE(Math::minmax({-3.0f, 2.0f, -1.0f}), expected);
CORRADE_COMPARE(Math::minmax({-3.0f, -1.0f, 2.0f}), expected);
const std::pair<Vector2, Vector2> expectedVec{Vector2{-3.0f, -2.0f}, Vector2{2.0f, 3.0f}};
CORRADE_COMPARE(Math::minmax({Vector2{-1.0f, 3.0f}, Vector2{2.0f, 1.0f}, Vector2{-3.0f, -2.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-1.0f, 1.0f}, Vector2{-3.0f, 3.0f}, Vector2{2.0f, -2.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{2.0f, -2.0f}, Vector2{-1.0f, 1.0f}, Vector2{-3.0f, 3.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{2.0f, 1.0f}, Vector2{-3.0f, -2.0f}, Vector2{-1.0f, 3.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-3.0f, 3.0f}, Vector2{2.0f, -2.0f}, Vector2{-1.0f, 1.0f}}), expectedVec);
CORRADE_COMPARE(Math::minmax({Vector2{-3.0f, -2.0f}, Vector2{-1.0f, 3.0f}, Vector2{2.0f, 1.0f}}), expectedVec);
const Float array[]{-1.0f, 2.0f, -3.0f};
CORRADE_COMPARE(Math::minmax(array), expected);
}
void FunctionsTest::clamp() {
CORRADE_COMPARE(Math::clamp(0.5f, -1.0f, 5.0f), 0.5f);
CORRADE_COMPARE(Math::clamp(-1.6f, -1.0f, 5.0f), -1.0f);

1
src/Magnum/Math/Test/RangeTest.cpp

@ -26,6 +26,7 @@
#include <sstream>
#include <Corrade/TestSuite/Tester.h>
#include "Magnum/Math/FunctionsBatch.h"
#include "Magnum/Math/Range.h"
#include "Magnum/Math/StrictWeakOrdering.h"

2
src/Magnum/MeshTools/CompressIndices.cpp

@ -29,7 +29,7 @@
#include <Corrade/Containers/Array.h>
#include <Corrade/Containers/ArrayViewStl.h>
#include "Magnum/Math/Functions.h"
#include "Magnum/Math/FunctionsBatch.h"
namespace Magnum { namespace MeshTools {

Loading…
Cancel
Save