JUCE-7.0.12-0-g4f43011b96 JUCE-7.0.12-0-g4f43011b96
JUCE — C++ application framework with suport for VST, VST3, LV2 audio plug-ins

« « « Anklang Documentation
Loading...
Searching...
No Matches
juce_Interpolators.cpp
Go to the documentation of this file.
1 /*
2 ==============================================================================
3
4 This file is part of the JUCE library.
5 Copyright (c) 2022 - Raw Material Software Limited
6
7 JUCE is an open source library subject to commercial or open-source
8 licensing.
9
10 The code included in this file is provided under the terms of the ISC license
11 http://www.isc.org/downloads/software-support-policy/isc-license. Permission
12 To use, copy, modify, and/or distribute this software for any purpose with or
13 without fee is hereby granted provided that the above copyright notice and
14 this permission notice appear in all copies.
15
16 JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
17 EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
18 DISCLAIMED.
19
20 ==============================================================================
21*/
22
23namespace juce
24{
25
26#if JUCE_UNIT_TESTS
27
28class InterpolatorTests final : public UnitTest
29{
30public:
32 : UnitTest ("InterpolatorTests", UnitTestCategories::audio)
33 {
34 }
35
36private:
37 template <typename InterpolatorType>
38 void runInterplatorTests (const String& interpolatorName)
39 {
40 auto createGaussian = [] (std::vector<float>& destination, float scale, float centreInSamples, float width)
41 {
42 for (size_t i = 0; i < destination.size(); ++i)
43 {
44 auto x = (((float) i) - centreInSamples) * width;
45 destination[i] = std::exp (-(x * x));
46 }
47
48 FloatVectorOperations::multiply (destination.data(), scale, (int) destination.size());
49 };
50
51 auto findGaussianPeak = [] (const std::vector<float>& input) -> float
52 {
53 auto max = std::max_element (std::begin (input), std::end (input));
54 auto maxPrev = max - 1;
55 jassert (maxPrev >= std::begin (input));
56 auto maxNext = max + 1;
57 jassert (maxNext < std::end (input));
58 auto quadraticMaxLoc = (*maxPrev - *maxNext) / (2.0f * ((*maxNext + *maxPrev) - (2.0f * *max)));
59 return quadraticMaxLoc + (float) std::distance (std::begin (input), max);
60 };
61
62 auto expectAllElementsWithin = [this] (const std::vector<float>& v1, const std::vector<float>& v2, float tolerance)
63 {
64 expectEquals ((int) v1.size(), (int) v2.size());
65
66 for (size_t i = 0; i < v1.size(); ++i)
67 expectWithinAbsoluteError (v1[i], v2[i], tolerance);
68 };
69
70 InterpolatorType interpolator;
71
72 constexpr size_t inputSize = 1001;
73 static_assert (inputSize > 800 + InterpolatorType::getBaseLatency(),
74 "The test InterpolatorTests input buffer is too small");
75
77 constexpr auto inputGaussianMidpoint = (float) (inputSize - 1) / 2.0f;
78 constexpr auto inputGaussianValueAtEnds = 0.000001f;
80
82
83 for (auto speedRatio : { 0.4, 0.8263, 1.0, 1.05, 1.2384, 1.6 })
84 {
85 const auto expectedGaussianMidpoint = (inputGaussianMidpoint + InterpolatorType::getBaseLatency()) / (float) speedRatio;
87
88 const auto outputBufferSize = (size_t) std::floor ((float) input.size() / speedRatio);
89
90 for (int numBlocks : { 1, 5 })
91 {
92 const auto inputBlockSize = (float) input.size() / (float) numBlocks;
94
96
97 beginTest (interpolatorName + " process " + String (numBlocks) + " blocks ratio " + String (speedRatio));
98
99 interpolator.reset();
100
101 {
102 auto* inputPtr = input.data();
103 auto* outputPtr = output.data();
104
105 for (int i = 0; i < numBlocks; ++i)
106 {
107 auto numInputSamplesRead = interpolator.process (speedRatio, inputPtr, outputPtr, outputBlockSize);
110 }
111 }
112
113 expectWithinAbsoluteError (findGaussianPeak (output), expectedGaussianMidpoint, 0.1f);
114
115 std::vector<float> expectedOutput (output.size());
117
119
120 beginTest (interpolatorName + " process adding " + String (numBlocks) + " blocks ratio " + String (speedRatio));
121
122 interpolator.reset();
123
124 constexpr float addingGain = 0.7384f;
125
126 {
127 auto* inputPtr = input.data();
128 auto* outputPtr = output.data();
129
130 for (int i = 0; i < numBlocks; ++i)
131 {
132 auto numInputSamplesRead = interpolator.processAdding (speedRatio, inputPtr, outputPtr, outputBlockSize, addingGain);
135 }
136 }
137
138 expectWithinAbsoluteError (findGaussianPeak (output), expectedGaussianMidpoint, 0.1f);
139
140 std::vector<float> additionalOutput (output.size());
142 FloatVectorOperations::add (expectedOutput.data(), additionalOutput.data(), (int) additionalOutput.size());
143
145 }
146
147 beginTest (interpolatorName + " process wrap 0 ratio " + String (speedRatio));
148
150
151 interpolator.reset();
152 interpolator.process (speedRatio, input.data(), doubleLengthOutput.data(), (int) doubleLengthOutput.size(),
153 (int) input.size(), 0);
154
157
159
160 beginTest (interpolatorName + " process wrap double ratio " + String (speedRatio));
161
162 interpolator.reset();
163 interpolator.process (speedRatio, input.data(), doubleLengthOutput.data(), (int) doubleLengthOutput.size(),
164 (int) input.size(), (int) input.size());
165
168 FloatVectorOperations::add (expectedDoubleLengthOutput.data(), secondGaussian.data(), (int) expectedDoubleLengthOutput.size());
169
171 }
172 }
173
174public:
175 void runTest() override
176 {
177 runInterplatorTests<WindowedSincInterpolator> ("WindowedSincInterpolator");
178 runInterplatorTests<LagrangeInterpolator> ("LagrangeInterpolator");
179 runInterplatorTests<CatmullRomInterpolator> ("CatmullRomInterpolator");
180 runInterplatorTests<LinearInterpolator> ("LinearInterpolator");
181 }
182};
183
185
186#endif
187
188} // namespace juce
T begin(T... args)
T data(T... args)
T distance(T... args)
T end(T... args)
T exp(T... args)
T floor(T... args)
#define jassert(expression)
Platform-independent assertion macro.
typedef int
T log(T... args)
typedef float
T max_element(T... args)
T max(T... args)
JUCE Namespace.
Type unalignedPointerCast(void *ptr) noexcept
Casts a pointer to another type via void*, which suppresses the cast-align warning which sometimes ar...
Definition juce_Memory.h:88
T size(T... args)
T sqrt(T... args)
typedef size_t