OpenShot Library | libopenshot-audio  0.1.9
juce_MathsFunctions.h
1 
2 /** @weakgroup juce_core-maths
3  * @{
4  */
5 /*
6  ==============================================================================
7 
8  This file is part of the JUCE library.
9  Copyright (c) 2017 - ROLI Ltd.
10 
11  JUCE is an open source library subject to commercial or open-source
12  licensing.
13 
14  The code included in this file is provided under the terms of the ISC license
15  http://www.isc.org/downloads/software-support-policy/isc-license. Permission
16  To use, copy, modify, and/or distribute this software for any purpose with or
17  without fee is hereby granted provided that the above copyright notice and
18  this permission notice appear in all copies.
19 
20  JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
21  EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
22  DISCLAIMED.
23 
24  ==============================================================================
25 */
26 
27 namespace juce
28 {
29 
30 //==============================================================================
31 /*
32  This file sets up some handy mathematical typdefs and functions.
33 */
34 
35 //==============================================================================
36 // Definitions for the int8, int16, int32, int64 and pointer_sized_int types.
37 
38 /** A platform-independent 8-bit signed integer type. */
39 using int8 = signed char;
40 /** A platform-independent 8-bit unsigned integer type. */
41 using uint8 = unsigned char;
42 /** A platform-independent 16-bit signed integer type. */
43 using int16 = signed short;
44 /** A platform-independent 16-bit unsigned integer type. */
45 using uint16 = unsigned short;
46 /** A platform-independent 32-bit signed integer type. */
47 using int32 = signed int;
48 /** A platform-independent 32-bit unsigned integer type. */
49 using uint32 = unsigned int;
50 
51 #if JUCE_MSVC
52  /** A platform-independent 64-bit integer type. */
53  using int64 = __int64;
54  /** A platform-independent 64-bit unsigned integer type. */
55  using uint64 = unsigned __int64;
56 #else
57  /** A platform-independent 64-bit integer type. */
58  using int64 = long long;
59  /** A platform-independent 64-bit unsigned integer type. */
60  using uint64 = unsigned long long;
61 #endif
62 
63 #ifndef DOXYGEN
64  /** A macro for creating 64-bit literals.
65  Historically, this was needed to support portability with MSVC6, and is kept here
66  so that old code will still compile, but nowadays every compiler will support the
67  LL and ULL suffixes, so you should use those in preference to this macro.
68  */
69  #define literal64bit(longLiteral) (longLiteral##LL)
70 #endif
71 
72 #if JUCE_64BIT
73  /** A signed integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
74  using pointer_sized_int = int64;
75  /** An unsigned integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
76  using pointer_sized_uint = uint64;
77 #elif JUCE_MSVC
78  /** A signed integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
79  using pointer_sized_int = _W64 int;
80  /** An unsigned integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
81  using pointer_sized_uint = _W64 unsigned int;
82 #else
83  /** A signed integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
84  using pointer_sized_int = int;
85  /** An unsigned integer type that's guaranteed to be large enough to hold a pointer without truncating it. */
86  using pointer_sized_uint = unsigned int;
87 #endif
88 
89 #if JUCE_WINDOWS && ! JUCE_MINGW
90  using ssize_t = pointer_sized_int;
91 #endif
92 
93 //==============================================================================
94 // Some indispensable min/max functions
95 
96 /** Returns the larger of two values. */
97 template <typename Type>
98 JUCE_CONSTEXPR Type jmax (Type a, Type b) { return a < b ? b : a; }
99 
100 /** Returns the larger of three values. */
101 template <typename Type>
102 JUCE_CONSTEXPR Type jmax (Type a, Type b, Type c) { return a < b ? (b < c ? c : b) : (a < c ? c : a); }
103 
104 /** Returns the larger of four values. */
105 template <typename Type>
106 JUCE_CONSTEXPR Type jmax (Type a, Type b, Type c, Type d) { return jmax (a, jmax (b, c, d)); }
107 
108 /** Returns the smaller of two values. */
109 template <typename Type>
110 JUCE_CONSTEXPR Type jmin (Type a, Type b) { return b < a ? b : a; }
111 
112 /** Returns the smaller of three values. */
113 template <typename Type>
114 JUCE_CONSTEXPR Type jmin (Type a, Type b, Type c) { return b < a ? (c < b ? c : b) : (c < a ? c : a); }
115 
116 /** Returns the smaller of four values. */
117 template <typename Type>
118 JUCE_CONSTEXPR Type jmin (Type a, Type b, Type c, Type d) { return jmin (a, jmin (b, c, d)); }
119 
120 /** Remaps a normalised value (between 0 and 1) to a target range.
121  This effectively returns (targetRangeMin + value0To1 * (targetRangeMax - targetRangeMin)).
122 */
123 template <typename Type>
124 JUCE_CONSTEXPR Type jmap (Type value0To1, Type targetRangeMin, Type targetRangeMax)
125 {
126  return targetRangeMin + value0To1 * (targetRangeMax - targetRangeMin);
127 }
128 
129 /** Remaps a value from a source range to a target range. */
130 template <typename Type>
131 Type jmap (Type sourceValue, Type sourceRangeMin, Type sourceRangeMax, Type targetRangeMin, Type targetRangeMax)
132 {
133  jassert (sourceRangeMax != sourceRangeMin); // mapping from a range of zero will produce NaN!
134  return targetRangeMin + ((targetRangeMax - targetRangeMin) * (sourceValue - sourceRangeMin)) / (sourceRangeMax - sourceRangeMin);
135 }
136 
137 /** Scans an array of values, returning the minimum value that it contains. */
138 template <typename Type>
139 Type findMinimum (const Type* data, int numValues)
140 {
141  if (numValues <= 0)
142  return Type (0);
143 
144  auto result = *data++;
145 
146  while (--numValues > 0) // (> 0 rather than >= 0 because we've already taken the first sample)
147  {
148  auto v = *data++;
149 
150  if (v < result)
151  result = v;
152  }
153 
154  return result;
155 }
156 
157 /** Scans an array of values, returning the maximum value that it contains. */
158 template <typename Type>
159 Type findMaximum (const Type* values, int numValues)
160 {
161  if (numValues <= 0)
162  return Type (0);
163 
164  auto result = *values++;
165 
166  while (--numValues > 0) // (> 0 rather than >= 0 because we've already taken the first sample)
167  {
168  auto v = *values++;
169 
170  if (result < v)
171  result = v;
172  }
173 
174  return result;
175 }
176 
177 /** Scans an array of values, returning the minimum and maximum values that it contains. */
178 template <typename Type>
179 void findMinAndMax (const Type* values, int numValues, Type& lowest, Type& highest)
180 {
181  if (numValues <= 0)
182  {
183  lowest = Type (0);
184  highest = Type (0);
185  }
186  else
187  {
188  auto mn = *values++;
189  auto mx = mn;
190 
191  while (--numValues > 0) // (> 0 rather than >= 0 because we've already taken the first sample)
192  {
193  auto v = *values++;
194 
195  if (mx < v) mx = v;
196  if (v < mn) mn = v;
197  }
198 
199  lowest = mn;
200  highest = mx;
201  }
202 }
203 
204 //==============================================================================
205 /** Constrains a value to keep it within a given range.
206 
207  This will check that the specified value lies between the lower and upper bounds
208  specified, and if not, will return the nearest value that would be in-range. Effectively,
209  it's like calling jmax (lowerLimit, jmin (upperLimit, value)).
210 
211  Note that it expects that lowerLimit <= upperLimit. If this isn't true,
212  the results will be unpredictable.
213 
214  @param lowerLimit the minimum value to return
215  @param upperLimit the maximum value to return
216  @param valueToConstrain the value to try to return
217  @returns the closest value to valueToConstrain which lies between lowerLimit
218  and upperLimit (inclusive)
219  @see jmin, jmax, jmap
220 */
221 template <typename Type>
222 Type jlimit (Type lowerLimit,
223  Type upperLimit,
224  Type valueToConstrain) noexcept
225 {
226  jassert (lowerLimit <= upperLimit); // if these are in the wrong order, results are unpredictable..
227 
228  return valueToConstrain < lowerLimit ? lowerLimit
229  : (upperLimit < valueToConstrain ? upperLimit
230  : valueToConstrain);
231 }
232 
233 /** Returns true if a value is at least zero, and also below a specified upper limit.
234  This is basically a quicker way to write:
235  @code valueToTest >= 0 && valueToTest < upperLimit
236  @endcode
237 */
238 template <typename Type1, typename Type2>
239 bool isPositiveAndBelow (Type1 valueToTest, Type2 upperLimit) noexcept
240 {
241  jassert (Type1() <= static_cast<Type1> (upperLimit)); // makes no sense to call this if the upper limit is itself below zero..
242  return Type1() <= valueToTest && valueToTest < static_cast<Type1> (upperLimit);
243 }
244 
245 template <typename Type>
246 bool isPositiveAndBelow (int valueToTest, Type upperLimit) noexcept
247 {
248  jassert (upperLimit >= 0); // makes no sense to call this if the upper limit is itself below zero..
249  return static_cast<unsigned int> (valueToTest) < static_cast<unsigned int> (upperLimit);
250 }
251 
252 /** Returns true if a value is at least zero, and also less than or equal to a specified upper limit.
253  This is basically a quicker way to write:
254  @code valueToTest >= 0 && valueToTest <= upperLimit
255  @endcode
256 */
257 template <typename Type1, typename Type2>
258 bool isPositiveAndNotGreaterThan (Type1 valueToTest, Type2 upperLimit) noexcept
259 {
260  jassert (Type1() <= static_cast<Type1> (upperLimit)); // makes no sense to call this if the upper limit is itself below zero..
261  return Type1() <= valueToTest && valueToTest <= static_cast<Type1> (upperLimit);
262 }
263 
264 template <typename Type>
265 bool isPositiveAndNotGreaterThan (int valueToTest, Type upperLimit) noexcept
266 {
267  jassert (upperLimit >= 0); // makes no sense to call this if the upper limit is itself below zero..
268  return static_cast<unsigned int> (valueToTest) <= static_cast<unsigned int> (upperLimit);
269 }
270 
271 /** Computes the absolute difference between two values and returns true if it is less than or equal
272  to a given tolerance, otherwise it returns false.
273 */
274 template <typename Type>
275 bool isWithin (Type a, Type b, Type tolerance) noexcept
276 {
277  return std::abs (a - b) <= tolerance;
278 }
279 
280 /** Returns true if the two numbers are approximately equal. This is useful for floating-point
281  and double comparisons.
282 */
283 template <typename Type>
284 bool approximatelyEqual (Type a, Type b) noexcept
285 {
286  return std::abs (a - b) <= (std::numeric_limits<Type>::epsilon() * std::max (a, b))
287  || std::abs (a - b) < std::numeric_limits<Type>::min();
288 }
289 
290 //==============================================================================
291 /** Handy function for avoiding unused variables warning. */
292 template <typename... Types>
293 void ignoreUnused (Types&&...) noexcept {}
294 
295 /** Handy function for getting the number of elements in a simple const C array.
296  E.g.
297  @code
298  static int myArray[] = { 1, 2, 3 };
299 
300  int numElements = numElementsInArray (myArray) // returns 3
301  @endcode
302 */
303 template <typename Type, int N>
304 int numElementsInArray (Type (&array)[N])
305 {
306  (void) array;
307  (void) sizeof (0[array]); // This line should cause an error if you pass an object with a user-defined subscript operator
308  return N;
309 }
310 
311 //==============================================================================
312 // Some useful maths functions that aren't always present with all compilers and build settings.
313 
314 /** Using juce_hypot is easier than dealing with the different types of hypot function
315  that are provided by the various platforms and compilers. */
316 template <typename Type>
317 Type juce_hypot (Type a, Type b) noexcept
318 {
319  #if JUCE_MSVC
320  return static_cast<Type> (_hypot (a, b));
321  #else
322  return static_cast<Type> (hypot (a, b));
323  #endif
324 }
325 
326 #ifndef DOXYGEN
327 template <>
328 inline float juce_hypot (float a, float b) noexcept
329 {
330  #if JUCE_MSVC
331  return _hypotf (a, b);
332  #else
333  return hypotf (a, b);
334  #endif
335 }
336 #endif
337 
338 #if JUCE_MSVC && ! defined (DOXYGEN) // The MSVC libraries omit these functions for some reason...
339  template<typename Type> Type asinh (Type x) { return std::log (x + std::sqrt (x * x + (Type) 1)); }
340  template<typename Type> Type acosh (Type x) { return std::log (x + std::sqrt (x * x - (Type) 1)); }
341  template<typename Type> Type atanh (Type x) { return (std::log (x + (Type) 1) - std::log (((Type) 1) - x)) / (Type) 2; }
342 #endif
343 
344 //==============================================================================
345 #if JUCE_HAS_CONSTEXPR
346 
347 /** Commonly used mathematical constants
348 
349  @tags{Core}
350 */
351 template <typename FloatType>
352 struct MathConstants
353 {
354  /** A predefined value for Pi */
355  static constexpr FloatType pi = static_cast<FloatType> (3.141592653589793238L);
356 
357  /** A predefined value for 2 * Pi */
358  static constexpr FloatType twoPi = static_cast<FloatType> (2 * 3.141592653589793238L);
359 
360  /** A predefined value for Pi / 2 */
361  static constexpr FloatType halfPi = static_cast<FloatType> (3.141592653589793238L / 2);
362 
363  /** A predefined value for Euler's number */
364  static constexpr FloatType euler = static_cast<FloatType> (2.71828182845904523536L);
365 
366  /** A predefined value for sqrt(2) */
367  static constexpr FloatType sqrt2 = static_cast<FloatType> (1.4142135623730950488L);
368 };
369 
370 #else
371 
372 /** Commonly used mathematical constants
373 
374  @tags{Core}
375 */
376 template <typename FloatType>
378 {
379  /** A predefined value for Pi */
380  static const FloatType pi;
381 
382  /** A predefined value for 2 * Pi */
383  static const FloatType twoPi;
384 
385  /** A predefined value for Pi / 2 */
386  static const FloatType halfPi;
387 
388  /** A predefined value for Euler's number */
389  static const FloatType euler;
390 
391  /** A predefined value for sqrt(2) */
392  static const FloatType sqrt2;
393 };
394 
395 template <typename FloatType>
396 const FloatType MathConstants<FloatType>::pi = static_cast<FloatType> (3.141592653589793238L);
397 
398 template <typename FloatType>
399 const FloatType MathConstants<FloatType>::twoPi = static_cast<FloatType> (2 * 3.141592653589793238L);
400 
401 template <typename FloatType>
402 const FloatType MathConstants<FloatType>::halfPi = static_cast<FloatType> (3.141592653589793238L / 2);
403 
404 template <typename FloatType>
405 const FloatType MathConstants<FloatType>::euler = static_cast<FloatType> (2.71828182845904523536L);
406 
407 template <typename FloatType>
408 const FloatType MathConstants<FloatType>::sqrt2 = static_cast<FloatType> (1.4142135623730950488L);
409 
410 #endif
411 
412 #ifndef DOXYGEN
413 /** A double-precision constant for pi.
414  @deprecated This is deprecated in favour of MathConstants<double>::pi.
415  The reason is that "double_Pi" was a confusing name, and many people misused it,
416  wrongly thinking it meant 2 * pi !
417 */
418 const JUCE_CONSTEXPR double double_Pi = MathConstants<double>::pi;
419 
420 /** A single-precision constant for pi.
421  @deprecated This is deprecated in favour of MathConstants<float>::pi.
422  The reason is that "double_Pi" was a confusing name, and many people misused it,
423  wrongly thinking it meant 2 * pi !
424 */
425 const JUCE_CONSTEXPR float float_Pi = MathConstants<float>::pi;
426 #endif
427 
428 /** Converts an angle in degrees to radians. */
429 template <typename FloatType>
430 JUCE_CONSTEXPR FloatType degreesToRadians (FloatType degrees) noexcept { return degrees * (MathConstants<FloatType>::pi / FloatType (180)); }
431 
432 /** Converts an angle in radians to degrees. */
433 template <typename FloatType>
434 JUCE_CONSTEXPR FloatType radiansToDegrees (FloatType radians) noexcept { return radians * (FloatType (180) / MathConstants<FloatType>::pi); }
435 
436 
437 //==============================================================================
438 /** The isfinite() method seems to vary between platforms, so this is a
439  platform-independent function for it.
440 */
441 template <typename NumericType>
442 bool juce_isfinite (NumericType) noexcept
443 {
444  return true; // Integer types are always finite
445 }
446 
447 template <>
448 inline bool juce_isfinite (float value) noexcept
449 {
450  #if JUCE_WINDOWS && ! JUCE_MINGW
451  return _finite (value) != 0;
452  #else
453  using std::isfinite;
454  return isfinite (value);
455  #endif
456 }
457 
458 template <>
459 inline bool juce_isfinite (double value) noexcept
460 {
461  #if JUCE_WINDOWS && ! JUCE_MINGW
462  return _finite (value) != 0;
463  #else
464  using std::isfinite;
465  return isfinite (value);
466  #endif
467 }
468 
469 //==============================================================================
470 #if JUCE_MSVC
471  #pragma optimize ("t", off)
472  #ifndef __INTEL_COMPILER
473  #pragma float_control (precise, on, push)
474  #endif
475 #endif
476 
477 /** Fast floating-point-to-integer conversion.
478 
479  This is faster than using the normal c++ cast to convert a float to an int, and
480  it will round the value to the nearest integer, rather than rounding it down
481  like the normal cast does.
482 
483  Note that this routine gets its speed at the expense of some accuracy, and when
484  rounding values whose floating point component is exactly 0.5, odd numbers and
485  even numbers will be rounded up or down differently.
486 */
487 template <typename FloatType>
488 int roundToInt (const FloatType value) noexcept
489 {
490  #ifdef __INTEL_COMPILER
491  #pragma float_control (precise, on, push)
492  #endif
493 
494  union { int asInt[2]; double asDouble; } n;
495  n.asDouble = ((double) value) + 6755399441055744.0;
496 
497  #if JUCE_BIG_ENDIAN
498  return n.asInt [1];
499  #else
500  return n.asInt [0];
501  #endif
502 }
503 
504 inline int roundToInt (int value) noexcept
505 {
506  return value;
507 }
508 
509 #if JUCE_MSVC
510  #ifndef __INTEL_COMPILER
511  #pragma float_control (pop)
512  #endif
513  #pragma optimize ("", on) // resets optimisations to the project defaults
514 #endif
515 
516 /** Fast floating-point-to-integer conversion.
517 
518  This is a slightly slower and slightly more accurate version of roundToInt(). It works
519  fine for values above zero, but negative numbers are rounded the wrong way.
520 */
521 inline int roundToIntAccurate (double value) noexcept
522 {
523  #ifdef __INTEL_COMPILER
524  #pragma float_control (pop)
525  #endif
526 
527  return roundToInt (value + 1.5e-8);
528 }
529 
530 //==============================================================================
531 /** Truncates a positive floating-point number to an unsigned int.
532 
533  This is generally faster than static_cast<unsigned int> (std::floor (x))
534  but it only works for positive numbers small enough to be represented as an
535  unsigned int.
536 */
537 template <typename FloatType>
538 unsigned int truncatePositiveToUnsignedInt (FloatType value) noexcept
539 {
540  jassert (value >= static_cast<FloatType> (0));
541  jassert (static_cast<FloatType> (value) <= std::numeric_limits<unsigned int>::max());
542 
543  return static_cast<unsigned int> (value);
544 }
545 
546 //==============================================================================
547 /** Returns true if the specified integer is a power-of-two. */
548 template <typename IntegerType>
549 JUCE_CONSTEXPR bool isPowerOfTwo (IntegerType value)
550 {
551  return (value & (value - 1)) == 0;
552 }
553 
554 /** Returns the smallest power-of-two which is equal to or greater than the given integer. */
555 inline int nextPowerOfTwo (int n) noexcept
556 {
557  --n;
558  n |= (n >> 1);
559  n |= (n >> 2);
560  n |= (n >> 4);
561  n |= (n >> 8);
562  n |= (n >> 16);
563  return n + 1;
564 }
565 
566 /** Returns the index of the highest set bit in a (non-zero) number.
567  So for n=3 this would return 1, for n=7 it returns 2, etc.
568  An input value of 0 is illegal!
569 */
570 int findHighestSetBit (uint32 n) noexcept;
571 
572 /** Returns the number of bits in a 32-bit integer. */
573 inline int countNumberOfBits (uint32 n) noexcept
574 {
575  n -= ((n >> 1) & 0x55555555);
576  n = (((n >> 2) & 0x33333333) + (n & 0x33333333));
577  n = (((n >> 4) + n) & 0x0f0f0f0f);
578  n += (n >> 8);
579  n += (n >> 16);
580  return (int) (n & 0x3f);
581 }
582 
583 /** Returns the number of bits in a 64-bit integer. */
584 inline int countNumberOfBits (uint64 n) noexcept
585 {
586  return countNumberOfBits ((uint32) n) + countNumberOfBits ((uint32) (n >> 32));
587 }
588 
589 /** Performs a modulo operation, but can cope with the dividend being negative.
590  The divisor must be greater than zero.
591 */
592 template <typename IntegerType>
593 IntegerType negativeAwareModulo (IntegerType dividend, const IntegerType divisor) noexcept
594 {
595  jassert (divisor > 0);
596  dividend %= divisor;
597  return (dividend < 0) ? (dividend + divisor) : dividend;
598 }
599 
600 /** Returns the square of its argument. */
601 template <typename NumericType>
602 inline JUCE_CONSTEXPR NumericType square (NumericType n) noexcept
603 {
604  return n * n;
605 }
606 
607 //==============================================================================
608 /** Writes a number of bits into a memory buffer at a given bit index.
609  The buffer is treated as a sequence of 8-bit bytes, and the value is encoded in little-endian order,
610  so for example if startBit = 10, and numBits = 11 then the lower 6 bits of the value would be written
611  into bits 2-8 of targetBuffer[1], and the upper 5 bits of value into bits 0-5 of targetBuffer[2].
612 
613  @see readLittleEndianBitsInBuffer
614 */
615 void writeLittleEndianBitsInBuffer (void* targetBuffer, uint32 startBit, uint32 numBits, uint32 value) noexcept;
616 
617 /** Reads a number of bits from a buffer at a given bit index.
618  The buffer is treated as a sequence of 8-bit bytes, and the value is encoded in little-endian order,
619  so for example if startBit = 10, and numBits = 11 then the lower 6 bits of the result would be read
620  from bits 2-8 of sourceBuffer[1], and the upper 5 bits of the result from bits 0-5 of sourceBuffer[2].
621 
622  @see writeLittleEndianBitsInBuffer
623 */
624 uint32 readLittleEndianBitsInBuffer (const void* sourceBuffer, uint32 startBit, uint32 numBits) noexcept;
625 
626 
627 //==============================================================================
628 #if JUCE_INTEL || defined (DOXYGEN)
629  /** This macro can be applied to a float variable to check whether it contains a denormalised
630  value, and to normalise it if necessary.
631  On CPUs that aren't vulnerable to denormalisation problems, this will have no effect.
632  */
633  #define JUCE_UNDENORMALISE(x) { (x) += 0.1f; (x) -= 0.1f; }
634 #else
635  #define JUCE_UNDENORMALISE(x)
636 #endif
637 
638 //==============================================================================
639 /** This namespace contains a few template classes for helping work out class type variations.
640 */
641 namespace TypeHelpers
642 {
643  /** The ParameterType struct is used to find the best type to use when passing some kind
644  of object as a parameter.
645 
646  Of course, this is only likely to be useful in certain esoteric template situations.
647 
648  E.g. "myFunction (typename TypeHelpers::ParameterType<int>::type, typename TypeHelpers::ParameterType<MyObject>::type)"
649  would evaluate to "myfunction (int, const MyObject&)", keeping any primitive types as
650  pass-by-value, but passing objects as a const reference, to avoid copying.
651 
652  @tags{Core}
653  */
654  template <typename Type> struct ParameterType { using type = const Type&; };
655 
656  #if ! DOXYGEN
657  template <typename Type> struct ParameterType <Type&> { using type = Type&; };
658  template <typename Type> struct ParameterType <Type*> { using type = Type*; };
659  template <> struct ParameterType <char> { using type = char; };
660  template <> struct ParameterType <unsigned char> { using type = unsigned char; };
661  template <> struct ParameterType <short> { using type = short; };
662  template <> struct ParameterType <unsigned short> { using type = unsigned short; };
663  template <> struct ParameterType <int> { using type = int; };
664  template <> struct ParameterType <unsigned int> { using type = unsigned int; };
665  template <> struct ParameterType <long> { using type = long; };
666  template <> struct ParameterType <unsigned long> { using type = unsigned long; };
667  template <> struct ParameterType <int64> { using type = int64; };
668  template <> struct ParameterType <uint64> { using type = uint64; };
669  template <> struct ParameterType <bool> { using type = bool; };
670  template <> struct ParameterType <float> { using type = float; };
671  template <> struct ParameterType <double> { using type = double; };
672  #endif
673 
674  /** These templates are designed to take a type, and if it's a double, they return a double
675  type; for anything else, they return a float type.
676 
677  @tags{Core}
678  */
679  template <typename Type> struct SmallestFloatType { using type = float; };
680 
681  #if ! DOXYGEN
682  template <> struct SmallestFloatType <double> { using type = double; };
683  #endif
684 
685  /** These templates are designed to take an integer type, and return an unsigned int
686  version with the same size.
687 
688  @tags{Core}
689  */
690  template <int bytes> struct UnsignedTypeWithSize {};
691 
692  #if ! DOXYGEN
693  template <> struct UnsignedTypeWithSize<1> { using type = uint8; };
694  template <> struct UnsignedTypeWithSize<2> { using type = uint16; };
695  template <> struct UnsignedTypeWithSize<4> { using type = uint32; };
696  template <> struct UnsignedTypeWithSize<8> { using type = uint64; };
697  #endif
698 }
699 
700 //==============================================================================
701 #if ! DOXYGEN
702  // These old functions are deprecated: Just use roundToInt instead.
703  JUCE_DEPRECATED_ATTRIBUTE inline int roundDoubleToInt (double value) noexcept { return roundToInt (value); }
704  JUCE_DEPRECATED_ATTRIBUTE inline int roundFloatToInt (float value) noexcept { return roundToInt (value); }
705 
706  // This old function isn't needed - just use std::abs() instead
707  JUCE_DEPRECATED_ATTRIBUTE inline int64 abs64 (int64 n) noexcept { return std::abs (n); }
708 #endif
709 
710 } // namespace juce
711 
712 /** @}*/
These templates are designed to take an integer type, and return an unsigned int version with the sam...
These templates are designed to take a type, and if it&#39;s a double, they return a double type; for any...
static const FloatType pi
A predefined value for Pi.
The ParameterType struct is used to find the best type to use when passing some kind of object as a p...
static const FloatType halfPi
A predefined value for Pi / 2.
static const FloatType euler
A predefined value for Euler&#39;s number.
static const FloatType sqrt2
A predefined value for sqrt(2)
static const FloatType twoPi
A predefined value for 2 * Pi.
Commonly used mathematical constants.