From e546767a6d993fab0fbc9601ee4154a6d4427161 Mon Sep 17 00:00:00 2001 From: Chris Cannam Date: Tue, 21 Jun 2022 10:25:08 +0100 Subject: [PATCH] Rename/rejig so as to have just a single Impl and then R2 and R3 stretcher classes --- README.md | 2 +- meson.build | 4 +- rubberband/RubberBandStretcher.h | 5 +- single/RubberBandSingle.cpp | 2 +- src/RubberBandStretcher.cpp | 356 ++++++++++++++---- src/common/sysutils.h | 6 + .../{StretcherImpl.cpp => R2Stretcher.cpp} | 165 ++++---- src/faster/{StretcherImpl.h => R2Stretcher.h} | 31 +- src/faster/StretcherChannelData.cpp | 32 +- src/faster/StretcherChannelData.h | 4 +- src/faster/StretcherProcess.cpp | 120 +++--- src/finer/Guide.h | 5 +- .../{R3StretcherImpl.cpp => R3Stretcher.cpp} | 86 ++--- .../{R3StretcherImpl.h => R3Stretcher.h} | 10 +- 14 files changed, 534 insertions(+), 294 deletions(-) rename src/faster/{StretcherImpl.cpp => R2Stretcher.cpp} (87%) rename src/faster/{StretcherImpl.h => R2Stretcher.h} (92%) rename src/finer/{R3StretcherImpl.cpp => R3Stretcher.cpp} (92%) rename src/finer/{R3StretcherImpl.h => R3Stretcher.h} (98%) diff --git a/README.md b/README.md index ffe204c..16671ff 100644 --- a/README.md +++ b/README.md @@ -106,7 +106,7 @@ Rubber Band consists of: ## 2. Using the Rubber Band command-line tool -The Rubber Band command-line tool builds as `bin/rubberband`. The +The Rubber Band command-line tool builds as `build/rubberband`. The basic incantation is ``` diff --git a/meson.build b/meson.build index a9404e9..442e274 100644 --- a/meson.build +++ b/meson.build @@ -39,8 +39,8 @@ library_sources = [ 'src/faster/HighFrequencyAudioCurve.cpp', 'src/faster/SilentAudioCurve.cpp', 'src/faster/PercussiveAudioCurve.cpp', + 'src/faster/R2Stretcher.cpp', 'src/faster/StretcherChannelData.cpp', - 'src/faster/StretcherImpl.cpp', 'src/faster/StretcherProcess.cpp', 'src/common/Profiler.cpp', 'src/common/Resampler.cpp', @@ -49,7 +49,7 @@ library_sources = [ 'src/common/StretchCalculator.cpp', 'src/common/sysutils.cpp', 'src/common/Thread.cpp', - 'src/finer/R3StretcherImpl.cpp', + 'src/finer/R3Stretcher.cpp', ] jni_sources = [ diff --git a/rubberband/RubberBandStretcher.h b/rubberband/RubberBandStretcher.h index b14a440..60fc9d9 100644 --- a/rubberband/RubberBandStretcher.h +++ b/rubberband/RubberBandStretcher.h @@ -81,7 +81,6 @@ namespace RubberBand { -class R3StretcherImpl;//!!! class RUBBERBAND_DLLEXPORT RubberBandStretcher @@ -807,7 +806,9 @@ public: protected: class Impl; Impl *m_d; - R3StretcherImpl *m_r3d; + + RubberBandStretcher(const RubberBandStretcher &) =delete; + RubberBandStretcher &operator=(const RubberBandStretcher &) =delete; }; } diff --git a/single/RubberBandSingle.cpp b/single/RubberBandSingle.cpp index a04b2c4..bea6a76 100644 --- a/single/RubberBandSingle.cpp +++ b/single/RubberBandSingle.cpp @@ -70,7 +70,7 @@ #include "../src/common/sysutils.cpp" #include "../src/common/Thread.cpp" #include "../src/faster/StretcherChannelData.cpp" -#include "../src/faster/StretcherImpl.cpp" +#include "../src/faster/R2StretcherImpl.cpp" #include "../src/faster/StretcherProcess.cpp" #include "../src/finer/R3StretcherImpl.cpp" diff --git a/src/RubberBandStretcher.cpp b/src/RubberBandStretcher.cpp index f850d89..6043217 100644 --- a/src/RubberBandStretcher.cpp +++ b/src/RubberBandStretcher.cpp @@ -21,169 +21,402 @@ you must obtain a valid commercial licence before doing so. */ -#include "faster/StretcherImpl.h" -#include "finer/R3StretcherImpl.h" +#include "faster/R2Stretcher.h" +#include "finer/R3Stretcher.h" namespace RubberBand { +class RubberBandStretcher::Impl +{ + R2Stretcher *m_r2; + R3Stretcher *m_r3; + +public: + Impl(size_t sampleRate, size_t channels, Options options, + double initialTimeRatio, double initialPitchScale) : + m_r2 (!(options & OptionEngineFiner) ? + new R2Stretcher(sampleRate, channels, options, + initialTimeRatio, initialPitchScale) + : nullptr), + m_r3 ((options & OptionEngineFiner) ? + new R3Stretcher(R3Stretcher::Parameters + (double(sampleRate), channels, options), + initialTimeRatio, initialPitchScale) + : nullptr) + { + } + + ~Impl() + { + delete m_r2; + delete m_r3; + } + + void reset() + { + if (m_r2) m_r2->reset(); + else m_r3->reset(); + } + + RTENTRY__ + void + setTimeRatio(double ratio) + { + if (m_r2) m_r2->setTimeRatio(ratio); + else m_r3->setTimeRatio(ratio); + } + + RTENTRY__ + void + setPitchScale(double scale) + { + if (m_r2) m_r2->setPitchScale(scale); + else m_r3->setPitchScale(scale); + } + + RTENTRY__ + void + setFormantScale(double scale) + { + //!!! + if (m_r3) m_r3->setFormantScale(scale); + } + + RTENTRY__ + double + getTimeRatio() const + { + if (m_r2) return m_r2->getTimeRatio(); + else return m_r3->getTimeRatio(); + } + + RTENTRY__ + double + getPitchScale() const + { + if (m_r2) return m_r2->getPitchScale(); + else return m_r3->getPitchScale(); + } + + RTENTRY__ + double + getFormantScale() const + { + //!!! + if (m_r2) return 0.0; + else return m_r3->getFormantScale(); + } + + RTENTRY__ + size_t + getLatency() const + { + if (m_r2) return m_r2->getLatency(); + else return m_r3->getLatency(); + } + +//!!! review all these + + RTENTRY__ + void + setTransientsOption(Options options) + { + if (m_r2) m_r2->setTransientsOption(options); + } + + RTENTRY__ + void + setDetectorOption(Options options) + { + if (m_r2) m_r2->setDetectorOption(options); + } + + RTENTRY__ + void + setPhaseOption(Options options) + { + if (m_r2) m_r2->setPhaseOption(options); + } + + RTENTRY__ + void + setFormantOption(Options options) + { + if (m_r2) m_r2->setFormantOption(options); + else if (m_r3) m_r3->setFormantOption(options); + } + + RTENTRY__ + void + setPitchOption(Options options) + { + if (m_r2) m_r2->setPitchOption(options); + } + + void + setExpectedInputDuration(size_t samples) + { + if (m_r2) m_r2->setExpectedInputDuration(samples); + } + + void + setMaxProcessSize(size_t samples) + { + if (m_r2) m_r2->setMaxProcessSize(samples); //!!! definitely need for r3d + } + + void + setKeyFrameMap(const std::map &mapping) + { + if (m_r2) m_r2->setKeyFrameMap(mapping); + else m_r3->setKeyFrameMap(mapping); + } + + RTENTRY__ + size_t + getSamplesRequired() const + { + if (m_r2) return m_r2->getSamplesRequired(); + else return m_r3->getSamplesRequired(); + } + + void + study(const float *const *input, size_t samples, + bool final) + { + if (m_r2) m_r2->study(input, samples, final); + else m_r3->study(input, samples, final); + } + + RTENTRY__ + void + process(const float *const *input, size_t samples, + bool final) + { + if (m_r2) m_r2->process(input, samples, final); + else m_r3->process(input, samples, final); + } + + RTENTRY__ + int + available() const + { + if (m_r2) return m_r2->available(); + else return m_r3->available(); + } + + RTENTRY__ + size_t + retrieve(float *const *output, size_t samples) const + { + if (m_r2) return m_r2->retrieve(output, samples); + else return m_r3->retrieve(output, samples); + } + + float + getFrequencyCutoff(int n) const + { + if (m_r2) return m_r2->getFrequencyCutoff(n); + else return {}; + } + + void + setFrequencyCutoff(int n, float f) + { + if (m_r2) m_r2->setFrequencyCutoff(n, f); + } + + size_t + getInputIncrement() const + { + if (m_r2) return m_r2->getInputIncrement(); + else return {}; + } + + std::vector + getOutputIncrements() const + { + if (m_r2) return m_r2->getOutputIncrements(); + else return {}; + } + + std::vector + getPhaseResetCurve() const + { + if (m_r2) return m_r2->getPhaseResetCurve(); + else return {}; + } + + std::vector + getExactTimePoints() const + { + if (m_r2) return m_r2->getExactTimePoints(); + else return {}; + } + + RTENTRY__ + size_t + getChannelCount() const + { + if (m_r2) return m_r2->getChannelCount(); + else return m_r3->getChannelCount(); + } + + void + calculateStretch() + { + if (m_r2) m_r2->calculateStretch(); + } + + void + setDebugLevel(int level) + { + if (m_r2) m_r2->setDebugLevel(level); + } + + static void + setDefaultDebugLevel(int level) + { + R2Stretcher::setDefaultDebugLevel(level); +//!!! R3Stretcher::setDefaultDebugLevel(level); + } +}; + RubberBandStretcher::RubberBandStretcher(size_t sampleRate, size_t channels, Options options, double initialTimeRatio, double initialPitchScale) : - m_d - (!(options & OptionEngineFiner) ? - new Impl(sampleRate, channels, options, - initialTimeRatio, initialPitchScale) - : nullptr), - m_r3d - ((options & OptionEngineFiner) ? - new R3StretcherImpl(R3StretcherImpl::Parameters - (double(sampleRate), channels, options), - initialTimeRatio, initialPitchScale) - : nullptr) + m_d(new Impl(sampleRate, channels, options, + initialTimeRatio, initialPitchScale)) { } RubberBandStretcher::~RubberBandStretcher() { delete m_d; - delete m_r3d; } void RubberBandStretcher::reset() { - if (m_d) m_d->reset(); - else m_r3d->reset(); + m_d->reset(); } RTENTRY__ void RubberBandStretcher::setTimeRatio(double ratio) { - if (m_d) m_d->setTimeRatio(ratio); - else m_r3d->setTimeRatio(ratio); + m_d->setTimeRatio(ratio); } RTENTRY__ void RubberBandStretcher::setPitchScale(double scale) { - if (m_d) m_d->setPitchScale(scale); - else m_r3d->setPitchScale(scale); + m_d->setPitchScale(scale); } RTENTRY__ void RubberBandStretcher::setFormantScale(double scale) { - if (m_r3d) m_r3d->setFormantScale(scale); + m_d->setFormantScale(scale); } RTENTRY__ double RubberBandStretcher::getTimeRatio() const { - if (m_d) return m_d->getTimeRatio(); - else return m_r3d->getTimeRatio(); + return m_d->getTimeRatio(); } RTENTRY__ double RubberBandStretcher::getPitchScale() const { - if (m_d) return m_d->getPitchScale(); - else return m_r3d->getPitchScale(); + return m_d->getPitchScale(); } RTENTRY__ double RubberBandStretcher::getFormantScale() const { - if (m_d) return 0.0; - else return m_r3d->getFormantScale(); + return m_d->getFormantScale(); } RTENTRY__ size_t RubberBandStretcher::getLatency() const { - if (m_d) return m_d->getLatency(); - else return m_r3d->getLatency(); + return m_d->getLatency(); } -//!!! review all these - RTENTRY__ void RubberBandStretcher::setTransientsOption(Options options) { - if (m_d) m_d->setTransientsOption(options); + m_d->setTransientsOption(options); } RTENTRY__ void RubberBandStretcher::setDetectorOption(Options options) { - if (m_d) m_d->setDetectorOption(options); + m_d->setDetectorOption(options); } RTENTRY__ void RubberBandStretcher::setPhaseOption(Options options) { - if (m_d) m_d->setPhaseOption(options); + m_d->setPhaseOption(options); } RTENTRY__ void RubberBandStretcher::setFormantOption(Options options) { - if (m_d) m_d->setFormantOption(options); - else if (m_r3d) m_r3d->setFormantOption(options); + m_d->setFormantOption(options); } RTENTRY__ void RubberBandStretcher::setPitchOption(Options options) { - if (m_d) m_d->setPitchOption(options); + m_d->setPitchOption(options); } void RubberBandStretcher::setExpectedInputDuration(size_t samples) { - if (m_d) m_d->setExpectedInputDuration(samples); + m_d->setExpectedInputDuration(samples); } void RubberBandStretcher::setMaxProcessSize(size_t samples) { - if (m_d) m_d->setMaxProcessSize(samples); //!!! definitely need for r3d + m_d->setMaxProcessSize(samples); } void RubberBandStretcher::setKeyFrameMap(const std::map &mapping) { - if (m_d) m_d->setKeyFrameMap(mapping); - else m_r3d->setKeyFrameMap(mapping); + m_d->setKeyFrameMap(mapping); } RTENTRY__ size_t RubberBandStretcher::getSamplesRequired() const { - if (m_d) return m_d->getSamplesRequired(); - else return m_r3d->getSamplesRequired(); + return m_d->getSamplesRequired(); } void RubberBandStretcher::study(const float *const *input, size_t samples, bool final) { - if (m_d) m_d->study(input, samples, final); - else m_r3d->study(input, samples, final); + m_d->study(input, samples, final); } RTENTRY__ @@ -191,85 +424,76 @@ void RubberBandStretcher::process(const float *const *input, size_t samples, bool final) { - if (m_d) m_d->process(input, samples, final); - else m_r3d->process(input, samples, final); + m_d->process(input, samples, final); } RTENTRY__ int RubberBandStretcher::available() const { - if (m_d) return m_d->available(); - else return m_r3d->available(); + return m_d->available(); } RTENTRY__ size_t RubberBandStretcher::retrieve(float *const *output, size_t samples) const { - if (m_d) return m_d->retrieve(output, samples); - else return m_r3d->retrieve(output, samples); + return m_d->retrieve(output, samples); } float RubberBandStretcher::getFrequencyCutoff(int n) const { - if (m_d) return m_d->getFrequencyCutoff(n); - else return {}; + return m_d->getFrequencyCutoff(n); } void RubberBandStretcher::setFrequencyCutoff(int n, float f) { - if (m_d) m_d->setFrequencyCutoff(n, f); + m_d->setFrequencyCutoff(n, f); } size_t RubberBandStretcher::getInputIncrement() const { - if (m_d) return m_d->getInputIncrement(); - else return {}; + return m_d->getInputIncrement(); } std::vector RubberBandStretcher::getOutputIncrements() const { - if (m_d) return m_d->getOutputIncrements(); - else return {}; + return m_d->getOutputIncrements(); } std::vector RubberBandStretcher::getPhaseResetCurve() const { - if (m_d) return m_d->getPhaseResetCurve(); - else return {}; + return m_d->getPhaseResetCurve(); } std::vector RubberBandStretcher::getExactTimePoints() const { - if (m_d) return m_d->getExactTimePoints(); - else return {}; + return m_d->getExactTimePoints(); } RTENTRY__ size_t RubberBandStretcher::getChannelCount() const { - if (m_d) return m_d->getChannelCount(); - else return m_r3d->getChannelCount(); + return m_d->getChannelCount(); } void RubberBandStretcher::calculateStretch() { - if (m_d) m_d->calculateStretch(); + m_d->calculateStretch(); } void RubberBandStretcher::setDebugLevel(int level) { - if (m_d) m_d->setDebugLevel(level); + m_d->setDebugLevel(level); } void diff --git a/src/common/sysutils.h b/src/common/sysutils.h index e0532f3..9bcdd9a 100644 --- a/src/common/sysutils.h +++ b/src/common/sysutils.h @@ -88,6 +88,12 @@ namespace RubberBand { +#ifdef PROCESS_SAMPLE_TYPE +typedef PROCESS_SAMPLE_TYPE process_t; +#else +typedef double process_t; +#endif + extern const char *system_get_platform_tag(); extern bool system_is_multiprocessor(); extern void system_specific_initialise(); diff --git a/src/faster/StretcherImpl.cpp b/src/faster/R2Stretcher.cpp similarity index 87% rename from src/faster/StretcherImpl.cpp rename to src/faster/R2Stretcher.cpp index 4cc760b..202f69a 100644 --- a/src/faster/StretcherImpl.cpp +++ b/src/faster/R2Stretcher.cpp @@ -21,7 +21,7 @@ you must obtain a valid commercial licence before doing so. */ -#include "StretcherImpl.h" +#include "R2Stretcher.h" #include "PercussiveAudioCurve.h" #include "HighFrequencyAudioCurve.h" @@ -51,21 +51,21 @@ using std::min; namespace RubberBand { const size_t -RubberBandStretcher::Impl::m_defaultIncrement = 256; +R2Stretcher::m_defaultIncrement = 256; const size_t -RubberBandStretcher::Impl::m_defaultFftSize = 2048; +R2Stretcher::m_defaultFftSize = 2048; int -RubberBandStretcher::Impl::m_defaultDebugLevel = 0; +R2Stretcher::m_defaultDebugLevel = 0; static bool _initialised = false; -RubberBandStretcher::Impl::Impl(size_t sampleRate, - size_t channels, - Options options, - double initialTimeRatio, - double initialPitchScale) : +R2Stretcher::R2Stretcher(size_t sampleRate, + size_t channels, + RubberBandStretcher::Options options, + double initialTimeRatio, + double initialPitchScale) : m_sampleRate(sampleRate), m_channels(channels), m_timeRatio(initialTimeRatio), @@ -111,7 +111,7 @@ RubberBandStretcher::Impl::Impl(size_t sampleRate, } if (m_debugLevel > 0) { - cerr << "RubberBandStretcher::Impl::Impl: rate = " << m_sampleRate << ", options = " << options << endl; + cerr << "R2Stretcher::R2Stretcher: rate = " << m_sampleRate << ", options = " << options << endl; } // Window size will vary according to the audio sample rate, but @@ -120,15 +120,17 @@ RubberBandStretcher::Impl::Impl(size_t sampleRate, // if (m_rateMultiple < 1.f) m_rateMultiple = 1.f; m_baseFftSize = roundUp(int(m_defaultFftSize * m_rateMultiple)); - if ((options & OptionWindowShort) || (options & OptionWindowLong)) { - if ((options & OptionWindowShort) && (options & OptionWindowLong)) { - cerr << "RubberBandStretcher::Impl::Impl: Cannot specify OptionWindowLong and OptionWindowShort together; falling back to OptionWindowStandard" << endl; - } else if (options & OptionWindowShort) { + if ((options & RubberBandStretcher::OptionWindowShort) || + (options & RubberBandStretcher::OptionWindowLong)) { + if ((options & RubberBandStretcher::OptionWindowShort) && + (options & RubberBandStretcher::OptionWindowLong)) { + cerr << "R2Stretcher::R2Stretcher: Cannot specify OptionWindowLong and OptionWindowShort together; falling back to OptionWindowStandard" << endl; + } else if (options & RubberBandStretcher::OptionWindowShort) { m_baseFftSize = m_baseFftSize / 2; if (m_debugLevel > 0) { cerr << "setting baseFftSize to " << m_baseFftSize << endl; } - } else if (options & OptionWindowLong) { + } else if (options & RubberBandStretcher::OptionWindowLong) { m_baseFftSize = m_baseFftSize * 2; if (m_debugLevel > 0) { cerr << "setting baseFftSize to " << m_baseFftSize << endl; @@ -141,7 +143,7 @@ RubberBandStretcher::Impl::Impl(size_t sampleRate, m_maxProcessSize = m_aWindowSize; } - if (m_options & OptionProcessRealTime) { + if (m_options & RubberBandStretcher::OptionProcessRealTime) { m_realtime = true; } @@ -152,9 +154,9 @@ RubberBandStretcher::Impl::Impl(size_t sampleRate, if (m_realtime) { m_threaded = false; - } else if (m_options & OptionThreadingNever) { + } else if (m_options & RubberBandStretcher::OptionThreadingNever) { m_threaded = false; - } else if (!(m_options & OptionThreadingAlways) && + } else if (!(m_options & RubberBandStretcher::OptionThreadingAlways) && !system_is_multiprocessor()) { m_threaded = false; } @@ -168,7 +170,7 @@ RubberBandStretcher::Impl::Impl(size_t sampleRate, configure(); } -RubberBandStretcher::Impl::~Impl() +R2Stretcher::~R2Stretcher() { #ifndef NO_THREADING if (m_threaded) { @@ -205,7 +207,7 @@ RubberBandStretcher::Impl::~Impl() } void -RubberBandStretcher::Impl::reset() +R2Stretcher::reset() { #ifndef NO_THREADING if (m_threaded) { @@ -247,11 +249,11 @@ RubberBandStretcher::Impl::reset() } void -RubberBandStretcher::Impl::setTimeRatio(double ratio) +R2Stretcher::setTimeRatio(double ratio) { if (!m_realtime) { if (m_mode == Studying || m_mode == Processing) { - cerr << "RubberBandStretcher::Impl::setTimeRatio: Cannot set ratio while studying or processing in non-RT mode" << endl; + cerr << "R2Stretcher::setTimeRatio: Cannot set ratio while studying or processing in non-RT mode" << endl; return; } } @@ -263,11 +265,11 @@ RubberBandStretcher::Impl::setTimeRatio(double ratio) } void -RubberBandStretcher::Impl::setPitchScale(double fs) +R2Stretcher::setPitchScale(double fs) { if (!m_realtime) { if (m_mode == Studying || m_mode == Processing) { - cerr << "RubberBandStretcher::Impl::setPitchScale: Cannot set ratio while studying or processing in non-RT mode" << endl; + cerr << "R2Stretcher::setPitchScale: Cannot set ratio while studying or processing in non-RT mode" << endl; return; } } @@ -281,7 +283,7 @@ RubberBandStretcher::Impl::setPitchScale(double fs) reconfigure(); - if (!(m_options & OptionPitchHighConsistency) && + if (!(m_options & RubberBandStretcher::OptionPitchHighConsistency) && (was1 || resampleBeforeStretching() != rbs) && m_pitchScale != 1.f) { @@ -295,19 +297,19 @@ RubberBandStretcher::Impl::setPitchScale(double fs) } double -RubberBandStretcher::Impl::getTimeRatio() const +R2Stretcher::getTimeRatio() const { return m_timeRatio; } double -RubberBandStretcher::Impl::getPitchScale() const +R2Stretcher::getPitchScale() const { return m_pitchScale; } void -RubberBandStretcher::Impl::setExpectedInputDuration(size_t samples) +R2Stretcher::setExpectedInputDuration(size_t samples) { if (samples == m_expectedInputDuration) return; m_expectedInputDuration = samples; @@ -316,7 +318,7 @@ RubberBandStretcher::Impl::setExpectedInputDuration(size_t samples) } void -RubberBandStretcher::Impl::setMaxProcessSize(size_t samples) +R2Stretcher::setMaxProcessSize(size_t samples) { if (samples <= m_maxProcessSize) return; m_maxProcessSize = samples; @@ -325,15 +327,15 @@ RubberBandStretcher::Impl::setMaxProcessSize(size_t samples) } void -RubberBandStretcher::Impl::setKeyFrameMap(const std::map & +R2Stretcher::setKeyFrameMap(const std::map & mapping) { if (m_realtime) { - cerr << "RubberBandStretcher::Impl::setKeyFrameMap: Cannot specify key frame map in RT mode" << endl; + cerr << "R2Stretcher::setKeyFrameMap: Cannot specify key frame map in RT mode" << endl; return; } if (m_mode == Processing) { - cerr << "RubberBandStretcher::Impl::setKeyFrameMap: Cannot specify key frame map after process() has begun" << endl; + cerr << "R2Stretcher::setKeyFrameMap: Cannot specify key frame map after process() has begun" << endl; return; } @@ -343,7 +345,7 @@ RubberBandStretcher::Impl::setKeyFrameMap(const std::map & } float -RubberBandStretcher::Impl::getFrequencyCutoff(int n) const +R2Stretcher::getFrequencyCutoff(int n) const { switch (n) { case 0: return m_freq0; @@ -354,7 +356,7 @@ RubberBandStretcher::Impl::getFrequencyCutoff(int n) const } void -RubberBandStretcher::Impl::setFrequencyCutoff(int n, float f) +R2Stretcher::setFrequencyCutoff(int n, float f) { switch (n) { case 0: m_freq0 = f; break; @@ -364,7 +366,7 @@ RubberBandStretcher::Impl::setFrequencyCutoff(int n, float f) } double -RubberBandStretcher::Impl::getEffectiveRatio() const +R2Stretcher::getEffectiveRatio() const { // Returns the ratio that the internal time stretcher needs to // achieve, not the resulting duration ratio of the output (which @@ -381,7 +383,7 @@ RubberBandStretcher::Impl::getEffectiveRatio() const } size_t -RubberBandStretcher::Impl::roundUp(size_t value) +R2Stretcher::roundUp(size_t value) { if (!(value & (value - 1))) return value; int bits = 0; @@ -391,7 +393,7 @@ RubberBandStretcher::Impl::roundUp(size_t value) } void -RubberBandStretcher::Impl::calculateSizes() +R2Stretcher::calculateSizes() { size_t inputIncrement = m_defaultIncrement; size_t windowSize = m_baseFftSize; @@ -511,7 +513,7 @@ RubberBandStretcher::Impl::calculateSizes() m_fftSize = windowSize; - if (m_options & OptionSmoothingOn) { + if (m_options & RubberBandStretcher::OptionSmoothingOn) { m_aWindowSize = windowSize * 2; m_sWindowSize = windowSize * 2; } else { @@ -565,7 +567,7 @@ RubberBandStretcher::Impl::calculateSizes() } void -RubberBandStretcher::Impl::configure() +R2Stretcher::configure() { if (m_debugLevel > 0) { std::cerr << "configure[" << this << "]: realtime = " << m_realtime << ", pitch scale = " @@ -652,7 +654,7 @@ RubberBandStretcher::Impl::configure() } if (m_pitchScale != 1.0 || - (m_options & OptionPitchHighConsistency) || + (m_options & RubberBandStretcher::OptionPitchHighConsistency) || m_realtime) { for (size_t c = 0; c < m_channels; ++c) { @@ -698,7 +700,7 @@ RubberBandStretcher::Impl::configure() delete m_stretchCalculator; m_stretchCalculator = new StretchCalculator (m_sampleRate, m_increment, - !(m_options & OptionTransientsSmooth)); + !(m_options & RubberBandStretcher::OptionTransientsSmooth)); m_stretchCalculator->setDebugLevel(m_debugLevel); m_inputDuration = 0; @@ -727,7 +729,7 @@ RubberBandStretcher::Impl::configure() void -RubberBandStretcher::Impl::reconfigure() +R2Stretcher::reconfigure() { if (!m_realtime) { if (m_mode == Studying) { @@ -836,43 +838,50 @@ RubberBandStretcher::Impl::reconfigure() } size_t -RubberBandStretcher::Impl::getLatency() const +R2Stretcher::getLatency() const { if (!m_realtime) return 0; return lrint((m_aWindowSize/2) / m_pitchScale); } void -RubberBandStretcher::Impl::setTransientsOption(Options options) +R2Stretcher::setTransientsOption(RubberBandStretcher::Options options) { if (!m_realtime) { - cerr << "RubberBandStretcher::Impl::setTransientsOption: Not permissible in non-realtime mode" << endl; + cerr << "R2Stretcher::setTransientsOption: Not permissible in non-realtime mode" << endl; return; } - int mask = (OptionTransientsMixed | OptionTransientsSmooth | OptionTransientsCrisp); + int mask = (RubberBandStretcher::OptionTransientsMixed | + RubberBandStretcher::OptionTransientsSmooth | + RubberBandStretcher::OptionTransientsCrisp); m_options &= ~mask; options &= mask; m_options |= options; m_stretchCalculator->setUseHardPeaks - (!(m_options & OptionTransientsSmooth)); + (!(m_options & RubberBandStretcher::OptionTransientsSmooth)); } void -RubberBandStretcher::Impl::setDetectorOption(Options options) +R2Stretcher::setDetectorOption(RubberBandStretcher::Options options) { if (!m_realtime) { - cerr << "RubberBandStretcher::Impl::setDetectorOption: Not permissible in non-realtime mode" << endl; + cerr << "R2Stretcher::setDetectorOption: Not permissible in non-realtime mode" << endl; return; } - int mask = (OptionDetectorPercussive | OptionDetectorCompound | OptionDetectorSoft); + int mask = (RubberBandStretcher::OptionDetectorPercussive | + RubberBandStretcher::OptionDetectorCompound | + RubberBandStretcher::OptionDetectorSoft); m_options &= ~mask; options &= mask; m_options |= options; CompoundAudioCurve::Type dt = CompoundAudioCurve::CompoundDetector; - if (m_options & OptionDetectorPercussive) dt = CompoundAudioCurve::PercussiveDetector; - else if (m_options & OptionDetectorSoft) dt = CompoundAudioCurve::SoftDetector; + if (m_options & RubberBandStretcher::OptionDetectorPercussive) { + dt = CompoundAudioCurve::PercussiveDetector; + } else if (m_options & RubberBandStretcher::OptionDetectorSoft) { + dt = CompoundAudioCurve::SoftDetector; + } if (dt == m_detectorType) return; m_detectorType = dt; @@ -883,36 +892,38 @@ RubberBandStretcher::Impl::setDetectorOption(Options options) } void -RubberBandStretcher::Impl::setPhaseOption(Options options) +R2Stretcher::setPhaseOption(RubberBandStretcher::Options options) { - int mask = (OptionPhaseLaminar | OptionPhaseIndependent); + int mask = (RubberBandStretcher::OptionPhaseLaminar | + RubberBandStretcher::OptionPhaseIndependent); m_options &= ~mask; options &= mask; m_options |= options; } void -RubberBandStretcher::Impl::setFormantOption(Options options) +R2Stretcher::setFormantOption(RubberBandStretcher::Options options) { - int mask = (OptionFormantShifted | OptionFormantPreserved); + int mask = (RubberBandStretcher::OptionFormantShifted | + RubberBandStretcher::OptionFormantPreserved); m_options &= ~mask; options &= mask; m_options |= options; } void -RubberBandStretcher::Impl::setPitchOption(Options options) +R2Stretcher::setPitchOption(RubberBandStretcher::Options options) { if (!m_realtime) { - cerr << "RubberBandStretcher::Impl::setPitchOption: Pitch option is not used in non-RT mode" << endl; + cerr << "R2Stretcher::setPitchOption: Pitch option is not used in non-RT mode" << endl; return; } - Options prior = m_options; + RubberBandStretcher::Options prior = m_options; - int mask = (OptionPitchHighQuality | - OptionPitchHighSpeed | - OptionPitchHighConsistency); + int mask = (RubberBandStretcher::OptionPitchHighQuality | + RubberBandStretcher::OptionPitchHighSpeed | + RubberBandStretcher::OptionPitchHighConsistency); m_options &= ~mask; options &= mask; m_options |= options; @@ -921,19 +932,19 @@ RubberBandStretcher::Impl::setPitchOption(Options options) } void -RubberBandStretcher::Impl::study(const float *const *input, size_t samples, bool final) +R2Stretcher::study(const float *const *input, size_t samples, bool final) { - Profiler profiler("RubberBandStretcher::Impl::study"); + Profiler profiler("R2Stretcher::study"); if (m_realtime) { if (m_debugLevel > 1) { - cerr << "RubberBandStretcher::Impl::study: Not meaningful in realtime mode" << endl; + cerr << "R2Stretcher::study: Not meaningful in realtime mode" << endl; } return; } if (m_mode == Processing || m_mode == Finished) { - cerr << "RubberBandStretcher::Impl::study: Cannot study after processing" << endl; + cerr << "R2Stretcher::study: Cannot study after processing" << endl; return; } m_mode = Studying; @@ -1071,7 +1082,7 @@ RubberBandStretcher::Impl::study(const float *const *input, size_t samples, bool } vector -RubberBandStretcher::Impl::getOutputIncrements() const +R2Stretcher::getOutputIncrements() const { if (!m_realtime) { return m_outputIncrements; @@ -1085,7 +1096,7 @@ RubberBandStretcher::Impl::getOutputIncrements() const } vector -RubberBandStretcher::Impl::getPhaseResetCurve() const +R2Stretcher::getPhaseResetCurve() const { if (!m_realtime) { return m_phaseResetDf; @@ -1099,7 +1110,7 @@ RubberBandStretcher::Impl::getPhaseResetCurve() const } vector -RubberBandStretcher::Impl::getExactTimePoints() const +R2Stretcher::getExactTimePoints() const { std::vector points; if (!m_realtime) { @@ -1113,9 +1124,9 @@ RubberBandStretcher::Impl::getExactTimePoints() const } void -RubberBandStretcher::Impl::calculateStretch() +R2Stretcher::calculateStretch() { - Profiler profiler("RubberBandStretcher::Impl::calculateStretch"); + Profiler profiler("R2Stretcher::calculateStretch"); size_t inputDuration = m_inputDuration; @@ -1156,16 +1167,16 @@ RubberBandStretcher::Impl::calculateStretch() } void -RubberBandStretcher::Impl::setDebugLevel(int level) +R2Stretcher::setDebugLevel(int level) { m_debugLevel = level; if (m_stretchCalculator) m_stretchCalculator->setDebugLevel(level); } size_t -RubberBandStretcher::Impl::getSamplesRequired() const +R2Stretcher::getSamplesRequired() const { - Profiler profiler("RubberBandStretcher::Impl::getSamplesRequired"); + Profiler profiler("R2Stretcher::getSamplesRequired"); size_t reqd = 0; @@ -1214,12 +1225,12 @@ RubberBandStretcher::Impl::getSamplesRequired() const } void -RubberBandStretcher::Impl::process(const float *const *input, size_t samples, bool final) +R2Stretcher::process(const float *const *input, size_t samples, bool final) { - Profiler profiler("RubberBandStretcher::Impl::process"); + Profiler profiler("R2Stretcher::process"); if (m_mode == Finished) { - cerr << "RubberBandStretcher::Impl::process: Cannot process again after final chunk" << endl; + cerr << "R2Stretcher::process: Cannot process again after final chunk" << endl; return; } diff --git a/src/faster/StretcherImpl.h b/src/faster/R2Stretcher.h similarity index 92% rename from src/faster/StretcherImpl.h rename to src/faster/R2Stretcher.h index 98be6fc..06efbcb 100644 --- a/src/faster/StretcherImpl.h +++ b/src/faster/R2Stretcher.h @@ -42,21 +42,16 @@ namespace RubberBand { -#ifdef PROCESS_SAMPLE_TYPE -typedef PROCESS_SAMPLE_TYPE process_t; -#else -typedef double process_t; -#endif - class AudioCurveCalculator; class StretchCalculator; -class RubberBandStretcher::Impl +class R2Stretcher { public: - Impl(size_t sampleRate, size_t channels, Options options, - double initialTimeRatio, double initialPitchScale); - ~Impl(); + R2Stretcher(size_t sampleRate, size_t channels, + RubberBandStretcher::Options options, + double initialTimeRatio, double initialPitchScale); + ~R2Stretcher(); void reset(); void setTimeRatio(double ratio); @@ -67,11 +62,11 @@ public: size_t getLatency() const; - void setTransientsOption(Options); - void setDetectorOption(Options); - void setPhaseOption(Options); - void setFormantOption(Options); - void setPitchOption(Options); + void setTransientsOption(RubberBandStretcher::Options); + void setDetectorOption(RubberBandStretcher::Options); + void setPhaseOption(RubberBandStretcher::Options); + void setFormantOption(RubberBandStretcher::Options); + void setPitchOption(RubberBandStretcher::Options); void setExpectedInputDuration(size_t samples); void setMaxProcessSize(size_t samples); @@ -178,7 +173,7 @@ protected: #endif bool m_realtime; - Options m_options; + RubberBandStretcher::Options m_options; int m_debugLevel; enum ProcessMode { @@ -203,12 +198,12 @@ protected: class ProcessThread : public Thread { public: - ProcessThread(Impl *s, size_t c); + ProcessThread(R2Stretcher *s, size_t c); void run(); void signalDataAvailable(); void abandon(); private: - Impl *m_s; + R2Stretcher *m_s; size_t m_channel; Condition m_dataAvailable; bool m_abandoning; diff --git a/src/faster/StretcherChannelData.cpp b/src/faster/StretcherChannelData.cpp index 3d379c6..43af2d2 100644 --- a/src/faster/StretcherChannelData.cpp +++ b/src/faster/StretcherChannelData.cpp @@ -31,27 +31,27 @@ namespace RubberBand { -RubberBandStretcher::Impl::ChannelData::ChannelData(size_t windowSize, - size_t fftSize, - size_t outbufSize) +R2Stretcher::ChannelData::ChannelData(size_t windowSize, + size_t fftSize, + size_t outbufSize) { std::set s; construct(s, windowSize, fftSize, outbufSize); } -RubberBandStretcher::Impl::ChannelData::ChannelData(const std::set &sizes, - size_t initialWindowSize, - size_t initialFftSize, - size_t outbufSize) +R2Stretcher::ChannelData::ChannelData(const std::set &sizes, + size_t initialWindowSize, + size_t initialFftSize, + size_t outbufSize) { construct(sizes, initialWindowSize, initialFftSize, outbufSize); } void -RubberBandStretcher::Impl::ChannelData::construct(const std::set &sizes, - size_t initialWindowSize, - size_t initialFftSize, - size_t outbufSize) +R2Stretcher::ChannelData::construct(const std::set &sizes, + size_t initialWindowSize, + size_t initialFftSize, + size_t outbufSize) { size_t maxSize = initialWindowSize * 2; if (initialFftSize > maxSize) maxSize = initialFftSize; @@ -114,7 +114,7 @@ RubberBandStretcher::Impl::ChannelData::construct(const std::set &sizes, void -RubberBandStretcher::Impl::ChannelData::setSizes(size_t windowSize, +R2Stretcher::ChannelData::setSizes(size_t windowSize, size_t fftSize) { // std::cerr << "ChannelData::setSizes: windowSize = " << windowSize << ", fftSize = " << fftSize << std::endl; @@ -206,7 +206,7 @@ RubberBandStretcher::Impl::ChannelData::setSizes(size_t windowSize, } void -RubberBandStretcher::Impl::ChannelData::setOutbufSize(size_t outbufSize) +R2Stretcher::ChannelData::setOutbufSize(size_t outbufSize) { size_t oldSize = outbuf->getSize(); @@ -224,13 +224,13 @@ RubberBandStretcher::Impl::ChannelData::setOutbufSize(size_t outbufSize) } void -RubberBandStretcher::Impl::ChannelData::setResampleBufSize(size_t sz) +R2Stretcher::ChannelData::setResampleBufSize(size_t sz) { resamplebuf = reallocate_and_zero(resamplebuf, resamplebufSize, sz); resamplebufSize = sz; } -RubberBandStretcher::Impl::ChannelData::~ChannelData() +R2Stretcher::ChannelData::~ChannelData() { delete resampler; @@ -259,7 +259,7 @@ RubberBandStretcher::Impl::ChannelData::~ChannelData() } void -RubberBandStretcher::Impl::ChannelData::reset() +R2Stretcher::ChannelData::reset() { inbuf->reset(); outbuf->reset(); diff --git a/src/faster/StretcherChannelData.h b/src/faster/StretcherChannelData.h index ab23f41..1b2d673 100644 --- a/src/faster/StretcherChannelData.h +++ b/src/faster/StretcherChannelData.h @@ -24,7 +24,7 @@ #ifndef RUBBERBAND_STRETCHERCHANNELDATA_H #define RUBBERBAND_STRETCHERCHANNELDATA_H -#include "StretcherImpl.h" +#include "R2Stretcher.h" #include #include @@ -34,7 +34,7 @@ namespace RubberBand class Resampler; -class RubberBandStretcher::Impl::ChannelData +class R2Stretcher::ChannelData { public: /** diff --git a/src/faster/StretcherProcess.cpp b/src/faster/StretcherProcess.cpp index c870bef..64ebd07 100644 --- a/src/faster/StretcherProcess.cpp +++ b/src/faster/StretcherProcess.cpp @@ -21,7 +21,7 @@ you must obtain a valid commercial licence before doing so. */ -#include "StretcherImpl.h" +#include "R2Stretcher.h" #include "StretcherChannelData.h" #include "../common/StretchCalculator.h" @@ -47,7 +47,7 @@ namespace RubberBand { #ifndef NO_THREADING -RubberBandStretcher::Impl::ProcessThread::ProcessThread(Impl *s, size_t c) : +R2Stretcher::ProcessThread::ProcessThread(R2Stretcher *s, size_t c) : m_s(s), m_channel(c), m_dataAvailable(std::string("data ") + char('A' + c)), @@ -55,7 +55,7 @@ RubberBandStretcher::Impl::ProcessThread::ProcessThread(Impl *s, size_t c) : { } void -RubberBandStretcher::Impl::ProcessThread::run() +R2Stretcher::ProcessThread::run() { if (m_s->m_debugLevel > 1) { cerr << "thread " << m_channel << " getting going" << endl; @@ -108,7 +108,7 @@ RubberBandStretcher::Impl::ProcessThread::run() } void -RubberBandStretcher::Impl::ProcessThread::signalDataAvailable() +R2Stretcher::ProcessThread::signalDataAvailable() { m_dataAvailable.lock(); m_dataAvailable.signal(); @@ -116,7 +116,7 @@ RubberBandStretcher::Impl::ProcessThread::signalDataAvailable() } void -RubberBandStretcher::Impl::ProcessThread::abandon() +R2Stretcher::ProcessThread::abandon() { m_abandoning = true; } @@ -124,16 +124,16 @@ RubberBandStretcher::Impl::ProcessThread::abandon() #endif bool -RubberBandStretcher::Impl::resampleBeforeStretching() const +R2Stretcher::resampleBeforeStretching() const { // We can't resample before stretching in offline mode, because // the stretch calculation is based on doing it the other way // around. It would take more work (and testing) to enable this. if (!m_realtime) return false; - if (m_options & OptionPitchHighQuality) { + if (m_options & RubberBandStretcher::OptionPitchHighQuality) { return (m_pitchScale < 1.0); // better sound - } else if (m_options & OptionPitchHighConsistency) { + } else if (m_options & RubberBandStretcher::OptionPitchHighConsistency) { return false; } else { return (m_pitchScale > 1.0); // better performance @@ -141,7 +141,7 @@ RubberBandStretcher::Impl::resampleBeforeStretching() const } void -RubberBandStretcher::Impl::prepareChannelMS(size_t c, +R2Stretcher::prepareChannelMS(size_t c, const float *const *inputs, size_t offset, size_t samples, @@ -161,13 +161,13 @@ RubberBandStretcher::Impl::prepareChannelMS(size_t c, } size_t -RubberBandStretcher::Impl::consumeChannel(size_t c, +R2Stretcher::consumeChannel(size_t c, const float *const *inputs, size_t offset, size_t samples, bool final) { - Profiler profiler("RubberBandStretcher::Impl::consumeChannel"); + Profiler profiler("R2Stretcher::consumeChannel"); ChannelData &cd = *m_channelData[c]; RingBuffer &inbuf = *cd.inbuf; @@ -179,13 +179,14 @@ RubberBandStretcher::Impl::consumeChannel(size_t c, const float *input = 0; - bool useMidSide = ((m_options & OptionChannelsTogether) && - (m_channels >= 2) && - (c < 2)); + bool useMidSide = + ((m_options & RubberBandStretcher::OptionChannelsTogether) && + (m_channels >= 2) && + (c < 2)); if (resampling) { - Profiler profiler2("RubberBandStretcher::Impl::resample"); + Profiler profiler2("R2Stretcher::resample"); toWrite = int(ceil(samples / m_pitchScale)); if (writable < toWrite) { @@ -204,7 +205,7 @@ RubberBandStretcher::Impl::consumeChannel(size_t c, size_t reqSize = int(ceil(samples / m_pitchScale)); if (reqSize > cd.resamplebufSize) { - cerr << "WARNING: RubberBandStretcher::Impl::consumeChannel: resizing resampler buffer from " + cerr << "WARNING: R2Stretcher::consumeChannel: resizing resampler buffer from " << cd.resamplebufSize << " to " << reqSize << endl; cd.setResampleBufSize(reqSize); } @@ -265,9 +266,9 @@ RubberBandStretcher::Impl::consumeChannel(size_t c, } void -RubberBandStretcher::Impl::processChunks(size_t c, bool &any, bool &last) +R2Stretcher::processChunks(size_t c, bool &any, bool &last) { - Profiler profiler("RubberBandStretcher::Impl::processChunks"); + Profiler profiler("R2Stretcher::processChunks"); // Process as many chunks as there are available on the input // buffer for channel c. This requires that the increments have @@ -338,9 +339,9 @@ RubberBandStretcher::Impl::processChunks(size_t c, bool &any, bool &last) } bool -RubberBandStretcher::Impl::processOneChunk() +R2Stretcher::processOneChunk() { - Profiler profiler("RubberBandStretcher::Impl::processOneChunk"); + Profiler profiler("R2Stretcher::processOneChunk"); // Process a single chunk for all channels, provided there is // enough data on each channel for at least one chunk. This is @@ -381,9 +382,9 @@ RubberBandStretcher::Impl::processOneChunk() } bool -RubberBandStretcher::Impl::testInbufReadSpace(size_t c) +R2Stretcher::testInbufReadSpace(size_t c) { - Profiler profiler("RubberBandStretcher::Impl::testInbufReadSpace"); + Profiler profiler("R2Stretcher::testInbufReadSpace"); ChannelData &cd = *m_channelData[c]; RingBuffer &inbuf = *cd.inbuf; @@ -437,12 +438,12 @@ RubberBandStretcher::Impl::testInbufReadSpace(size_t c) } bool -RubberBandStretcher::Impl::processChunkForChannel(size_t c, +R2Stretcher::processChunkForChannel(size_t c, size_t phaseIncrement, size_t shiftIncrement, bool phaseReset) { - Profiler profiler("RubberBandStretcher::Impl::processChunkForChannel"); + Profiler profiler("R2Stretcher::processChunkForChannel"); // Process a single chunk on a single channel. This assumes // enough input data is available; caller must have tested this @@ -541,11 +542,11 @@ RubberBandStretcher::Impl::processChunkForChannel(size_t c, } void -RubberBandStretcher::Impl::calculateIncrements(size_t &phaseIncrementRtn, +R2Stretcher::calculateIncrements(size_t &phaseIncrementRtn, size_t &shiftIncrementRtn, bool &phaseReset) { - Profiler profiler("RubberBandStretcher::Impl::calculateIncrements"); + Profiler profiler("R2Stretcher::calculateIncrements"); // cerr << "calculateIncrements" << endl; @@ -571,7 +572,7 @@ RubberBandStretcher::Impl::calculateIncrements(size_t &phaseIncrementRtn, size_t bc = cd.chunkCount; for (size_t c = 1; c < m_channels; ++c) { if (m_channelData[c]->chunkCount != bc) { - cerr << "ERROR: RubberBandStretcher::Impl::calculateIncrements: Channels are not in sync" << endl; + cerr << "ERROR: R2Stretcher::calculateIncrements: Channels are not in sync" << endl; return; } } @@ -676,12 +677,12 @@ RubberBandStretcher::Impl::calculateIncrements(size_t &phaseIncrementRtn, } bool -RubberBandStretcher::Impl::getIncrements(size_t channel, +R2Stretcher::getIncrements(size_t channel, size_t &phaseIncrementRtn, size_t &shiftIncrementRtn, bool &phaseReset) { - Profiler profiler("RubberBandStretcher::Impl::getIncrements"); + Profiler profiler("R2Stretcher::getIncrements"); if (channel >= m_channels) { phaseIncrementRtn = m_increment; @@ -710,7 +711,7 @@ RubberBandStretcher::Impl::getIncrements(size_t channel, bool gotData = true; if (cd.chunkCount >= m_outputIncrements.size()) { -// cerr << "WARNING: RubberBandStretcher::Impl::getIncrements:" +// cerr << "WARNING: R2Stretcher::getIncrements:" // << " chunk count " << cd.chunkCount << " >= " // << m_outputIncrements.size() << endl; if (m_outputIncrements.size() == 0) { @@ -741,7 +742,7 @@ RubberBandStretcher::Impl::getIncrements(size_t channel, } /* if (shiftIncrement >= int(m_windowSize)) { - cerr << "*** ERROR: RubberBandStretcher::Impl::processChunks: shiftIncrement " << shiftIncrement << " >= windowSize " << m_windowSize << " at " << cd.chunkCount << " (of " << m_outputIncrements.size() << ")" << endl; + cerr << "*** ERROR: R2Stretcher::processChunks: shiftIncrement " << shiftIncrement << " >= windowSize " << m_windowSize << " at " << cd.chunkCount << " (of " << m_outputIncrements.size() << ")" << endl; shiftIncrement = m_windowSize; } */ @@ -752,9 +753,9 @@ RubberBandStretcher::Impl::getIncrements(size_t channel, } void -RubberBandStretcher::Impl::analyseChunk(size_t channel) +R2Stretcher::analyseChunk(size_t channel) { - Profiler profiler("RubberBandStretcher::Impl::analyseChunk"); + Profiler profiler("R2Stretcher::analyseChunk"); ChannelData &cd = *m_channelData[channel]; @@ -773,11 +774,11 @@ RubberBandStretcher::Impl::analyseChunk(size_t channel) } void -RubberBandStretcher::Impl::modifyChunk(size_t channel, +R2Stretcher::modifyChunk(size_t channel, size_t outputIncrement, bool phaseReset) { - Profiler profiler("RubberBandStretcher::Impl::modifyChunk"); + Profiler profiler("R2Stretcher::modifyChunk"); ChannelData &cd = *m_channelData[channel]; @@ -790,8 +791,8 @@ RubberBandStretcher::Impl::modifyChunk(size_t channel, bool unchanged = cd.unchanged && (outputIncrement == m_increment); bool fullReset = phaseReset; - bool laminar = !(m_options & OptionPhaseIndependent); - bool bandlimited = (m_options & OptionTransientsMixed); + bool laminar = !(m_options & RubberBandStretcher::OptionPhaseIndependent); + bool bandlimited = (m_options & RubberBandStretcher::OptionTransientsMixed); int bandlow = lrint((150 * m_fftSize) / rate); int bandhigh = lrint((1000 * m_fftSize) / rate); @@ -917,9 +918,9 @@ RubberBandStretcher::Impl::modifyChunk(size_t channel, void -RubberBandStretcher::Impl::formantShiftChunk(size_t channel) +R2Stretcher::formantShiftChunk(size_t channel) { - Profiler profiler("RubberBandStretcher::Impl::formantShiftChunk"); + Profiler profiler("R2Stretcher::formantShiftChunk"); ChannelData &cd = *m_channelData[channel]; @@ -977,13 +978,12 @@ RubberBandStretcher::Impl::formantShiftChunk(size_t channel) } void -RubberBandStretcher::Impl::synthesiseChunk(size_t channel, +R2Stretcher::synthesiseChunk(size_t channel, size_t shiftIncrement) { - Profiler profiler("RubberBandStretcher::Impl::synthesiseChunk"); + Profiler profiler("R2Stretcher::synthesiseChunk"); - - if ((m_options & OptionFormantPreserved) && + if ((m_options & RubberBandStretcher::OptionFormantPreserved) && (m_pitchScale != 1.0)) { formantShiftChunk(channel); } @@ -1049,9 +1049,9 @@ RubberBandStretcher::Impl::synthesiseChunk(size_t channel, } void -RubberBandStretcher::Impl::writeChunk(size_t channel, size_t shiftIncrement, bool last) +R2Stretcher::writeChunk(size_t channel, size_t shiftIncrement, bool last) { - Profiler profiler("RubberBandStretcher::Impl::writeChunk"); + Profiler profiler("R2Stretcher::writeChunk"); ChannelData &cd = *m_channelData[channel]; @@ -1077,10 +1077,11 @@ RubberBandStretcher::Impl::writeChunk(size_t channel, size_t shiftIncrement, boo bool resampledAlready = resampleBeforeStretching(); if (!resampledAlready && - (m_pitchScale != 1.0 || m_options & OptionPitchHighConsistency) && + (m_pitchScale != 1.0 || + (m_options & RubberBandStretcher::OptionPitchHighConsistency)) && cd.resampler) { - Profiler profiler2("RubberBandStretcher::Impl::resample"); + Profiler profiler2("R2Stretcher::resample"); size_t reqSize = int(ceil(si / m_pitchScale)); if (reqSize > cd.resamplebufSize) { @@ -1089,7 +1090,7 @@ RubberBandStretcher::Impl::writeChunk(size_t channel, size_t shiftIncrement, boo // first place. But we retain this check in case the // pitch scale has changed since then, or the stretch // calculator has gone mad, or something. - cerr << "WARNING: RubberBandStretcher::Impl::writeChunk: resizing resampler buffer from " + cerr << "WARNING: R2Stretcher::writeChunk: resizing resampler buffer from " << cd.resamplebufSize << " to " << reqSize << endl; cd.setResampleBufSize(reqSize); } @@ -1134,7 +1135,7 @@ RubberBandStretcher::Impl::writeChunk(size_t channel, size_t shiftIncrement, boo cd.accumulatorFill = 0; if (cd.draining) { if (m_debugLevel > 1) { - cerr << "RubberBandStretcher::Impl::processChunks: setting outputComplete to true" << endl; + cerr << "R2Stretcher::processChunks: setting outputComplete to true" << endl; } cd.outputComplete = true; } @@ -1142,9 +1143,9 @@ RubberBandStretcher::Impl::writeChunk(size_t channel, size_t shiftIncrement, boo } void -RubberBandStretcher::Impl::writeOutput(RingBuffer &to, float *from, size_t qty, size_t &outCount, size_t theoreticalOut) +R2Stretcher::writeOutput(RingBuffer &to, float *from, size_t qty, size_t &outCount, size_t theoreticalOut) { - Profiler profiler("RubberBandStretcher::Impl::writeOutput"); + Profiler profiler("R2Stretcher::writeOutput"); // In non-RT mode, we don't want to write the first startSkip // samples, because the first chunk is centred on the start of the @@ -1183,7 +1184,7 @@ RubberBandStretcher::Impl::writeOutput(RingBuffer &to, float *from, size_ size_t written = to.write(from, qty); if (written < qty) { - cerr << "WARNING: RubberBandStretcher::Impl::writeOutput: " + cerr << "WARNING: R2Stretcher::writeOutput: " << "Buffer overrun on output: wrote " << written << " of " << qty << " samples" << endl; } @@ -1216,9 +1217,9 @@ RubberBandStretcher::Impl::writeOutput(RingBuffer &to, float *from, size_ } int -RubberBandStretcher::Impl::available() const +R2Stretcher::available() const { - Profiler profiler("RubberBandStretcher::Impl::available"); + Profiler profiler("R2Stretcher::available"); #ifndef NO_THREADING if (m_threaded) { @@ -1242,7 +1243,7 @@ RubberBandStretcher::Impl::available() const //!!! do we ever actually do this? if so, this method should not be const // ^^^ yes, we do sometimes -- e.g. when fed a very short file bool any = false, last = false; - ((RubberBandStretcher::Impl *)this)->processChunks(c, any, last); + ((R2Stretcher *)this)->processChunks(c, any, last); } } } @@ -1273,9 +1274,9 @@ RubberBandStretcher::Impl::available() const } size_t -RubberBandStretcher::Impl::retrieve(float *const *output, size_t samples) const +R2Stretcher::retrieve(float *const *output, size_t samples) const { - Profiler profiler("RubberBandStretcher::Impl::retrieve"); + Profiler profiler("R2Stretcher::retrieve"); size_t got = samples; @@ -1284,14 +1285,15 @@ RubberBandStretcher::Impl::retrieve(float *const *output, size_t samples) const if (gotHere < got) { if (c > 0) { if (m_debugLevel > 0) { - cerr << "RubberBandStretcher::Impl::retrieve: WARNING: channel imbalance detected" << endl; + cerr << "R2Stretcher::retrieve: WARNING: channel imbalance detected" << endl; } } got = gotHere; } } - if ((m_options & OptionChannelsTogether) && (m_channels >= 2)) { + if ((m_options & RubberBandStretcher::OptionChannelsTogether) && + (m_channels >= 2)) { for (size_t i = 0; i < got; ++i) { float mid = output[0][i]; float side = output[1][i]; diff --git a/src/finer/Guide.h b/src/finer/Guide.h index 2e07c4e..f71148b 100644 --- a/src/finer/Guide.h +++ b/src/finer/Guide.h @@ -124,8 +124,9 @@ public: m_configuration.fftBandLimits[0] = BandLimits(bandFftSize, rate, 0.0, m_maxLower); - // This is the classification and fallback FFT: we need the - // full range for it + // This is the classification and fallback FFT: we need it to + // go up to Nyquist so we can seamlessly switch to it for + // longer stretches bandFftSize = roundUp(int(ceil(rate/32.0))); m_configuration.fftBandLimits[1] = BandLimits(bandFftSize, rate, 0.0, rate / 2.0); diff --git a/src/finer/R3StretcherImpl.cpp b/src/finer/R3Stretcher.cpp similarity index 92% rename from src/finer/R3StretcherImpl.cpp rename to src/finer/R3Stretcher.cpp index e349243..57b8f6a 100644 --- a/src/finer/R3StretcherImpl.cpp +++ b/src/finer/R3Stretcher.cpp @@ -21,7 +21,7 @@ you must obtain a valid commercial licence before doing so. */ -#include "R3StretcherImpl.h" +#include "R3Stretcher.h" #include "../common/VectorOpsComplex.h" @@ -29,9 +29,9 @@ namespace RubberBand { -R3StretcherImpl::R3StretcherImpl(Parameters parameters, - double initialTimeRatio, - double initialPitchScale) : +R3Stretcher::R3Stretcher(Parameters parameters, + double initialTimeRatio, + double initialPitchScale) : m_parameters(parameters), m_timeRatio(initialTimeRatio), m_pitchScale(initialPitchScale), @@ -144,39 +144,39 @@ R3StretcherImpl::R3StretcherImpl(Parameters parameters, } WindowType -R3StretcherImpl::ScaleData::analysisWindowShape(int fftSize) +R3Stretcher::ScaleData::analysisWindowShape(int fftSize) { if (fftSize > 2048) return HannWindow; else return NiemitaloForwardWindow; } int -R3StretcherImpl::ScaleData::analysisWindowLength(int fftSize) +R3Stretcher::ScaleData::analysisWindowLength(int fftSize) { return fftSize; } WindowType -R3StretcherImpl::ScaleData::synthesisWindowShape(int fftSize) +R3Stretcher::ScaleData::synthesisWindowShape(int fftSize) { if (fftSize > 2048) return HannWindow; else return NiemitaloReverseWindow; } int -R3StretcherImpl::ScaleData::synthesisWindowLength(int fftSize) +R3Stretcher::ScaleData::synthesisWindowLength(int fftSize) { if (fftSize > 2048) return fftSize/2; else return fftSize; } void -R3StretcherImpl::setTimeRatio(double ratio) +R3Stretcher::setTimeRatio(double ratio) { if (!isRealTime()) { if (m_mode == ProcessMode::Studying || m_mode == ProcessMode::Processing) { - m_parameters.logger("R3StretcherImpl::setTimeRatio: Cannot set time ratio while studying or processing in non-RT mode"); + m_parameters.logger("R3Stretcher::setTimeRatio: Cannot set time ratio while studying or processing in non-RT mode"); return; } } @@ -187,12 +187,12 @@ R3StretcherImpl::setTimeRatio(double ratio) } void -R3StretcherImpl::setPitchScale(double scale) +R3Stretcher::setPitchScale(double scale) { if (!isRealTime()) { if (m_mode == ProcessMode::Studying || m_mode == ProcessMode::Processing) { - m_parameters.logger("R3StretcherImpl::setTimeRatio: Cannot set pitch scale while studying or processing in non-RT mode"); + m_parameters.logger("R3Stretcher::setTimeRatio: Cannot set pitch scale while studying or processing in non-RT mode"); return; } } @@ -203,12 +203,12 @@ R3StretcherImpl::setPitchScale(double scale) } void -R3StretcherImpl::setFormantScale(double scale) +R3Stretcher::setFormantScale(double scale) { if (!isRealTime()) { if (m_mode == ProcessMode::Studying || m_mode == ProcessMode::Processing) { - m_parameters.logger("R3StretcherImpl::setTimeRatio: Cannot set formant scale while studying or processing in non-RT mode"); + m_parameters.logger("R3Stretcher::setTimeRatio: Cannot set formant scale while studying or processing in non-RT mode"); return; } } @@ -217,7 +217,7 @@ R3StretcherImpl::setFormantScale(double scale) } void -R3StretcherImpl::setFormantOption(RubberBandStretcher::Options options) +R3Stretcher::setFormantOption(RubberBandStretcher::Options options) { int mask = (RubberBandStretcher::OptionFormantShifted | RubberBandStretcher::OptionFormantPreserved); @@ -227,14 +227,14 @@ R3StretcherImpl::setFormantOption(RubberBandStretcher::Options options) } void -R3StretcherImpl::setKeyFrameMap(const std::map &mapping) +R3Stretcher::setKeyFrameMap(const std::map &mapping) { if (isRealTime()) { - m_parameters.logger("R3StretcherImpl::setKeyFrameMap: Cannot specify key frame map in RT mode"); + m_parameters.logger("R3Stretcher::setKeyFrameMap: Cannot specify key frame map in RT mode"); return; } if (m_mode == ProcessMode::Processing || m_mode == ProcessMode::Finished) { - m_parameters.logger("R3StretcherImpl::setKeyFrameMap: Cannot specify key frame map after process() has begun"); + m_parameters.logger("R3Stretcher::setKeyFrameMap: Cannot specify key frame map after process() has begun"); return; } @@ -242,7 +242,7 @@ R3StretcherImpl::setKeyFrameMap(const std::map &mapping) } void -R3StretcherImpl::calculateHop() +R3Stretcher::calculateHop() { double ratio = getEffectiveRatio(); @@ -281,11 +281,11 @@ R3StretcherImpl::calculateHop() m_inhop = int(floor(inhop)); - std::cout << "R3StretcherImpl::calculateHop: inhop = " << m_inhop << ", proposed outhop = " << proposedOuthop << ", mean outhop = " << m_inhop * ratio << std::endl; + std::cout << "R3Stretcher::calculateHop: inhop = " << m_inhop << ", proposed outhop = " << proposedOuthop << ", mean outhop = " << m_inhop * ratio << std::endl; } void -R3StretcherImpl::updateRatioFromMap() +R3Stretcher::updateRatioFromMap() { if (m_keyFrameMap.empty()) return; @@ -344,25 +344,25 @@ R3StretcherImpl::updateRatioFromMap() } double -R3StretcherImpl::getTimeRatio() const +R3Stretcher::getTimeRatio() const { return m_timeRatio; } double -R3StretcherImpl::getPitchScale() const +R3Stretcher::getPitchScale() const { return m_pitchScale; } double -R3StretcherImpl::getFormantScale() const +R3Stretcher::getFormantScale() const { return m_formantScale; } size_t -R3StretcherImpl::getLatency() const +R3Stretcher::getLatency() const { if (!isRealTime()) { return 0; @@ -373,13 +373,13 @@ R3StretcherImpl::getLatency() const } size_t -R3StretcherImpl::getChannelCount() const +R3Stretcher::getChannelCount() const { return m_parameters.channels; } void -R3StretcherImpl::reset() +R3Stretcher::reset() { m_calculator->reset(); m_resampler->reset(); @@ -406,15 +406,15 @@ R3StretcherImpl::reset() } void -R3StretcherImpl::study(const float *const *, size_t samples, bool) +R3Stretcher::study(const float *const *, size_t samples, bool) { if (isRealTime()) { - m_parameters.logger("R3StretcherImpl::study: Not meaningful in realtime mode"); + m_parameters.logger("R3Stretcher::study: Not meaningful in realtime mode"); return; } if (m_mode == ProcessMode::Processing || m_mode == ProcessMode::Finished) { - m_parameters.logger("R3StretcherImpl::study: Cannot study after processing"); + m_parameters.logger("R3Stretcher::study: Cannot study after processing"); return; } @@ -427,7 +427,7 @@ R3StretcherImpl::study(const float *const *, size_t samples, bool) } size_t -R3StretcherImpl::getSamplesRequired() const +R3Stretcher::getSamplesRequired() const { if (available() != 0) return 0; int longest = m_guideConfiguration.longestFftSize; @@ -440,10 +440,10 @@ R3StretcherImpl::getSamplesRequired() const } void -R3StretcherImpl::process(const float *const *input, size_t samples, bool final) +R3Stretcher::process(const float *const *input, size_t samples, bool final) { if (m_mode == ProcessMode::Finished) { - m_parameters.logger("R3StretcherImpl::process: Cannot process again after final chunk"); + m_parameters.logger("R3Stretcher::process: Cannot process again after final chunk"); return; } @@ -468,7 +468,7 @@ R3StretcherImpl::process(const float *const *input, size_t samples, bool final) size_t ws = m_channelData[0]->inbuf->getWriteSpace(); if (samples > ws) { //!!! check this - m_parameters.logger("R3StretcherImpl::process: WARNING: Forced to increase input buffer size. Either setMaxProcessSize was not properly called or process is being called repeatedly without retrieve."); + m_parameters.logger("R3Stretcher::process: WARNING: Forced to increase input buffer size. Either setMaxProcessSize was not properly called or process is being called repeatedly without retrieve."); size_t newSize = m_channelData[0]->inbuf->getSize() - ws + samples; for (int c = 0; c < m_parameters.channels; ++c) { auto newBuf = m_channelData[c]->inbuf->resized(newSize); @@ -486,7 +486,7 @@ R3StretcherImpl::process(const float *const *input, size_t samples, bool final) } int -R3StretcherImpl::available() const +R3Stretcher::available() const { int av = int(m_channelData[0]->outbuf->getReadSpace()); if (av == 0 && m_mode == ProcessMode::Finished) { @@ -497,7 +497,7 @@ R3StretcherImpl::available() const } size_t -R3StretcherImpl::retrieve(float *const *output, size_t samples) const +R3Stretcher::retrieve(float *const *output, size_t samples) const { int got = samples; @@ -505,7 +505,7 @@ R3StretcherImpl::retrieve(float *const *output, size_t samples) const int gotHere = m_channelData[c]->outbuf->read(output[c], got); if (gotHere < got) { if (c > 0) { - m_parameters.logger("R3StretcherImpl::retrieve: WARNING: channel imbalance detected"); + m_parameters.logger("R3Stretcher::retrieve: WARNING: channel imbalance detected"); } got = std::min(got, std::max(gotHere, 0)); } @@ -515,7 +515,7 @@ R3StretcherImpl::retrieve(float *const *output, size_t samples) const } void -R3StretcherImpl::consume() +R3Stretcher::consume() { int longest = m_guideConfiguration.longestFftSize; int channels = m_parameters.channels; @@ -673,7 +673,7 @@ R3StretcherImpl::consume() } void -R3StretcherImpl::analyseChannel(int c, int inhop, int prevInhop, int prevOuthop) +R3Stretcher::analyseChannel(int c, int inhop, int prevInhop, int prevOuthop) { int longest = m_guideConfiguration.longestFftSize; int classify = m_guideConfiguration.classificationFftSize; @@ -908,7 +908,7 @@ R3StretcherImpl::analyseChannel(int c, int inhop, int prevInhop, int prevOuthop) } void -R3StretcherImpl::analyseFormant(int c) +R3Stretcher::analyseFormant(int c) { auto &cd = m_channelData.at(c); auto &f = *cd->formant; @@ -942,7 +942,7 @@ R3StretcherImpl::analyseFormant(int c) } void -R3StretcherImpl::adjustFormant(int c) +R3Stretcher::adjustFormant(int c) { auto &cd = m_channelData.at(c); @@ -976,7 +976,7 @@ R3StretcherImpl::adjustFormant(int c) } void -R3StretcherImpl::adjustPreKick(int c) +R3Stretcher::adjustPreKick(int c) { auto &cd = m_channelData.at(c); auto fftSize = cd->guidance.fftBands[0].fftSize; @@ -1007,7 +1007,7 @@ R3StretcherImpl::adjustPreKick(int c) } void -R3StretcherImpl::synthesiseChannel(int c, int outhop) +R3Stretcher::synthesiseChannel(int c, int outhop) { int longest = m_guideConfiguration.longestFftSize; diff --git a/src/finer/R3StretcherImpl.h b/src/finer/R3Stretcher.h similarity index 98% rename from src/finer/R3StretcherImpl.h rename to src/finer/R3Stretcher.h index bc23d70..6ba2944 100644 --- a/src/finer/R3StretcherImpl.h +++ b/src/finer/R3Stretcher.h @@ -46,7 +46,7 @@ namespace RubberBand { -class R3StretcherImpl +class R3Stretcher { public: struct Parameters { @@ -61,10 +61,10 @@ public: logger(_log) { } }; - R3StretcherImpl(Parameters parameters, - double initialTimeRatio, - double initialPitchScale); - ~R3StretcherImpl() { } + R3Stretcher(Parameters parameters, + double initialTimeRatio, + double initialPitchScale); + ~R3Stretcher() { } void reset();