Bump version to 21.06.18.1
[LibreOffice.git] / include / tools / helpers.hxx
blobe105ed355b664395b740dfe9e9a9349d58929d8d
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 */
9 #ifndef INCLUDED_TOOLS_HELPERS_HXX
10 #define INCLUDED_TOOLS_HELPERS_HXX
12 #include <sal/config.h>
13 #include <sal/types.h>
14 #include <tools/long.hxx>
15 #include <o3tl/safeint.hxx>
16 #include <cassert>
17 #include <type_traits>
19 template<typename T>
20 inline
21 typename std::enable_if<
22 std::is_signed<T>::value || std::is_floating_point<T>::value, long >::type
23 MinMax(T nVal, tools::Long nMin, tools::Long nMax)
25 assert(nMin <= nMax);
26 if (nVal >= nMin)
28 if (nVal <= nMax)
29 return static_cast<tools::Long>(nVal);
30 else
31 return nMax;
33 else
35 return nMin;
39 template<typename T>
40 inline
41 typename std::enable_if<
42 std::is_unsigned<T>::value, long >::type
43 MinMax(T nVal, tools::Long nMin, tools::Long nMax)
45 assert(nMin <= nMax);
46 if (nMax < 0)
48 return nMax;
50 else
52 if (nMin < 0 || nVal >= static_cast<unsigned long>(nMin))
54 if (nVal <= static_cast<unsigned long>(nMax))
55 return static_cast<tools::Long>(nVal);
56 else
57 return nMax;
59 else
61 return nMin;
66 inline sal_uInt32 AlignedWidth4Bytes(sal_uInt32 nWidthBits)
68 if (nWidthBits > SAL_MAX_UINT32 - 31)
69 nWidthBits = SAL_MAX_UINT32;
70 else
71 nWidthBits += 31;
72 return (nWidthBits >> 5) << 2;
75 inline tools::Long FRound( double fVal )
77 return fVal > 0.0 ? static_cast<tools::Long>( fVal + 0.5 ) : -static_cast<tools::Long>( -fVal + 0.5 );
80 //valid range: (-180,180]
81 template <typename T>
82 [[nodiscard]] inline typename std::enable_if<std::is_signed<T>::value, T>::type
83 NormAngle180(T angle)
85 while (angle <= -180)
86 angle += 360;
87 while (angle > 180)
88 angle -= 360;
89 return angle;
92 //valid range: [0,360)
93 template <typename T> [[nodiscard]] inline T NormAngle360(T angle)
95 while (angle < 0)
96 angle += 360;
97 while (angle >= 360)
98 angle -= 360;
99 return angle;
102 /** Convert 100th-mm to twips
104 A twip is 1/20 of a point, one inch is equal to 72 points, and
105 one inch is 2,540 100th-mm.
107 Thus:
108 twips = n * 72 / 2,540 / 20
109 = n * 72 / 127
111 Adding 63 (half of 127) fixes truncation issues in int arithmetic.
113 This formula is (n>=0) ? (n*72+63) / 127 : (n*72-63) / 127
115 inline sal_Int64 sanitiseMm100ToTwip(sal_Int64 n)
117 if (n >= 0)
119 if (o3tl::checked_multiply<sal_Int64>(n, 72, n) || o3tl::checked_add<sal_Int64>(n, 63, n))
120 n = SAL_MAX_INT64;
122 else
124 if (o3tl::checked_multiply<sal_Int64>(n, 72, n) || o3tl::checked_sub<sal_Int64>(n, 63, n))
125 n = SAL_MIN_INT64;
127 return n / 127; // 127 is 2,540 100th-mm divided by 20pts
130 #endif
132 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */