1
0
Fork 0
mirror of https://github.com/juce-framework/JUCE.git synced 2026-01-10 23:44:24 +00:00

DSP: Improved some variable names and documentation

This commit is contained in:
Tom Poole 2019-02-13 10:07:54 +00:00
parent 10fc12da84
commit 77feb173b0
8 changed files with 265 additions and 195 deletions

View file

@ -42,18 +42,18 @@ typename FIR::Coefficients<FloatType>::Ptr
auto* result = new typename FIR::Coefficients<FloatType> (order + 1u);
auto* c = result->getRawCoefficients();
auto normalizedFrequency = frequency / sampleRate;
auto normalisedFrequency = frequency / sampleRate;
for (size_t i = 0; i <= order; ++i)
{
if (i == order * 0.5)
{
c[i] = static_cast<FloatType> (normalizedFrequency * 2);
c[i] = static_cast<FloatType> (normalisedFrequency * 2);
}
else
{
auto indice = MathConstants<double>::pi * (static_cast<double> (i) - 0.5 * static_cast<double> (order));
c[i] = static_cast<FloatType> (std::sin (2.0 * indice * normalizedFrequency) / indice);
c[i] = static_cast<FloatType> (std::sin (2.0 * indice * normalisedFrequency) / indice);
}
}
@ -66,23 +66,23 @@ typename FIR::Coefficients<FloatType>::Ptr
template <typename FloatType>
typename FIR::Coefficients<FloatType>::Ptr
FilterDesign<FloatType>::designFIRLowpassKaiserMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType attenuationdB)
FloatType normalisedTransitionWidth,
FloatType amplitudedB)
{
jassert (sampleRate > 0);
jassert (frequency > 0 && frequency <= sampleRate * 0.5);
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (attenuationdB >= -100 && attenuationdB <= 0);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (amplitudedB >= -100 && amplitudedB <= 0);
FloatType beta = 0;
if (attenuationdB < -50)
beta = static_cast<FloatType> (0.1102 * (-attenuationdB - 8.7));
else if (attenuationdB <= 21)
beta = static_cast<FloatType> (0.5842 * std::pow (-attenuationdB - 21, 0.4) + 0.07886 * (-attenuationdB - 21));
if (amplitudedB < -50)
beta = static_cast<FloatType> (0.1102 * (-amplitudedB - 8.7));
else if (amplitudedB <= 21)
beta = static_cast<FloatType> (0.5842 * std::pow (-amplitudedB - 21, 0.4) + 0.07886 * (-amplitudedB - 21));
int order = attenuationdB < -21 ? roundToInt (std::ceil ((-attenuationdB - 7.95) / (2.285 * normalizedTransitionWidth * MathConstants<double>::twoPi)))
: roundToInt (std::ceil (5.79 / (normalizedTransitionWidth * MathConstants<double>::twoPi)));
int order = amplitudedB < -21 ? roundToInt (std::ceil ((-amplitudedB - 7.95) / (2.285 * normalisedTransitionWidth * MathConstants<double>::twoPi)))
: roundToInt (std::ceil (5.79 / (normalisedTransitionWidth * MathConstants<double>::twoPi)));
jassert (order >= 0);
@ -94,14 +94,14 @@ typename FIR::Coefficients<FloatType>::Ptr
template <typename FloatType>
typename FIR::Coefficients<FloatType>::Ptr
FilterDesign<FloatType>::designFIRLowpassTransitionMethod (FloatType frequency, double sampleRate, size_t order,
FloatType normalizedTransitionWidth, FloatType spline)
FloatType normalisedTransitionWidth, FloatType spline)
{
jassert (sampleRate > 0);
jassert (frequency > 0 && frequency <= sampleRate * 0.5);
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (spline >= 1.0 && spline <= 4.0);
auto normalizedFrequency = frequency / static_cast<FloatType> (sampleRate);
auto normalisedFrequency = frequency / static_cast<FloatType> (sampleRate);
auto* result = new typename FIR::Coefficients<FloatType> (order + 1u);
auto* c = result->getRawCoefficients();
@ -110,13 +110,13 @@ typename FIR::Coefficients<FloatType>::Ptr
{
if (i == order / 2 && order % 2 == 0)
{
c[i] = static_cast<FloatType> (2 * normalizedFrequency);
c[i] = static_cast<FloatType> (2 * normalisedFrequency);
}
else
{
auto indice = MathConstants<double>::pi * (i - 0.5 * order);
auto indice2 = MathConstants<double>::pi * normalizedTransitionWidth * (i - 0.5 * order) / spline;
c[i] = static_cast<FloatType> (std::sin (2 * indice * normalizedFrequency)
auto indice2 = MathConstants<double>::pi * normalisedTransitionWidth * (i - 0.5 * order) / spline;
c[i] = static_cast<FloatType> (std::sin (2 * indice * normalisedFrequency)
/ indice * std::pow (std::sin (indice2) / indice2, spline));
}
}
@ -128,18 +128,18 @@ template <typename FloatType>
typename FIR::Coefficients<FloatType>::Ptr
FilterDesign<FloatType>::designFIRLowpassLeastSquaresMethod (FloatType frequency,
double sampleRate, size_t order,
FloatType normalizedTransitionWidth,
FloatType normalisedTransitionWidth,
FloatType stopBandWeight)
{
jassert (sampleRate > 0);
jassert (frequency > 0 && frequency <= sampleRate * 0.5);
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (stopBandWeight >= 1.0 && stopBandWeight <= 100.0);
auto normalizedFrequency = static_cast<double> (frequency) / sampleRate;
auto normalisedFrequency = static_cast<double> (frequency) / sampleRate;
auto wp = MathConstants<double>::twoPi * (static_cast<double> (normalizedFrequency - normalizedTransitionWidth / 2.0));
auto ws = MathConstants<double>::twoPi * (static_cast<double> (normalizedFrequency + normalizedTransitionWidth / 2.0));
auto wp = MathConstants<double>::twoPi * (static_cast<double> (normalisedFrequency - normalisedTransitionWidth / 2.0));
auto ws = MathConstants<double>::twoPi * (static_cast<double> (normalisedFrequency + normalisedTransitionWidth / 2.0));
auto N = order + 1;
@ -236,15 +236,15 @@ typename FIR::Coefficients<FloatType>::Ptr
template <typename FloatType>
typename FIR::Coefficients<FloatType>::Ptr
FilterDesign<FloatType>::designFIRLowpassHalfBandEquirippleMethod (FloatType normalizedTransitionWidth,
FloatType attenuationdB)
FilterDesign<FloatType>::designFIRLowpassHalfBandEquirippleMethod (FloatType normalisedTransitionWidth,
FloatType amplitudedB)
{
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (attenuationdB >= -300 && attenuationdB <= -10);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (amplitudedB >= -300 && amplitudedB <= -10);
auto wpT = (0.5 - normalizedTransitionWidth) * MathConstants<double>::pi;
auto wpT = (0.5 - normalisedTransitionWidth) * MathConstants<double>::pi;
auto n = roundToInt (std::ceil ((attenuationdB - 18.18840664 * wpT + 33.64775300) / (18.54155181 * wpT - 29.13196871)));
auto n = roundToInt (std::ceil ((amplitudedB - 18.18840664 * wpT + 33.64775300) / (18.54155181 * wpT - 29.13196871)));
auto kp = (n * wpT - 1.57111377 * n + 0.00665857) / (-1.01927560 * n + 0.37221484);
auto A = (0.01525753 * n + 0.03682344 + 9.24760314 / (double) n) * kp + 1.01701407 + 0.73512298 / (double) n;
auto B = (0.00233667 * n - 1.35418408 + 5.75145813 / (double) n) * kp + 1.02999650 - 0.72759508 / (double) n;
@ -339,67 +339,67 @@ Array<double> FilterDesign<FloatType>::getPartialImpulseResponseHn (int n, doubl
template <typename FloatType>
ReferenceCountedArray<IIR::Coefficients<FloatType>>
FilterDesign<FloatType>::designIIRLowpassHighOrderButterworthMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB)
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB)
{
return designIIRLowpassHighOrderGeneralMethod (0, frequency, sampleRate, normalizedTransitionWidth,
passbandAttenuationdB, stopbandAttenuationdB);
return designIIRLowpassHighOrderGeneralMethod (0, frequency, sampleRate, normalisedTransitionWidth,
passbandAmplitudedB, stopbandAmplitudedB);
}
template <typename FloatType>
ReferenceCountedArray<IIR::Coefficients<FloatType>>
FilterDesign<FloatType>::designIIRLowpassHighOrderChebyshev1Method (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB)
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB)
{
return designIIRLowpassHighOrderGeneralMethod (1, frequency, sampleRate, normalizedTransitionWidth,
passbandAttenuationdB, stopbandAttenuationdB);
return designIIRLowpassHighOrderGeneralMethod (1, frequency, sampleRate, normalisedTransitionWidth,
passbandAmplitudedB, stopbandAmplitudedB);
}
template <typename FloatType>
ReferenceCountedArray<IIR::Coefficients<FloatType>>
FilterDesign<FloatType>::designIIRLowpassHighOrderChebyshev2Method (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB)
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB)
{
return designIIRLowpassHighOrderGeneralMethod (2, frequency, sampleRate, normalizedTransitionWidth,
passbandAttenuationdB, stopbandAttenuationdB);
return designIIRLowpassHighOrderGeneralMethod (2, frequency, sampleRate, normalisedTransitionWidth,
passbandAmplitudedB, stopbandAmplitudedB);
}
template <typename FloatType>
ReferenceCountedArray<IIR::Coefficients<FloatType>>
FilterDesign<FloatType>::designIIRLowpassHighOrderEllipticMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB)
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB)
{
return designIIRLowpassHighOrderGeneralMethod (3, frequency, sampleRate, normalizedTransitionWidth,
passbandAttenuationdB, stopbandAttenuationdB);
return designIIRLowpassHighOrderGeneralMethod (3, frequency, sampleRate, normalisedTransitionWidth,
passbandAmplitudedB, stopbandAmplitudedB);
}
template <typename FloatType>
ReferenceCountedArray<IIR::Coefficients<FloatType>>
FilterDesign<FloatType>::designIIRLowpassHighOrderGeneralMethod (int type, FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB)
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB)
{
jassert (sampleRate > 0);
jassert (frequency > 0 && frequency <= sampleRate * 0.5);
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (passbandAttenuationdB > -20 && passbandAttenuationdB < 0);
jassert (stopbandAttenuationdB > -300 && stopbandAttenuationdB < -20);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (passbandAmplitudedB > -20 && passbandAmplitudedB < 0);
jassert (stopbandAmplitudedB > -300 && stopbandAmplitudedB < -20);
auto normalizedFrequency = frequency / sampleRate;
auto normalisedFrequency = frequency / sampleRate;
auto fp = normalizedFrequency - normalizedTransitionWidth / 2;
auto fs = normalizedFrequency + normalizedTransitionWidth / 2;
auto fp = normalisedFrequency - normalisedTransitionWidth / 2;
auto fs = normalisedFrequency + normalisedTransitionWidth / 2;
double Ap = passbandAttenuationdB;
double As = stopbandAttenuationdB;
double Ap = passbandAmplitudedB;
double As = stopbandAmplitudedB;
auto Gp = Decibels::decibelsToGain (Ap, -300.0);
auto Gs = Decibels::decibelsToGain (As, -300.0);
auto epsp = std::sqrt (1.0 / (Gp * Gp) - 1.0);
@ -610,14 +610,14 @@ ReferenceCountedArray<IIR::Coefficients<FloatType>>
template <typename FloatType>
typename FilterDesign<FloatType>::IIRPolyphaseAllpassStructure
FilterDesign<FloatType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (FloatType normalizedTransitionWidth,
FloatType stopbandAttenuationdB)
FilterDesign<FloatType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (FloatType normalisedTransitionWidth,
FloatType stopbandAmplitudedB)
{
jassert (normalizedTransitionWidth > 0 && normalizedTransitionWidth <= 0.5);
jassert (stopbandAttenuationdB > -300 && stopbandAttenuationdB < -10);
jassert (normalisedTransitionWidth > 0 && normalisedTransitionWidth <= 0.5);
jassert (stopbandAmplitudedB > -300 && stopbandAmplitudedB < -10);
const double wt = MathConstants<double>::twoPi * normalizedTransitionWidth;
const double ds = Decibels::decibelsToGain (stopbandAttenuationdB, static_cast<FloatType> (-300.0));
const double wt = MathConstants<double>::twoPi * normalisedTransitionWidth;
const double ds = Decibels::decibelsToGain (stopbandAmplitudedB, static_cast<FloatType> (-300.0));
auto k = std::pow (std::tan ((MathConstants<double>::pi - wt) / 4), 2.0);
auto kp = std::sqrt (1.0 - k * k);

View file

@ -56,7 +56,7 @@ struct FilterDesign
It generates linear phase filters coefficients.
Note: The flatTop WindowingMethod generates an impulse response with a
maximum amplitude higher than one, and might be normalized if necessary
maximum amplitude higher than one, and might be normalised if necessary
depending on the applications.
@param frequency the cutoff frequency of the low-pass filter
@ -71,7 +71,7 @@ struct FilterDesign
FloatType beta = static_cast<FloatType> (2));
/** This a variant of the function designFIRLowpassWindowMethod, which allows the
user to specify a transition width and an attenuation in dB,
user to specify a transition width and a negative gain in dB,
to get a low-pass filter using the Kaiser windowing function, with calculated
values of the filter order and of the beta parameter, to satisfy the constraints.
@ -79,14 +79,14 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param attenuationdB the attenuation in dB expected in the stop band
@param amplitudedB the maximum amplitude in dB expected in the stop band (must be negative)
*/
static FIRCoefficientsPtr designFIRLowpassKaiserMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType attenuationdB);
FloatType normalisedTransitionWidth,
FloatType amplitudedB);
/** This method is also a variant of the function designFIRLowpassWindowMethod, using
@ -98,14 +98,14 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param order the order of the filter
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param spline between 1.0 and 4.0, indicates how much the transition
is curved, with 1.0 meaning a straight line
*/
static FIRCoefficientsPtr designFIRLowpassTransitionMethod (FloatType frequency, double sampleRate,
size_t order,
FloatType normalizedTransitionWidth,
FloatType normalisedTransitionWidth,
FloatType spline);
/** This method generates a FIR::Coefficients for a low-pass filter, by
@ -117,14 +117,14 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param order the order of the filter
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param stopBandWeight between 1.0 and 100.0, indicates how much we want
attenuation in the stop band, against some oscillation
in the pass band
*/
static FIRCoefficientsPtr designFIRLowpassLeastSquaresMethod (FloatType frequency, double sampleRate, size_t order,
FloatType normalizedTransitionWidth,
FloatType normalisedTransitionWidth,
FloatType stopBandWeight);
/** This method generates a FIR::Coefficients for a low-pass filter, with
@ -135,12 +135,12 @@ struct FilterDesign
It generates linear phase filters coefficients.
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param attenuationdB the attenuation in dB expected in the stop band
@param amplitudedB the maximum amplitude in dB expected in the stop band (must be negative)
*/
static FIRCoefficientsPtr designFIRLowpassHalfBandEquirippleMethod (FloatType normalizedTransitionWidth,
FloatType attenuationdB);
static FIRCoefficientsPtr designFIRLowpassHalfBandEquirippleMethod (FloatType normalisedTransitionWidth,
FloatType amplitudedB);
//==============================================================================
/** This method returns an array of IIR::Coefficients, made to be used in
@ -152,16 +152,16 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param passbandAttenuationdB the lowest attenuation in dB expected in the pass band
@param stopbandAttenuationdB the attenuation in dB expected in the stop band
@param passbandAmplitudedB the highest gain in dB expected in the pass band (must be negative)
@param stopbandAmplitudedB the gain in dB expected in the stop band (must be negative)
*/
static ReferenceCountedArray<IIRCoefficients> designIIRLowpassHighOrderButterworthMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB);
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB);
//==============================================================================
/** This method returns an array of IIR::Coefficients, made to be used in
@ -199,15 +199,15 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param passbandAttenuationdB the lowest attenuation in dB expected in the pass band
@param stopbandAttenuationdB the attenuation in dB expected in the stop band
@param passbandAmplitudedB the highest amplitude in dB expected in the pass band (must be negative)
@param stopbandAmplitudedB the lowest amplitude in dB expected in the stop band (must be negative)
*/
static ReferenceCountedArray<IIRCoefficients> designIIRLowpassHighOrderChebyshev1Method (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB);
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB);
/** This method returns an array of IIR::Coefficients, made to be used in
cascaded IIRFilters, providing a minimum phase low-pass filter without any
@ -218,15 +218,15 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param passbandAttenuationdB the lowest attenuation in dB expected in the pass band
@param stopbandAttenuationdB the attenuation in dB expected in the stop band
@param passbandAmplitudedB the highest amplitude in dB expected in the pass band (must be negative)
@param stopbandAmplitudedB the lowest amplitude in dB expected in the stop band (must be negative)
*/
static ReferenceCountedArray<IIRCoefficients> designIIRLowpassHighOrderChebyshev2Method (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB);
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB);
/** This method returns an array of IIR::Coefficients, made to be used in
cascaded IIR::Filters, providing a minimum phase low-pass filter with ripples
@ -237,15 +237,15 @@ struct FilterDesign
@param frequency the cutoff frequency of the low-pass filter
@param sampleRate the sample rate being used in the filter design
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param passbandAttenuationdB the lowest attenuation in dB expected in the pass band
@param stopbandAttenuationdB the attenuation in dB expected in the stop band
@param passbandAmplitudedB the highest amplitude in dB expected in the pass band (must be negative)
@param stopbandAmplitudedB the lowest amplitude in dB expected in the stop band (must be negative)
*/
static ReferenceCountedArray<IIRCoefficients> designIIRLowpassHighOrderEllipticMethod (FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB);
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB);
/** The structure returned by the function designIIRLowpassHalfBandPolyphaseAllpassMethod.
@ -278,21 +278,21 @@ struct FilterDesign
The gain of the resulting pass-band is 6 dB, so don't forget to compensate it if you
want to use that method for something else than two times oversampling.
@param normalizedTransitionWidth the normalized size between 0 and 0.5 of the transition
@param normalisedTransitionWidth the normalised size between 0 and 0.5 of the transition
between the pass band and the stop band
@param stopbandAttenuationdB the attenuation in dB expected in the stop band
@param stopbandAmplitudedB the maximum amplitude in dB expected in the stop band (must be negative)
*/
static IIRPolyphaseAllpassStructure designIIRLowpassHalfBandPolyphaseAllpassMethod (FloatType normalizedTransitionWidth,
FloatType stopbandAttenuationdB);
static IIRPolyphaseAllpassStructure designIIRLowpassHalfBandPolyphaseAllpassMethod (FloatType normalisedTransitionWidth,
FloatType stopbandAmplitudedB);
private:
//==============================================================================
static Array<double> getPartialImpulseResponseHn (int n, double kp);
static ReferenceCountedArray<IIRCoefficients> designIIRLowpassHighOrderGeneralMethod (int type, FloatType frequency, double sampleRate,
FloatType normalizedTransitionWidth,
FloatType passbandAttenuationdB,
FloatType stopbandAttenuationdB);
FloatType normalisedTransitionWidth,
FloatType passbandAmplitudedB,
FloatType stopbandAmplitudedB);
FilterDesign() = delete;
};

View file

@ -61,7 +61,7 @@ struct ConvolutionEngine
bool wantsStereo = true;
bool wantsTrimming = true;
bool wantsNormalization = true;
bool wantsNormalisation = true;
int64 wantedSize = 0;
int finalSize = 0;
@ -345,7 +345,7 @@ struct Convolution::Pimpl : private Thread
changeImpulseResponseSize,
changeStereo,
changeTrimming,
changeNormalization,
changeNormalisation,
changeIgnore,
numChangeRequestTypes
};
@ -437,7 +437,7 @@ struct Convolution::Pimpl : private Thread
abstractFifo.finishedWrite (size1 + size2);
}
/** Reads requests from the fifo */
/** Reads requests from the fifo. */
void readFromFifo (ChangeRequest& type, juce::var& parameter)
{
int start1, size1, start2, size2;
@ -458,7 +458,7 @@ struct Convolution::Pimpl : private Thread
abstractFifo.finishedRead (size1 + size2);
}
/** Returns the number of requests that still need to be processed */
/** Returns the number of requests that still need to be processed. */
int getNumRemainingEntries() const noexcept
{
return abstractFifo.getNumReady();
@ -624,14 +624,14 @@ struct Convolution::Pimpl : private Thread
}
break;
case ChangeRequest::changeNormalization:
case ChangeRequest::changeNormalisation:
{
bool newWantsNormalization = requestsParameter[n];
bool newWantsNormalisation = requestsParameter[n];
if (currentInfo.wantsNormalization != newWantsNormalization)
if (currentInfo.wantsNormalisation != newWantsNormalisation)
changeLevel = jmax (1, changeLevel);
currentInfo.wantsNormalization = newWantsNormalization;
currentInfo.wantsNormalisation = newWantsNormalisation;
}
break;
@ -814,16 +814,16 @@ private:
if (isThreadRunning() && threadShouldExit())
return;
if (currentInfo.wantsNormalization)
if (currentInfo.wantsNormalisation)
{
if (currentInfo.originalNumChannels > 1)
{
normalizeImpulseResponse (currentInfo.buffer->getWritePointer (0), (int) currentInfo.finalSize, 1.0);
normalizeImpulseResponse (currentInfo.buffer->getWritePointer (1), (int) currentInfo.finalSize, 1.0);
normaliseImpulseResponse (currentInfo.buffer->getWritePointer (0), (int) currentInfo.finalSize, 1.0);
normaliseImpulseResponse (currentInfo.buffer->getWritePointer (1), (int) currentInfo.finalSize, 1.0);
}
else
{
normalizeImpulseResponse (currentInfo.buffer->getWritePointer (0), (int) currentInfo.finalSize, 1.0);
normaliseImpulseResponse (currentInfo.buffer->getWritePointer (0), (int) currentInfo.finalSize, 1.0);
}
}
@ -951,8 +951,8 @@ private:
impulseResponse.copyFrom (1, 0, impulseResponse, 0, 0, (int) currentInfo.finalSize);
}
/** Normalization of the impulse response based on its energy. */
void normalizeImpulseResponse (float* samples, int numSamples, double factorResampling) const
/** Normalisation of the impulse response based on its energy. */
void normaliseImpulseResponse (float* samples, int numSamples, double factorResampling) const
{
auto magnitude = 0.0f;
@ -1028,7 +1028,7 @@ private:
SpinLock processLock; // a necessary lock to use with this temporary buffer
AudioBuffer<float> impulseResponseOriginal; // a buffer with the original impulse response
AudioBuffer<float> impulseResponse; // a buffer with the impulse response trimmed, resampled, resized and normalized
AudioBuffer<float> impulseResponse; // a buffer with the impulse response trimmed, resampled, resized and normalised
//==============================================================================
OwnedArray<ConvolutionEngine> engines; // the 4 convolution engines being used
@ -1056,7 +1056,7 @@ Convolution::~Convolution()
void Convolution::loadImpulseResponse (const void* sourceData, size_t sourceDataSize,
bool wantsStereo, bool wantsTrimming, size_t size,
bool wantsNormalization)
bool wantsNormalisation)
{
if (sourceData == nullptr)
return;
@ -1068,7 +1068,7 @@ void Convolution::loadImpulseResponse (const void* sourceData, size_t sourceData
Pimpl::ChangeRequest::changeImpulseResponseSize,
Pimpl::ChangeRequest::changeStereo,
Pimpl::ChangeRequest::changeTrimming,
Pimpl::ChangeRequest::changeNormalization };
Pimpl::ChangeRequest::changeNormalisation };
Array<juce::var> sourceParameter;
@ -1079,13 +1079,13 @@ void Convolution::loadImpulseResponse (const void* sourceData, size_t sourceData
juce::var (static_cast<int64> (wantedSize)),
juce::var (wantsStereo),
juce::var (wantsTrimming),
juce::var (wantsNormalization) };
juce::var (wantsNormalisation) };
pimpl->addToFifo (types, parameters, 5);
}
void Convolution::loadImpulseResponse (const File& fileImpulseResponse, bool wantsStereo,
bool wantsTrimming, size_t size, bool wantsNormalization)
bool wantsTrimming, size_t size, bool wantsNormalisation)
{
if (! fileImpulseResponse.existsAsFile())
return;
@ -1097,7 +1097,7 @@ void Convolution::loadImpulseResponse (const File& fileImpulseResponse, bool wan
Pimpl::ChangeRequest::changeImpulseResponseSize,
Pimpl::ChangeRequest::changeStereo,
Pimpl::ChangeRequest::changeTrimming,
Pimpl::ChangeRequest::changeNormalization };
Pimpl::ChangeRequest::changeNormalisation };
Array<juce::var> sourceParameter;
@ -1108,20 +1108,20 @@ void Convolution::loadImpulseResponse (const File& fileImpulseResponse, bool wan
juce::var (static_cast<int64> (wantedSize)),
juce::var (wantsStereo),
juce::var (wantsTrimming),
juce::var (wantsNormalization) };
juce::var (wantsNormalisation) };
pimpl->addToFifo (types, parameters, 5);
}
void Convolution::copyAndLoadImpulseResponseFromBuffer (AudioBuffer<float>& buffer,
double bufferSampleRate, bool wantsStereo, bool wantsTrimming, bool wantsNormalization, size_t size)
double bufferSampleRate, bool wantsStereo, bool wantsTrimming, bool wantsNormalisation, size_t size)
{
copyAndLoadImpulseResponseFromBlock (AudioBlock<float> (buffer), bufferSampleRate,
wantsStereo, wantsTrimming, wantsNormalization, size);
wantsStereo, wantsTrimming, wantsNormalisation, size);
}
void Convolution::copyAndLoadImpulseResponseFromBlock (AudioBlock<float> block, double bufferSampleRate,
bool wantsStereo, bool wantsTrimming, bool wantsNormalization, size_t size)
bool wantsStereo, bool wantsTrimming, bool wantsNormalisation, size_t size)
{
jassert (bufferSampleRate > 0);
@ -1137,7 +1137,7 @@ void Convolution::copyAndLoadImpulseResponseFromBlock (AudioBlock<float> block,
Pimpl::ChangeRequest::changeImpulseResponseSize,
Pimpl::ChangeRequest::changeStereo,
Pimpl::ChangeRequest::changeTrimming,
Pimpl::ChangeRequest::changeNormalization };
Pimpl::ChangeRequest::changeNormalisation };
Array<juce::var> sourceParameter;
sourceParameter.add (juce::var ((int) ConvolutionEngine::ProcessingInformation::SourceType::sourceAudioBuffer));
@ -1147,7 +1147,7 @@ void Convolution::copyAndLoadImpulseResponseFromBlock (AudioBlock<float> block,
juce::var (static_cast<int64> (wantedSize)),
juce::var (wantsStereo),
juce::var (wantsTrimming),
juce::var (wantsNormalization) };
juce::var (wantsNormalisation) };
pimpl->addToFifo (types, parameters, 5);
}

View file

@ -96,11 +96,11 @@ public:
@param wantsTrimming requests to trim the start and the end of the impulse response
@param size the expected size for the impulse response after loading, can be
set to 0 for requesting maximum original impulse response size
@param wantsNormalization requests to normalize the impulse response amplitude
@param wantsNormalisation requests to normalise the impulse response amplitude
*/
void loadImpulseResponse (const void* sourceData, size_t sourceDataSize,
bool wantsStereo, bool wantsTrimming, size_t size,
bool wantsNormalization = true);
bool wantsNormalisation = true);
/** This function loads an impulse response from an audio file on any drive. It
can load any of the audio formats registered in JUCE, and performs some
@ -111,11 +111,11 @@ public:
@param wantsTrimming requests to trim the start and the end of the impulse response
@param size the expected size for the impulse response after loading, can be
set to 0 for requesting maximum original impulse response size
@param wantsNormalization requests to normalize the impulse response amplitude
@param wantsNormalisation requests to normalise the impulse response amplitude
*/
void loadImpulseResponse (const File& fileImpulseResponse,
bool wantsStereo, bool wantsTrimming, size_t size,
bool wantsNormalization = true);
bool wantsNormalisation = true);
/** This function loads an impulse response from an audio buffer, which is
copied before doing anything else. Performs some resampling and
@ -125,12 +125,12 @@ public:
@param bufferSampleRate the sampleRate of the data in the AudioBuffer
@param wantsStereo requests to process both stereo channels or only one mono channel
@param wantsTrimming requests to trim the start and the end of the impulse response
@param wantsNormalization requests to normalize the impulse response amplitude
@param wantsNormalisation requests to normalise the impulse response amplitude
@param size the expected size for the impulse response after loading, can be
set to 0 for requesting maximum original impulse response size
*/
void copyAndLoadImpulseResponseFromBuffer (AudioBuffer<float>& buffer, double bufferSampleRate,
bool wantsStereo, bool wantsTrimming, bool wantsNormalization,
bool wantsStereo, bool wantsTrimming, bool wantsNormalisation,
size_t size);
/** This function loads an impulse response from an audio block, which is
@ -141,12 +141,12 @@ public:
@param bufferSampleRate the sampleRate of the data in the AudioBuffer
@param wantsStereo requests to process both stereo channels or only one channel
@param wantsTrimming requests to trim the start and the end of the impulse response
@param wantsNormalization requests to normalize the impulse response amplitude
@param wantsNormalisation requests to normalise the impulse response amplitude
@param size the expected size for the impulse response after loading,
-1 for maximum length
*/
void copyAndLoadImpulseResponseFromBlock (AudioBlock<float> block, double bufferSampleRate,
bool wantsStereo, bool wantsTrimming, bool wantsNormalization,
bool wantsStereo, bool wantsTrimming, bool wantsNormalisation,
size_t size);

View file

@ -37,22 +37,22 @@ static inline FloatType ncos (size_t order, size_t i, size_t size) noexcept
}
template <typename FloatType>
WindowingFunction<FloatType>::WindowingFunction (size_t size, WindowingMethod type, bool normalize, FloatType beta)
WindowingFunction<FloatType>::WindowingFunction (size_t size, WindowingMethod type, bool normalise, FloatType beta)
{
fillWindowingTables (size, type, normalize, beta);
fillWindowingTables (size, type, normalise, beta);
}
template <typename FloatType>
void WindowingFunction<FloatType>::fillWindowingTables (size_t size, WindowingMethod type,
bool normalize, FloatType beta) noexcept
bool normalise, FloatType beta) noexcept
{
windowTable.resize (static_cast<int> (size));
fillWindowingTables (windowTable.getRawDataPointer(), size, type, normalize, beta);
fillWindowingTables (windowTable.getRawDataPointer(), size, type, normalise, beta);
}
template <typename FloatType>
void WindowingFunction<FloatType>::fillWindowingTables (FloatType* samples, size_t size,
WindowingMethod type, bool normalize,
WindowingMethod type, bool normalise,
FloatType beta) noexcept
{
switch (type)
@ -151,7 +151,7 @@ void WindowingFunction<FloatType>::fillWindowingTables (FloatType* samples, size
}
// DC frequency amplitude must be one
if (normalize)
if (normalise)
{
FloatType sum (0);
@ -181,14 +181,14 @@ const char* WindowingFunction<FloatType>::getWindowingMethodName (WindowingMetho
case hamming: return "Hamming";
case blackman: return "Blackman";
case blackmanHarris: return "Blackman-Harris";
case flatTop: return "FlatTop";
case flatTop: return "Flat Top";
case kaiser: return "Kaiser";
default: jassertfalse; return "";
}
}
template struct WindowingFunction<float>;
template struct WindowingFunction<double>;
template class WindowingFunction<float>;
template class WindowingFunction<double>;
} // namespace dsp
} // namespace juce

View file

@ -31,13 +31,20 @@ namespace dsp
/**
A class which provides multiple windowing functions useful for filter design
and spectrum analyzers
and spectrum analyzers.
The different functions provided here can be used by creating either a
WindowingFunction object, or a static function to fill an array with the
windowing method samples.
@tags{DSP}
*/
template <typename FloatType>
struct WindowingFunction
class JUCE_API WindowingFunction
{
public:
//==============================================================================
/** The windowing methods available. */
enum WindowingMethod
{
rectangular = 0,
@ -52,22 +59,46 @@ struct WindowingFunction
};
//==============================================================================
/** This constructor automatically fills a buffer of the specified size using
the fillWindowingTables function and the specified arguments.
@see fillWindowingTables
*/
WindowingFunction (size_t size, WindowingMethod,
bool normalize = true, FloatType beta = 0);
bool normalise = true, FloatType beta = 0);
//==============================================================================
/** Fills the content of an array with a given windowing method table */
/** Fills the content of the object array with a given windowing method table.
@param size the size of the destination buffer allocated in the object
@param type the type of windowing method being used
@param normalise if the result must be normalised, creating a DC amplitude
response of one
@param beta an optional argument useful only for Kaiser's method
which must be positive and sets the properties of the
method (bandwidth and attenuation increases with beta)
*/
void fillWindowingTables (size_t size, WindowingMethod type,
bool normalize = true, FloatType beta = 0) noexcept;
bool normalise = true, FloatType beta = 0) noexcept;
/** Fills the content of an array with a given windowing method table */
/** Fills the content of an array with a given windowing method table.
@param samples the destination buffer pointer
@param size the size of the destination buffer allocated in the object
@param type the type of windowing method being used
@param normalise if the result must be normalised, creating a DC amplitude
response of one
@param beta an optional argument useful only for Kaiser's method,
which must be positive and sets the properties of the
method (bandwidth and attenuation increases with beta)
*/
static void fillWindowingTables (FloatType* samples, size_t size, WindowingMethod,
bool normalize = true, FloatType beta = 0) noexcept;
bool normalise = true, FloatType beta = 0) noexcept;
/** Multiply the content of a buffer with the given window */
/** Multiplies the content of a buffer with the given window. */
void multiplyWithWindowingTable (FloatType* samples, size_t size) noexcept;
/** Returns the name of a given windowing method */
/** Returns the name of a given windowing method. */
static const char* getWindowingMethodName (WindowingMethod) noexcept;

View file

@ -116,14 +116,14 @@ struct Oversampling2TimesEquirippleFIR : public Oversampling<SampleType>::Overs
using ParentType = typename Oversampling<SampleType>::OversamplingStage;
Oversampling2TimesEquirippleFIR (size_t numChans,
SampleType normalizedTransitionWidthUp,
SampleType stopbandAttenuationdBUp,
SampleType normalizedTransitionWidthDown,
SampleType stopbandAttenuationdBDown)
SampleType normalisedTransitionWidthUp,
SampleType stopbandAmplitudedBUp,
SampleType normalisedTransitionWidthDown,
SampleType stopbandAmplitudedBDown)
: ParentType (numChans, 2)
{
coefficientsUp = *dsp::FilterDesign<SampleType>::designFIRLowpassHalfBandEquirippleMethod (normalizedTransitionWidthUp, stopbandAttenuationdBUp);
coefficientsDown = *dsp::FilterDesign<SampleType>::designFIRLowpassHalfBandEquirippleMethod (normalizedTransitionWidthDown, stopbandAttenuationdBDown);
coefficientsUp = *dsp::FilterDesign<SampleType>::designFIRLowpassHalfBandEquirippleMethod (normalisedTransitionWidthUp, stopbandAmplitudedBUp);
coefficientsDown = *dsp::FilterDesign<SampleType>::designFIRLowpassHalfBandEquirippleMethod (normalisedTransitionWidthDown, stopbandAmplitudedBDown);
auto N = coefficientsUp.getFilterOrder() + 1;
stateUp.setSize (static_cast<int> (this->numChannels), static_cast<int> (N));
@ -268,17 +268,17 @@ struct Oversampling2TimesPolyphaseIIR : public Oversampling<SampleType>::Oversa
using ParentType = typename Oversampling<SampleType>::OversamplingStage;
Oversampling2TimesPolyphaseIIR (size_t numChans,
SampleType normalizedTransitionWidthUp,
SampleType stopbandAttenuationdBUp,
SampleType normalizedTransitionWidthDown,
SampleType stopbandAttenuationdBDown)
SampleType normalisedTransitionWidthUp,
SampleType stopbandAmplitudedBUp,
SampleType normalisedTransitionWidthDown,
SampleType stopbandAmplitudedBDown)
: ParentType (numChans, 2)
{
auto structureUp = dsp::FilterDesign<SampleType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (normalizedTransitionWidthUp, stopbandAttenuationdBUp);
auto structureUp = dsp::FilterDesign<SampleType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (normalisedTransitionWidthUp, stopbandAmplitudedBUp);
auto coeffsUp = getCoefficients (structureUp);
latency = static_cast<SampleType> (-(coeffsUp.getPhaseForFrequency (0.0001, 1.0)) / (0.0001 * MathConstants<double>::twoPi));
auto structureDown = dsp::FilterDesign<SampleType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (normalizedTransitionWidthDown, stopbandAttenuationdBDown);
auto structureDown = dsp::FilterDesign<SampleType>::designIIRLowpassHalfBandPolyphaseAllpassMethod (normalisedTransitionWidthDown, stopbandAmplitudedBDown);
auto coeffsDown = getCoefficients (structureDown);
latency += static_cast<SampleType> (-(coeffsDown.getPhaseForFrequency (0.0001, 1.0)) / (0.0001 * MathConstants<double>::twoPi));
@ -599,22 +599,22 @@ void Oversampling<SampleType>::addDummyOversamplingStage()
template <typename SampleType>
void Oversampling<SampleType>::addOversamplingStage (FilterType type,
float normalizedTransitionWidthUp,
float stopbandAttenuationdBUp,
float normalizedTransitionWidthDown,
float stopbandAttenuationdBDown)
float normalisedTransitionWidthUp,
float stopbandAmplitudedBUp,
float normalisedTransitionWidthDown,
float stopbandAmplitudedBDown)
{
if (type == FilterType::filterHalfBandPolyphaseIIR)
{
stages.add (new Oversampling2TimesPolyphaseIIR<SampleType> (numChannels,
normalizedTransitionWidthUp, stopbandAttenuationdBUp,
normalizedTransitionWidthDown, stopbandAttenuationdBDown));
normalisedTransitionWidthUp, stopbandAmplitudedBUp,
normalisedTransitionWidthDown, stopbandAmplitudedBDown));
}
else
{
stages.add (new Oversampling2TimesEquirippleFIR<SampleType> (numChannels,
normalizedTransitionWidthUp, stopbandAttenuationdBUp,
normalizedTransitionWidthDown, stopbandAttenuationdBDown));
normalisedTransitionWidthUp, stopbandAmplitudedBUp,
normalisedTransitionWidthDown, stopbandAmplitudedBDown));
}
factorOversampling *= 2;

View file

@ -40,14 +40,14 @@ namespace dsp
The principle of oversampling is to increase the sample rate of a given
non-linear process, to prevent it from creating aliasing. Oversampling works
by upsampling N times the input signal, processing the upsampling signal
with the increased internal sample rate, and downsample the result to get
by upsampling N times the input signal, processing the upsampled signal
with the increased internal sample rate, and downsampling the result to get
back the original processing sample rate.
Choose between FIR or IIR filtering depending on your needs in term of
latency and phase distortion. With FIR filters, the phase is linear but the
latency is maximum. With IIR filtering, the phase is compromised around the
Nyquist frequency but the latency is minimum.
latency is maximised. With IIR filtering, the phase is compromised around the
Nyquist frequency but the latency is minimised.
@see FilterDesign.
@ -70,9 +70,6 @@ public:
Constructor of the oversampling class. All the processing parameters must be
provided at the creation of the oversampling object.
Note: You might want to create a class inheriting from Oversampling with a
different constructor if you need more control on what happens in the process.
@param numChannels the number of channels to process with this object
@param factor the processing will perform 2 ^ factor times oversampling
@param type the type of filter design employed for filtering during
@ -86,8 +83,13 @@ public:
FilterType type,
bool isMaxQuality = true);
/** Default constructor of the oversampling class, which can be used to create an
/** The default constructor of the oversampling class, which can be used to create an
empty object and then add the appropriate stages.
Note: This creates a "dummy" oversampling stage, which needs to be removed first
before adding proper oversampling stages.
@see clearOversamplingStages, addOversamplingStage
*/
explicit Oversampling (size_t numChannels = 1);
@ -134,12 +136,49 @@ public:
void processSamplesDown (dsp::AudioBlock<SampleType>& outputBlock) noexcept;
//===============================================================================
void addOversamplingStage (FilterType,
float normalizedTransitionWidthUp, float stopbandAttenuationdBUp,
float normalizedTransitionWidthDown, float stopbandAttenuationdBDown);
/** Adds a new oversampling stage to the Oversampling class, multiplying the
current oversampling factor by two. This is used with the default constructor
to create custom oversampling chains, requiring a call to the
clearOversamplingStages before any addition.
Note: Upsampling and downsampling filtering have different purposes, the
former removes upsampling artefacts while the latter removes useless frequency
content created by the oversampled process, so usually the attenuation is
increased when upsampling compared to downsampling.
@param type the type of filter design employed for filtering
during oversampling
@param normalisedTransitionWidthUp a value between 0 and 0.5 which specifies how much
the transition between passband and stopband is
steep, for upsampling filtering (the lower the better)
@param stopbandAmplitudedBUp the amplitude in dB in the stopband for upsampling
filtering, must be negative
@param normalisedTransitionWidthDown a value between 0 and 0.5 which specifies how much
the transition between passband and stopband is
steep, for downsampling filtering (the lower the better)
@param stopbandAmplitudedBDown the amplitude in dB in the stopband for downsampling
filtering, must be negative
@see clearOversamplingStages
*/
void addOversamplingStage (FilterType,
float normalisedTransitionWidthUp, float stopbandAmplitudedBUp,
float normalisedTransitionWidthDown, float stopbandAmplitudedBDown);
/** Adds a new "dummy" oversampling stage, which does nothing to the signal. Using
one can be useful if your application features a customisable oversampling factor
and if you want to select the current one from an OwnedArray without changing
anything in the processing code.
@see OwnedArray, clearOversamplingStages, addOversamplingStage
*/
void addDummyOversamplingStage();
/** Removes all the previously registered oversampling stages, so you can add
your own from scratch.
@see addOversamplingStage, addDummyOversamplingStage
*/
void clearOversamplingStages();
//===============================================================================