mirror of
https://github.com/microsoft/terminal.git
synced 2025-12-10 00:48:23 -06:00
add til::math, use it for float conversions to point, size (#5150)
This pull request introduces the `til::math` namespace, which provides some casting functions to be used in support of `til::point` and `til::size`. When point/size want to ingest a floating-point structure, they _must_ be instructed on how to convert those floating-point values into integers.
This enables:
```
Windows::Foundation::Point wfPoint = /* ... */;
til::point tp{ til::math::rounding, wfPoint };
```
Future thoughts: should the TilMath types be stackable? Right now, you cannot get "checked + rounding" behavior (where it throws if it doesn't fit) so everything is saturating.
## PR Checklist
* [x] Closes a request by Michael
* [x] I've discussed this with core contributors already
This commit is contained in:
parent
ef80f665d3
commit
dfc15780c7
@ -1,2 +1,3 @@
|
|||||||
powf
|
powf
|
||||||
sqrtf
|
sqrtf
|
||||||
|
isnan
|
||||||
|
|||||||
@ -482,6 +482,7 @@ cwchar
|
|||||||
cwctype
|
cwctype
|
||||||
cwd
|
cwd
|
||||||
cx
|
cx
|
||||||
|
cxcy
|
||||||
CXFRAME
|
CXFRAME
|
||||||
CXFULLSCREEN
|
CXFULLSCREEN
|
||||||
CXHSCROLL
|
CXHSCROLL
|
||||||
|
|||||||
@ -7,6 +7,7 @@
|
|||||||
|
|
||||||
#include "til/at.h"
|
#include "til/at.h"
|
||||||
#include "til/color.h"
|
#include "til/color.h"
|
||||||
|
#include "til/math.h"
|
||||||
#include "til/some.h"
|
#include "til/some.h"
|
||||||
#include "til/size.h"
|
#include "til/size.h"
|
||||||
#include "til/point.h"
|
#include "til/point.h"
|
||||||
|
|||||||
85
src/inc/til/math.h
Normal file
85
src/inc/til/math.h
Normal file
@ -0,0 +1,85 @@
|
|||||||
|
// Copyright (c) Microsoft Corporation.
|
||||||
|
// Licensed under the MIT license.
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
namespace til
|
||||||
|
{
|
||||||
|
// The til::math namespace contains TIL math guidance casts;
|
||||||
|
// they are intended to be used as the first argument to
|
||||||
|
// floating-point universal converters elsewhere in the til namespace.
|
||||||
|
namespace math
|
||||||
|
{
|
||||||
|
namespace details
|
||||||
|
{
|
||||||
|
struct ceiling_t
|
||||||
|
{
|
||||||
|
template<typename O, typename T>
|
||||||
|
static O cast(T val)
|
||||||
|
{
|
||||||
|
if constexpr (std::is_floating_point_v<T>)
|
||||||
|
{
|
||||||
|
THROW_HR_IF(E_ABORT, ::std::isnan(val));
|
||||||
|
return ::base::saturated_cast<O>(::std::ceil(val));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return ::base::saturated_cast<O>(val);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct flooring_t
|
||||||
|
{
|
||||||
|
template<typename O, typename T>
|
||||||
|
static O cast(T val)
|
||||||
|
{
|
||||||
|
if constexpr (std::is_floating_point_v<T>)
|
||||||
|
{
|
||||||
|
THROW_HR_IF(E_ABORT, ::std::isnan(val));
|
||||||
|
return ::base::saturated_cast<O>(::std::floor(val));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return ::base::saturated_cast<O>(val);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct rounding_t
|
||||||
|
{
|
||||||
|
template<typename O, typename T>
|
||||||
|
static O cast(T val)
|
||||||
|
{
|
||||||
|
if constexpr (std::is_floating_point_v<T>)
|
||||||
|
{
|
||||||
|
THROW_HR_IF(E_ABORT, ::std::isnan(val));
|
||||||
|
return ::base::saturated_cast<O>(::std::round(val));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return ::base::saturated_cast<O>(val);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct truncating_t
|
||||||
|
{
|
||||||
|
template<typename O, typename T>
|
||||||
|
static O cast(T val)
|
||||||
|
{
|
||||||
|
if constexpr (std::is_floating_point_v<T>)
|
||||||
|
{
|
||||||
|
THROW_HR_IF(E_ABORT, ::std::isnan(val));
|
||||||
|
}
|
||||||
|
return ::base::saturated_cast<O>(val);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
static constexpr details::ceiling_t ceiling; // positives become more positive, negatives become less negative
|
||||||
|
static constexpr details::flooring_t flooring; // positives become less positive, negatives become more negative
|
||||||
|
static constexpr details::rounding_t rounding; // it's rounding, from math class
|
||||||
|
static constexpr details::truncating_t truncating; // drop the decimal point, regardless of how close it is to the next value
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -53,6 +53,22 @@ namespace til // Terminal Implementation Library. Also: "Today I Learned"
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// This template will convert to size from anything that has a X and a Y field that are floating-point;
|
||||||
|
// a math type is required.
|
||||||
|
template<typename TilMath, typename TOther>
|
||||||
|
constexpr point(TilMath, const TOther& other, std::enable_if_t<std::is_floating_point_v<decltype(std::declval<TOther>().X)> && std::is_floating_point_v<decltype(std::declval<TOther>().Y)>, int> /*sentinel*/ = 0) :
|
||||||
|
point(TilMath::template cast<ptrdiff_t>(other.X), TilMath::template cast<ptrdiff_t>(other.Y))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// This template will convert to size from anything that has a x and a y field that are floating-point;
|
||||||
|
// a math type is required.
|
||||||
|
template<typename TilMath, typename TOther>
|
||||||
|
constexpr point(TilMath, const TOther& other, std::enable_if_t<std::is_floating_point_v<decltype(std::declval<TOther>().x)> && std::is_floating_point_v<decltype(std::declval<TOther>().y)>, int> /*sentinel*/ = 0) :
|
||||||
|
point(TilMath::template cast<ptrdiff_t>(other.x), TilMath::template cast<ptrdiff_t>(other.y))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
constexpr bool operator==(const point& other) const noexcept
|
constexpr bool operator==(const point& other) const noexcept
|
||||||
{
|
{
|
||||||
return _x == other._x &&
|
return _x == other._x &&
|
||||||
|
|||||||
@ -53,6 +53,30 @@ namespace til // Terminal Implementation Library. Also: "Today I Learned"
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// This template will convert to size from anything that has a X and a Y field that are floating-point;
|
||||||
|
// a math type is required.
|
||||||
|
template<typename TilMath, typename TOther>
|
||||||
|
constexpr size(TilMath, const TOther& other, std::enable_if_t<std::is_floating_point_v<decltype(std::declval<TOther>().X)> && std::is_floating_point_v<decltype(std::declval<TOther>().Y)>, int> /*sentinel*/ = 0) :
|
||||||
|
size(TilMath::template cast<ptrdiff_t>(other.X), TilMath::template cast<ptrdiff_t>(other.Y))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// This template will convert to size from anything that has a cx and a cy field that are floating-point;
|
||||||
|
// a math type is required.
|
||||||
|
template<typename TilMath, typename TOther>
|
||||||
|
constexpr size(TilMath, const TOther& other, std::enable_if_t<std::is_floating_point_v<decltype(std::declval<TOther>().cx)> && std::is_floating_point_v<decltype(std::declval<TOther>().cy)>, int> /*sentinel*/ = 0) :
|
||||||
|
size(TilMath::template cast<ptrdiff_t>(other.cx), TilMath::template cast<ptrdiff_t>(other.cy))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// This template will convert to size from anything that has a Width and a Height field that are floating-point;
|
||||||
|
// a math type is required.
|
||||||
|
template<typename TilMath, typename TOther>
|
||||||
|
constexpr size(TilMath, const TOther& other, std::enable_if_t<std::is_floating_point_v<decltype(std::declval<TOther>().Width)> && std::is_floating_point_v<decltype(std::declval<TOther>().Height)>, int> /*sentinel*/ = 0) :
|
||||||
|
size(TilMath::template cast<ptrdiff_t>(other.Width), TilMath::template cast<ptrdiff_t>(other.Height))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
constexpr bool operator==(const size& other) const noexcept
|
constexpr bool operator==(const size& other) const noexcept
|
||||||
{
|
{
|
||||||
return _width == other._width &&
|
return _width == other._width &&
|
||||||
|
|||||||
127
src/til/ut_til/MathTests.cpp
Normal file
127
src/til/ut_til/MathTests.cpp
Normal file
@ -0,0 +1,127 @@
|
|||||||
|
// Copyright (c) Microsoft Corporation.
|
||||||
|
// Licensed under the MIT license.
|
||||||
|
|
||||||
|
#include "precomp.h"
|
||||||
|
|
||||||
|
#include "til/math.h"
|
||||||
|
|
||||||
|
using namespace WEX::Common;
|
||||||
|
using namespace WEX::Logging;
|
||||||
|
using namespace WEX::TestExecution;
|
||||||
|
|
||||||
|
class MathTests
|
||||||
|
{
|
||||||
|
TEST_CLASS(MathTests);
|
||||||
|
|
||||||
|
template<typename TG, typename TX = ptrdiff_t>
|
||||||
|
struct TestCase
|
||||||
|
{
|
||||||
|
TG given;
|
||||||
|
TX expected;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<class TilMath, typename TG, typename TX, int N>
|
||||||
|
static void _RunCases(TilMath, const std::array<TestCase<TG, TX>, N>& cases)
|
||||||
|
{
|
||||||
|
for (const auto& tc : cases)
|
||||||
|
{
|
||||||
|
VERIFY_ARE_EQUAL(tc.expected, TilMath::template cast<decltype(tc.expected)>(tc.given));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD(Truncating)
|
||||||
|
{
|
||||||
|
std::array<TestCase<long double, ptrdiff_t>, 8> cases{
|
||||||
|
TestCase<long double, ptrdiff_t>{ 1., 1 },
|
||||||
|
{ 1.9, 1 },
|
||||||
|
{ -7.1, -7 },
|
||||||
|
{ -8.5, -8 },
|
||||||
|
{ PTRDIFF_MAX + 0.5, PTRDIFF_MAX },
|
||||||
|
{ PTRDIFF_MIN - 0.5, PTRDIFF_MIN },
|
||||||
|
{ INFINITY, PTRDIFF_MAX },
|
||||||
|
{ -INFINITY, PTRDIFF_MIN },
|
||||||
|
};
|
||||||
|
|
||||||
|
_RunCases(til::math::truncating, cases);
|
||||||
|
|
||||||
|
const auto fn = []() {
|
||||||
|
const auto v = til::math::details::truncating_t::cast<ptrdiff_t>(NAN);
|
||||||
|
};
|
||||||
|
VERIFY_THROWS_SPECIFIC(fn(), wil::ResultException, [](wil::ResultException& e) { return e.GetErrorCode() == E_ABORT; });
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD(Ceiling)
|
||||||
|
{
|
||||||
|
std::array<TestCase<long double, ptrdiff_t>, 8> cases{
|
||||||
|
TestCase<long double, ptrdiff_t>{ 1., 1 },
|
||||||
|
{ 1.9, 2 },
|
||||||
|
{ -7.1, -7 },
|
||||||
|
{ -8.5, -8 },
|
||||||
|
{ PTRDIFF_MAX + 0.5, PTRDIFF_MAX },
|
||||||
|
{ PTRDIFF_MIN - 0.5, PTRDIFF_MIN },
|
||||||
|
{ INFINITY, PTRDIFF_MAX },
|
||||||
|
{ -INFINITY, PTRDIFF_MIN },
|
||||||
|
};
|
||||||
|
|
||||||
|
_RunCases(til::math::ceiling, cases);
|
||||||
|
|
||||||
|
const auto fn = []() {
|
||||||
|
const auto v = til::math::details::ceiling_t::cast<ptrdiff_t>(NAN);
|
||||||
|
};
|
||||||
|
VERIFY_THROWS_SPECIFIC(fn(), wil::ResultException, [](wil::ResultException& e) { return e.GetErrorCode() == E_ABORT; });
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD(Flooring)
|
||||||
|
{
|
||||||
|
std::array<TestCase<long double, ptrdiff_t>, 8> cases{
|
||||||
|
TestCase<long double, ptrdiff_t>{ 1., 1 },
|
||||||
|
{ 1.9, 1 },
|
||||||
|
{ -7.1, -8 },
|
||||||
|
{ -8.5, -9 },
|
||||||
|
{ PTRDIFF_MAX + 0.5, PTRDIFF_MAX },
|
||||||
|
{ PTRDIFF_MIN - 0.5, PTRDIFF_MIN },
|
||||||
|
{ INFINITY, PTRDIFF_MAX },
|
||||||
|
{ -INFINITY, PTRDIFF_MIN },
|
||||||
|
};
|
||||||
|
|
||||||
|
_RunCases(til::math::flooring, cases);
|
||||||
|
|
||||||
|
const auto fn = []() {
|
||||||
|
const auto v = til::math::details::flooring_t::cast<ptrdiff_t>(NAN);
|
||||||
|
};
|
||||||
|
VERIFY_THROWS_SPECIFIC(fn(), wil::ResultException, [](wil::ResultException& e) { return e.GetErrorCode() == E_ABORT; });
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD(Rounding)
|
||||||
|
{
|
||||||
|
std::array<TestCase<long double, ptrdiff_t>, 8> cases{
|
||||||
|
TestCase<long double, ptrdiff_t>{ 1., 1 },
|
||||||
|
{ 1.9, 2 },
|
||||||
|
{ -7.1, -7 },
|
||||||
|
{ -8.5, -9 },
|
||||||
|
{ PTRDIFF_MAX + 0.5, PTRDIFF_MAX },
|
||||||
|
{ PTRDIFF_MIN - 0.5, PTRDIFF_MIN },
|
||||||
|
{ INFINITY, PTRDIFF_MAX },
|
||||||
|
{ -INFINITY, PTRDIFF_MIN },
|
||||||
|
};
|
||||||
|
|
||||||
|
_RunCases(til::math::rounding, cases);
|
||||||
|
|
||||||
|
const auto fn = []() {
|
||||||
|
const auto v = til::math::details::rounding_t::cast<ptrdiff_t>(NAN);
|
||||||
|
};
|
||||||
|
VERIFY_THROWS_SPECIFIC(fn(), wil::ResultException, [](wil::ResultException& e) { return e.GetErrorCode() == E_ABORT; });
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_METHOD(NormalIntegers)
|
||||||
|
{
|
||||||
|
std::array<TestCase<ptrdiff_t, int>, 4> cases{
|
||||||
|
TestCase<ptrdiff_t, int>{ 1, 1 },
|
||||||
|
{ -1, -1 },
|
||||||
|
{ PTRDIFF_MAX, INT_MAX },
|
||||||
|
{ PTRDIFF_MIN, INT_MIN },
|
||||||
|
};
|
||||||
|
|
||||||
|
_RunCases(til::math::rounding, cases);
|
||||||
|
}
|
||||||
|
};
|
||||||
@ -604,4 +604,101 @@ class PointTests
|
|||||||
|
|
||||||
// All ptrdiff_ts fit into a float, so there's no exception tests.
|
// All ptrdiff_ts fit into a float, so there's no exception tests.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename T>
|
||||||
|
struct PointTypeWith_xy
|
||||||
|
{
|
||||||
|
T x, y;
|
||||||
|
};
|
||||||
|
template<typename T>
|
||||||
|
struct PointTypeWith_XY
|
||||||
|
{
|
||||||
|
T X, Y;
|
||||||
|
};
|
||||||
|
TEST_METHOD(CastFromFloatWithMathTypes)
|
||||||
|
{
|
||||||
|
PointTypeWith_xy<float> xyFloatIntegral{ 1.f, 2.f };
|
||||||
|
PointTypeWith_xy<float> xyFloat{ 1.6f, 2.4f };
|
||||||
|
PointTypeWith_XY<double> XYDoubleIntegral{ 3., 4. };
|
||||||
|
PointTypeWith_XY<double> XYDouble{ 3.6, 4.4 };
|
||||||
|
Log::Comment(L"0.) Ceiling");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::ceiling, xyFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::ceiling, xyFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 2, 3 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::ceiling, XYDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::ceiling, XYDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 4, 5 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"1.) Flooring");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::flooring, xyFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::flooring, xyFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::flooring, XYDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::flooring, XYDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"2.) Rounding");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::rounding, xyFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::rounding, xyFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 2, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::rounding, XYDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::rounding, XYDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 4, 4 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"3.) Truncating");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::truncating, xyFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::truncating, xyFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::truncating, XYDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::point converted{ til::math::truncating, XYDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::point{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -515,4 +515,140 @@ class SizeTests
|
|||||||
|
|
||||||
// All ptrdiff_ts fit into a float, so there's no exception tests.
|
// All ptrdiff_ts fit into a float, so there's no exception tests.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename T>
|
||||||
|
struct SizeTypeWith_XY
|
||||||
|
{
|
||||||
|
T X, Y;
|
||||||
|
};
|
||||||
|
template<typename T>
|
||||||
|
struct SizeTypeWith_cxcy
|
||||||
|
{
|
||||||
|
T cx, cy;
|
||||||
|
};
|
||||||
|
template<typename T>
|
||||||
|
struct SizeTypeWith_WidthHeight
|
||||||
|
{
|
||||||
|
T Width, Height;
|
||||||
|
};
|
||||||
|
TEST_METHOD(CastFromFloatWithMathTypes)
|
||||||
|
{
|
||||||
|
SizeTypeWith_XY<float> XYFloatIntegral{ 1.f, 2.f };
|
||||||
|
SizeTypeWith_XY<float> XYFloat{ 1.6f, 2.4f };
|
||||||
|
SizeTypeWith_cxcy<double> cxcyDoubleIntegral{ 3., 4. };
|
||||||
|
SizeTypeWith_cxcy<double> cxcyDouble{ 3.6, 4.4 };
|
||||||
|
SizeTypeWith_WidthHeight<double> WHDoubleIntegral{ 5., 6. };
|
||||||
|
SizeTypeWith_WidthHeight<double> WHDouble{ 5.6, 6.4 };
|
||||||
|
Log::Comment(L"0.) Ceiling");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, XYFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, XYFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 2, 3 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, cxcyDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, cxcyDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 4, 5 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, WHDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::ceiling, WHDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 6, 7 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"1.) Flooring");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, XYFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, XYFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, cxcyDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, cxcyDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, WHDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::flooring, WHDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"2.) Rounding");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, XYFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, XYFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 2, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, cxcyDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, cxcyDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 4, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, WHDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::rounding, WHDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 6, 6 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Log::Comment(L"3.) Truncating");
|
||||||
|
{
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, XYFloatIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, XYFloat };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 1, 2 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, cxcyDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, cxcyDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 3, 4 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, WHDoubleIntegral };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
{
|
||||||
|
til::size converted{ til::math::truncating, WHDouble };
|
||||||
|
VERIFY_ARE_EQUAL((til::size{ 5, 6 }), converted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -18,6 +18,7 @@ SOURCES = \
|
|||||||
ColorTests.cpp \
|
ColorTests.cpp \
|
||||||
OperatorTests.cpp \
|
OperatorTests.cpp \
|
||||||
PointTests.cpp \
|
PointTests.cpp \
|
||||||
|
MathTests.cpp \
|
||||||
RectangleTests.cpp \
|
RectangleTests.cpp \
|
||||||
SizeTests.cpp \
|
SizeTests.cpp \
|
||||||
SomeTests.cpp \
|
SomeTests.cpp \
|
||||||
|
|||||||
@ -13,6 +13,7 @@
|
|||||||
<ClCompile Include="BitmapTests.cpp" />
|
<ClCompile Include="BitmapTests.cpp" />
|
||||||
<ClCompile Include="OperatorTests.cpp" />
|
<ClCompile Include="OperatorTests.cpp" />
|
||||||
<ClCompile Include="PointTests.cpp" />
|
<ClCompile Include="PointTests.cpp" />
|
||||||
|
<ClCompile Include="MathTests.cpp" />
|
||||||
<ClCompile Include="RectangleTests.cpp" />
|
<ClCompile Include="RectangleTests.cpp" />
|
||||||
<ClCompile Include="SizeTests.cpp" />
|
<ClCompile Include="SizeTests.cpp" />
|
||||||
<ClCompile Include="ColorTests.cpp" />
|
<ClCompile Include="ColorTests.cpp" />
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user