* Sort out resynthesis gain; add crispness parameter to pitch shifter plugin
This commit is contained in:
@@ -49,6 +49,8 @@ public:
|
|||||||
virtual int calculateSingle(double ratio, size_t inputDurationSoFar,
|
virtual int calculateSingle(double ratio, size_t inputDurationSoFar,
|
||||||
float curveValue);
|
float curveValue);
|
||||||
|
|
||||||
|
void setUseHardPeaks(bool use) { m_useHardPeaks = use; }
|
||||||
|
|
||||||
void reset();
|
void reset();
|
||||||
|
|
||||||
void setDebugLevel(int level) { m_debugLevel = level; }
|
void setDebugLevel(int level) { m_debugLevel = level; }
|
||||||
|
|||||||
@@ -403,7 +403,7 @@ RubberBandStretcher::Impl::calculateSizes()
|
|||||||
//necessary. clearly something wrong in our calculations... or do
|
//necessary. clearly something wrong in our calculations... or do
|
||||||
//we just need to ensure client calls setMaxProcessSize?
|
//we just need to ensure client calls setMaxProcessSize?
|
||||||
if (!m_realtime && !m_threaded) {
|
if (!m_realtime && !m_threaded) {
|
||||||
m_outbufSize = m_outbufSize * 2;
|
m_outbufSize = m_outbufSize * 5;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -616,10 +616,17 @@ RubberBandStretcher::Impl::getLatency() const
|
|||||||
void
|
void
|
||||||
RubberBandStretcher::Impl::setTransientsOption(Options options)
|
RubberBandStretcher::Impl::setTransientsOption(Options options)
|
||||||
{
|
{
|
||||||
|
if (!m_realtime) {
|
||||||
|
cerr << "RubberBandStretcher::Impl::setTransientsOption: Not permissible in non-realtime mode" << endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
m_options &= ~(OptionTransientsMixed |
|
m_options &= ~(OptionTransientsMixed |
|
||||||
OptionTransientsSmooth |
|
OptionTransientsSmooth |
|
||||||
OptionTransientsCrisp);
|
OptionTransientsCrisp);
|
||||||
m_options |= options;
|
m_options |= options;
|
||||||
|
|
||||||
|
m_stretchCalculator->setUseHardPeaks
|
||||||
|
(!(m_options & OptionTransientsSmooth));
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|||||||
@@ -661,7 +661,8 @@ RubberBandStretcher::Impl::synthesiseChunk(size_t channel)
|
|||||||
|
|
||||||
//!!! not much cop, this bit
|
//!!! not much cop, this bit
|
||||||
|
|
||||||
float area = m_window->getArea();
|
float area = m_window->getArea() * 1.5;
|
||||||
|
// float area = 1.f;
|
||||||
|
|
||||||
for (size_t i = 0; i < m_windowSize; ++i) {
|
for (size_t i = 0; i < m_windowSize; ++i) {
|
||||||
float val = m_window->getValue(i);
|
float val = m_window->getValue(i);
|
||||||
|
|||||||
@@ -19,6 +19,8 @@
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
|
||||||
|
namespace RubberBand {
|
||||||
|
|
||||||
enum WindowType {
|
enum WindowType {
|
||||||
RectangularWindow,
|
RectangularWindow,
|
||||||
BartlettWindow,
|
BartlettWindow,
|
||||||
@@ -158,4 +160,6 @@ void Window<T>::cosinewin(T *mult, T a0, T a1, T a2, T a3)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -19,6 +19,8 @@
|
|||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <cmath>
|
#include <cmath>
|
||||||
|
|
||||||
|
using namespace RubberBand;
|
||||||
|
|
||||||
const char *const
|
const char *const
|
||||||
RubberBandPitchShifter::portNamesMono[PortCountMono] =
|
RubberBandPitchShifter::portNamesMono[PortCountMono] =
|
||||||
{
|
{
|
||||||
@@ -26,6 +28,7 @@ RubberBandPitchShifter::portNamesMono[PortCountMono] =
|
|||||||
"Cents",
|
"Cents",
|
||||||
"Semitones",
|
"Semitones",
|
||||||
"Octaves",
|
"Octaves",
|
||||||
|
"Crispness",
|
||||||
"Input",
|
"Input",
|
||||||
"Output"
|
"Output"
|
||||||
};
|
};
|
||||||
@@ -37,6 +40,7 @@ RubberBandPitchShifter::portNamesStereo[PortCountStereo] =
|
|||||||
"Cents",
|
"Cents",
|
||||||
"Semitones",
|
"Semitones",
|
||||||
"Octaves",
|
"Octaves",
|
||||||
|
"Crispness",
|
||||||
"Input L",
|
"Input L",
|
||||||
"Output L",
|
"Output L",
|
||||||
"Input R",
|
"Input R",
|
||||||
@@ -50,6 +54,7 @@ RubberBandPitchShifter::portsMono[PortCountMono] =
|
|||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
||||||
LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO
|
LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO
|
||||||
};
|
};
|
||||||
@@ -61,6 +66,7 @@ RubberBandPitchShifter::portsStereo[PortCountStereo] =
|
|||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
|
LADSPA_PORT_INPUT | LADSPA_PORT_CONTROL,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
||||||
LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO,
|
LADSPA_PORT_OUTPUT | LADSPA_PORT_AUDIO,
|
||||||
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
LADSPA_PORT_INPUT | LADSPA_PORT_AUDIO,
|
||||||
@@ -85,6 +91,11 @@ RubberBandPitchShifter::hintsMono[PortCountMono] =
|
|||||||
LADSPA_HINT_BOUNDED_ABOVE |
|
LADSPA_HINT_BOUNDED_ABOVE |
|
||||||
LADSPA_HINT_INTEGER,
|
LADSPA_HINT_INTEGER,
|
||||||
-4.0, 4.0 },
|
-4.0, 4.0 },
|
||||||
|
{ LADSPA_HINT_DEFAULT_MAXIMUM |
|
||||||
|
LADSPA_HINT_BOUNDED_BELOW |
|
||||||
|
LADSPA_HINT_BOUNDED_ABOVE |
|
||||||
|
LADSPA_HINT_INTEGER,
|
||||||
|
0.0, 3.0 },
|
||||||
{ 0, 0, 0 },
|
{ 0, 0, 0 },
|
||||||
{ 0, 0, 0 }
|
{ 0, 0, 0 }
|
||||||
};
|
};
|
||||||
@@ -107,6 +118,11 @@ RubberBandPitchShifter::hintsStereo[PortCountStereo] =
|
|||||||
LADSPA_HINT_BOUNDED_ABOVE |
|
LADSPA_HINT_BOUNDED_ABOVE |
|
||||||
LADSPA_HINT_INTEGER,
|
LADSPA_HINT_INTEGER,
|
||||||
-4.0, 4.0 },
|
-4.0, 4.0 },
|
||||||
|
{ LADSPA_HINT_DEFAULT_MAXIMUM |
|
||||||
|
LADSPA_HINT_BOUNDED_BELOW |
|
||||||
|
LADSPA_HINT_BOUNDED_ABOVE |
|
||||||
|
LADSPA_HINT_INTEGER,
|
||||||
|
0.0, 3.0 },
|
||||||
{ 0, 0, 0 },
|
{ 0, 0, 0 },
|
||||||
{ 0, 0, 0 },
|
{ 0, 0, 0 },
|
||||||
{ 0, 0, 0 },
|
{ 0, 0, 0 },
|
||||||
@@ -167,7 +183,6 @@ RubberBandPitchShifter::ladspaDescriptorStereo =
|
|||||||
const LADSPA_Descriptor *
|
const LADSPA_Descriptor *
|
||||||
RubberBandPitchShifter::getDescriptor(unsigned long index)
|
RubberBandPitchShifter::getDescriptor(unsigned long index)
|
||||||
{
|
{
|
||||||
// std::cerr << "RubberBandPitchShifter::getDescriptor(" << index << ")" << std::endl;
|
|
||||||
if (index == 0) return &ladspaDescriptorMono;
|
if (index == 0) return &ladspaDescriptorMono;
|
||||||
if (index == 1) return &ladspaDescriptorStereo;
|
if (index == 1) return &ladspaDescriptorStereo;
|
||||||
else return 0;
|
else return 0;
|
||||||
@@ -178,27 +193,22 @@ RubberBandPitchShifter::RubberBandPitchShifter(int sampleRate, size_t channels)
|
|||||||
m_cents(0),
|
m_cents(0),
|
||||||
m_semitones(0),
|
m_semitones(0),
|
||||||
m_octaves(0),
|
m_octaves(0),
|
||||||
|
m_crispness(0),
|
||||||
m_ratio(1.0),
|
m_ratio(1.0),
|
||||||
m_prevRatio(1.0),
|
m_prevRatio(1.0),
|
||||||
|
m_currentCrispness(-1),
|
||||||
m_extraLatency(8192), //!!! this should be at least the maximum possible displacement from linear at input rates, divided by the pitch scale factor. It could be very large
|
m_extraLatency(8192), //!!! this should be at least the maximum possible displacement from linear at input rates, divided by the pitch scale factor. It could be very large
|
||||||
m_stretcher(new RubberBand::RubberBandStretcher
|
m_stretcher(new RubberBandStretcher
|
||||||
(sampleRate, channels,
|
(sampleRate, channels,
|
||||||
RubberBand::RubberBandStretcher::OptionProcessRealTime)),// |
|
RubberBandStretcher::OptionProcessRealTime)),
|
||||||
// RubberBand::RubberBandStretcher::OptionStretchPrecise |
|
|
||||||
// RubberBand::RubberBandStretcher::OptionTransientsSmooth |
|
|
||||||
// RubberBand::RubberBandStretcher::OptionTransientsCrisp |
|
|
||||||
// RubberBand::RubberBandStretcher::OptionPhasePeakLocked |
|
|
||||||
// RubberBand::RubberBandStretcher::OptionThreadingNone)),
|
|
||||||
m_sampleRate(sampleRate),
|
m_sampleRate(sampleRate),
|
||||||
m_channels(channels)
|
m_channels(channels)
|
||||||
{
|
{
|
||||||
// m_stretcher->setMaxProcessBlockSize(4096);
|
|
||||||
|
|
||||||
for (size_t c = 0; c < m_channels; ++c) {
|
for (size_t c = 0; c < m_channels; ++c) {
|
||||||
m_input[c] = 0;
|
m_input[c] = 0;
|
||||||
m_output[c] = 0;
|
m_output[c] = 0;
|
||||||
//!!! size must be at least max process size plus m_extraLatency:
|
//!!! size must be at least max process size plus m_extraLatency:
|
||||||
m_outputBuffer[c] = new RubberBand::RingBuffer<float>(8092); //!!!
|
m_outputBuffer[c] = new RingBuffer<float>(8092); //!!!
|
||||||
m_outputBuffer[c]->zero(m_extraLatency);
|
m_outputBuffer[c]->zero(m_extraLatency);
|
||||||
//!!! size must be at least max process size:
|
//!!! size must be at least max process size:
|
||||||
m_scratch[c] = new float[16384];//!!!
|
m_scratch[c] = new float[16384];//!!!
|
||||||
@@ -236,6 +246,7 @@ RubberBandPitchShifter::connectPort(LADSPA_Handle handle,
|
|||||||
&shifter->m_cents,
|
&shifter->m_cents,
|
||||||
&shifter->m_semitones,
|
&shifter->m_semitones,
|
||||||
&shifter->m_octaves,
|
&shifter->m_octaves,
|
||||||
|
&shifter->m_crispness,
|
||||||
&shifter->m_input[0],
|
&shifter->m_input[0],
|
||||||
&shifter->m_output[0],
|
&shifter->m_output[0],
|
||||||
&shifter->m_input[1],
|
&shifter->m_input[1],
|
||||||
@@ -249,8 +260,6 @@ void
|
|||||||
RubberBandPitchShifter::activate(LADSPA_Handle handle)
|
RubberBandPitchShifter::activate(LADSPA_Handle handle)
|
||||||
{
|
{
|
||||||
RubberBandPitchShifter *shifter = (RubberBandPitchShifter *)handle;
|
RubberBandPitchShifter *shifter = (RubberBandPitchShifter *)handle;
|
||||||
//!!! QMutexLocker locker(&shifter->m_mutex);
|
|
||||||
|
|
||||||
shifter->updateRatio();
|
shifter->updateRatio();
|
||||||
shifter->m_prevRatio = shifter->m_ratio;
|
shifter->m_prevRatio = shifter->m_ratio;
|
||||||
shifter->m_stretcher->reset();
|
shifter->m_stretcher->reset();
|
||||||
@@ -273,6 +282,38 @@ RubberBandPitchShifter::updateRatio()
|
|||||||
m_ratio = pow(2.0, oct);
|
m_ratio = pow(2.0, oct);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
RubberBandPitchShifter::updateCrispness()
|
||||||
|
{
|
||||||
|
if (!m_crispness) return;
|
||||||
|
|
||||||
|
int c = lrintf(*m_crispness);
|
||||||
|
if (c == m_currentCrispness) return;
|
||||||
|
if (c < 0 || c > 3) return;
|
||||||
|
RubberBandStretcher *s = m_stretcher;
|
||||||
|
|
||||||
|
switch (c) {
|
||||||
|
case 0:
|
||||||
|
s->setPhaseOption(RubberBandStretcher::OptionPhaseIndependent);
|
||||||
|
s->setTransientsOption(RubberBandStretcher::OptionTransientsSmooth);
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
s->setPhaseOption(RubberBandStretcher::OptionPhaseAdaptive);
|
||||||
|
s->setTransientsOption(RubberBandStretcher::OptionTransientsSmooth);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
s->setPhaseOption(RubberBandStretcher::OptionPhaseAdaptive);
|
||||||
|
s->setTransientsOption(RubberBandStretcher::OptionTransientsMixed);
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
s->setPhaseOption(RubberBandStretcher::OptionPhaseAdaptive);
|
||||||
|
s->setTransientsOption(RubberBandStretcher::OptionTransientsCrisp);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_currentCrispness = c;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
RubberBandPitchShifter::runImpl(unsigned long insamples)
|
RubberBandPitchShifter::runImpl(unsigned long insamples)
|
||||||
{
|
{
|
||||||
@@ -289,6 +330,8 @@ RubberBandPitchShifter::runImpl(unsigned long insamples)
|
|||||||
// std::cerr << "latency = " << *m_latency << std::endl;
|
// std::cerr << "latency = " << *m_latency << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
updateCrispness();
|
||||||
|
|
||||||
int samples = insamples;
|
int samples = insamples;
|
||||||
int processed = 0;
|
int processed = 0;
|
||||||
size_t outTotal = 0;
|
size_t outTotal = 0;
|
||||||
|
|||||||
@@ -37,12 +37,13 @@ protected:
|
|||||||
OctavesPort = 1,
|
OctavesPort = 1,
|
||||||
SemitonesPort = 2,
|
SemitonesPort = 2,
|
||||||
CentsPort = 3,
|
CentsPort = 3,
|
||||||
InputPort1 = 4,
|
CrispnessPort = 4,
|
||||||
OutputPort1 = 5,
|
InputPort1 = 5,
|
||||||
PortCountMono = 6,
|
OutputPort1 = 6,
|
||||||
InputPort2 = 6,
|
PortCountMono = OutputPort1 + 1,
|
||||||
OutputPort2 = 7,
|
InputPort2 = 7,
|
||||||
PortCountStereo = 8
|
OutputPort2 = 8,
|
||||||
|
PortCountStereo = OutputPort2 + 1
|
||||||
};
|
};
|
||||||
|
|
||||||
static const char *const portNamesMono[PortCountMono];
|
static const char *const portNamesMono[PortCountMono];
|
||||||
@@ -67,6 +68,7 @@ protected:
|
|||||||
|
|
||||||
void runImpl(unsigned long);
|
void runImpl(unsigned long);
|
||||||
void updateRatio();
|
void updateRatio();
|
||||||
|
void updateCrispness();
|
||||||
|
|
||||||
float *m_input[2];
|
float *m_input[2];
|
||||||
float *m_output[2];
|
float *m_output[2];
|
||||||
@@ -74,8 +76,10 @@ protected:
|
|||||||
float *m_cents;
|
float *m_cents;
|
||||||
float *m_semitones;
|
float *m_semitones;
|
||||||
float *m_octaves;
|
float *m_octaves;
|
||||||
|
float *m_crispness;
|
||||||
double m_ratio;
|
double m_ratio;
|
||||||
double m_prevRatio;
|
double m_prevRatio;
|
||||||
|
int m_currentCrispness;
|
||||||
|
|
||||||
size_t m_extraLatency;
|
size_t m_extraLatency;
|
||||||
|
|
||||||
|
|||||||
@@ -341,7 +341,6 @@ int main(int argc, char **argv)
|
|||||||
float value = obf[c][i];
|
float value = obf[c][i];
|
||||||
if (fabsf(value) > outpeak) outpeak = fabsf(value);
|
if (fabsf(value) > outpeak) outpeak = fabsf(value);
|
||||||
outsum += value * value;
|
outsum += value * value;
|
||||||
value *= 0.75;
|
|
||||||
if (value > 1.f) value = 1.f;
|
if (value > 1.f) value = 1.f;
|
||||||
if (value < -1.f) value = -1.f;
|
if (value < -1.f) value = -1.f;
|
||||||
fobf[i * channels + c] = value;
|
fobf[i * channels + c] = value;
|
||||||
@@ -401,7 +400,6 @@ int main(int argc, char **argv)
|
|||||||
float value = obf[c][i];
|
float value = obf[c][i];
|
||||||
if (fabsf(value) > outpeak) outpeak = fabsf(value);
|
if (fabsf(value) > outpeak) outpeak = fabsf(value);
|
||||||
outsum += value * value;
|
outsum += value * value;
|
||||||
value *= 0.75;//!!!
|
|
||||||
if (value > 1.f) value = 1.f;
|
if (value > 1.f) value = 1.f;
|
||||||
if (value < -1.f) value = -1.f;
|
if (value < -1.f) value = -1.f;
|
||||||
fobf[i * channels + c] = value;
|
fobf[i * channels + c] = value;
|
||||||
|
|||||||
Reference in New Issue
Block a user