From 4fb79f858ad4f10690ebdf3e59d6d775607b0f21 Mon Sep 17 00:00:00 2001 From: abscisys Date: Thu, 5 Jan 2023 01:34:31 +0100 Subject: [PATCH] Fixing the Phaser --- src/fx_phaser.cpp | 150 +++++++++++++++++++------------------- src/fx_phaser.h | 67 ++++++++--------- src/minidexed.cpp | 30 ++++++-- src/minidexed.h | 4 +- src/performance.ini | 4 +- src/performanceconfig.cpp | 36 +++++++-- src/performanceconfig.h | 12 ++- src/test/fxrack_test.cpp | 8 +- src/uimenu.cpp | 8 +- 9 files changed, 182 insertions(+), 137 deletions(-) diff --git a/src/fx_phaser.cpp b/src/fx_phaser.cpp index ad133ed..2afb5d8 100644 --- a/src/fx_phaser.cpp +++ b/src/fx_phaser.cpp @@ -1,129 +1,125 @@ #include "fx_phaser.h" +#include #include -PhaserParameter::PhaserParameter(float32_t sampling_rate, float32_t frequency, float32_t resonance) : - FXBase(sampling_rate), - frequency_(frequency), - resonance_(resonance) +AllpassDelay::AllpassDelay() : + a1_(0.0f) { - this->computeCoefficients(); + memset(this->z_, 0, 2 * sizeof(float32_t)); } -PhaserParameter::~PhaserParameter() +AllpassDelay::~AllpassDelay() { } -void PhaserParameter::computeCoefficients() +void AllpassDelay::processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) { - float32_t w0 = 2.0f * PI * this->getFrequency() / this->getSamplingRate(); - float32_t alpha = sin(w0) / (2.0f * this->resonance_); - this->a0 = 1.0f + alpha; - this->a1 = -2.0f * cos(w0); - this->a2 = 1.0f - alpha; - this->b1 = this->a1; - this->b2 = this->a2; + outL = inL * -this->a1_ + this->z_[0]; + this->z_[0] = outL * this->a1_ + inL; + + outR = inR * -this->a1_ + this->z_[1]; + this->z_[1] = outR * this->a1_ + inR; } -void PhaserParameter::setFrequency(float32_t frequency) +void AllpassDelay::setDelay(float32_t delay) { - this->frequency_ = frequency; - this->computeCoefficients(); + this->a1_ = (1.0f - delay) / (1.0f + delay); } -float32_t PhaserParameter::getFrequency() const + +Phaser::Phaser(float32_t sampling_rate, float32_t rate, float32_t depth, float32_t feedback) : + FXElement(sampling_rate), + lfo_(sampling_rate, LFO::Waveform::Sine, 0.0f, 2.5f), + depth_(0.0f), + feedback_(0.0f), + dmin_(0.0f), + dmax_(0.0f) { - return this->frequency_; + this->setRate(rate); + this->setDepth(depth); + this->setFeedback(feedback); + this->setFrequencyRange(440.0f, 1600.0f); + + memset(this->z_, 0, 2 * sizeof(float32_t)); } -void PhaserParameter::setResonance(float32_t resonance) +Phaser::~Phaser() { - this->resonance_ = constrain(resonance, 0.5f, 10.0f); - this->computeCoefficients(); } -float32_t PhaserParameter::getResonance() const +void Phaser::processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) { - return this->resonance_; -} + float32_t d = this->dmin_ + (this->dmax_ - this->dmin_) * ((1.0f + this->lfo_.process()) / 2.0f); + float32_t sampleL = inL + this->feedback_ * this->z_[0]; + float32_t sampleR = inR + this->feedback_ * this->z_[1]; + for(unsigned i = 0; i < this->nb_stages_; ++i) + { + this->stages_[i].setDelay(d); + this->stages_[i].processSample(sampleL, sampleR, sampleL, sampleR); + } + this->z_[0] = sampleL; + this->z_[1] = sampleR; -// PhaserStage implementation -PhaserStage::PhaserStage(float32_t sampling_rate, PhaserParameter* params) : - FXElement(sampling_rate), - params_(params) -{ - memset(this->z1, 0, 2 * sizeof(float32_t)); - memset(this->z2, 0, 2 * sizeof(float32_t)); + outL = inL + this->z_[0] * this->depth_; + outR = inR + this->z_[1] * this->depth_; } -void PhaserStage::processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) +void Phaser::setFrequencyRange(float32_t min_frequency, float32_t max_frequency) { - outL = (this->params_->a0 * inL + this->params_->a1 * this->z1[0] + this->params_->a2 * this->z2[0]) / this->params_->a0; - this->z2[0] = this->z1[0]; - this->z2[0] = inL; - - outR = (this->params_->a0 * inR + this->params_->a1 * this->z1[1] + this->params_->a2 * this->z2[1]) / this->params_->a0; - this->z2[1] = this->z1[1]; - this->z2[1] = inR; + this->dmin_ = 2.0f * std::min(min_frequency, max_frequency) / this->getSamplingRate(); + this->dmax_ = 2.0f * std::max(min_frequency, max_frequency) / this->getSamplingRate(); } - - -// Phaser implementation -Phaser::Phaser(float32_t sampling_rate, float32_t frequency, float32_t q) : - FXElement(sampling_rate), - params_(sampling_rate, frequency, q), - lfo_(sampling_rate, LFO::Waveform::Sine, 0.01f, 1.0f) +void Phaser::setRate(float32_t rate) { - for(unsigned i = 0; i < NUM_PHASER_STAGES; ++i) - { - this->stages_[i] = new PhaserStage(sampling_rate, &this->params_); - } + rate = constrain(rate, 0.0f, 1.0f); + this->lfo_.setNormalizedFrequency(rate); } -Phaser::~Phaser() +inline float32_t Phaser::getRate() const { - for(unsigned i = 0; i < NUM_PHASER_STAGES; ++i) - { - delete this->stages_[i]; - } + return this->lfo_.getNormalizedFrequency(); } -void Phaser::processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) +void Phaser::setDepth(float32_t depth) { - // Process the input sample through each stage of the phaser - float32_t sampleL = inL; - float32_t sampleR = inR; - for(unsigned s = 0; s < NUM_PHASER_STAGES; ++s) - { - this->stages_[s]->processSample(sampleL, sampleR, sampleL, sampleR); - } + depth = constrain(depth, 0.0f, 1.0f); + this->depth_ = depth; +} - // Modulate the output of the phaser using the LFO - float32_t lfo = this->lfo_.process(); - outR = sampleR * (0.5f + 0.5f * lfo); - outL = sampleL * (0.5f + 0.5f * lfo); +inline float32_t Phaser::getDepth() const +{ + return this->depth_; } -void Phaser::setFrequency(float32_t frequency) +void Phaser::setFeedback(float32_t feedback) { - this->lfo_.setNormalizedFrequency(frequency); - this->params_.setFrequency(this->lfo_.getFrequency()); + feedback = constrain(feedback, 0.0f, 0.97f); + this->feedback_ = feedback; } -inline float32_t Phaser::getFrequency() const +inline float32_t Phaser::getFeedback() const { - return this->lfo_.getNormalizedFrequency(); + return this->feedback_; } -void Phaser::setResonance(float32_t q) +void Phaser::setNbStages(unsigned nb_stages) { - this->params_.setResonance(q); + if(nb_stages < 2) + { + nb_stages = 2; + } + else if(nb_stages > MAX_NB_PHASES) + { + nb_stages = MAX_NB_PHASES; + } + this->nb_stages_ = nb_stages; } -inline float32_t Phaser::getResonance() const +unsigned Phaser::getNbStages() const { - return this->params_.getResonance(); + return this->nb_stages_; } diff --git a/src/fx_phaser.h b/src/fx_phaser.h index 735bcf9..fa6390c 100644 --- a/src/fx_phaser.h +++ b/src/fx_phaser.h @@ -20,66 +20,57 @@ #include "fx_components.h" -class PhaserStage; - -class PhaserParameter : public FXBase +class AllpassDelay { - friend class PhaserStage; - DISALLOW_COPY_AND_ASSIGN(PhaserParameter); + DISALLOW_COPY_AND_ASSIGN(AllpassDelay); public: - PhaserParameter(float32_t sampling_rate, float32_t frequency = 0.5f, float32_t q = 1.0f); - virtual ~PhaserParameter(); + AllpassDelay(); + virtual ~AllpassDelay(); - void setFrequency(float32_t frequency); - inline float32_t getFrequency() const; + virtual void processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR); - void setResonance(float32_t q); - inline float32_t getResonance() const; + void setDelay(float32_t delay); private: - void computeCoefficients(); - - float32_t frequency_; // LFO frequency in Hz (0.01 - 5.0) - float32_t resonance_; // Resonance factor for the filters (0.5 - 10.0) - - float32_t a0, a1, a2, b1, b2; // Coefficients for the stage's filter + float32_t a1_; + float32_t z_[2]; }; -class PhaserStage : public FXElement -{ - DISALLOW_COPY_AND_ASSIGN(PhaserStage); - -public: - PhaserStage(float32_t sampling_rate, PhaserParameter* params); - - virtual void processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) override; - -private: - PhaserParameter* params_; // All paremters of the phaser including the inner coefficients - float32_t z1[2], z2[2]; // State variables for the stage's filter -}; -#define NUM_PHASER_STAGES 6 +#define MAX_NB_PHASES 24 class Phaser : public FXElement { DISALLOW_COPY_AND_ASSIGN(Phaser); public: - Phaser(float32_t sampling_rate, float32_t frequency = 0.5f, float32_t resonance = 1.0f); + Phaser(float32_t sampling_rate, float32_t rate = 0.5f, float32_t depth = 1.0f, float32_t feedback = 0.7f); virtual ~Phaser(); virtual void processSample(float32_t inL, float32_t inR, float32_t& outL, float32_t& outR) override; - void setFrequency(float32_t frequency); - float32_t getFrequency() const; + void setFrequencyRange(float32_t min_frequency, float32_t max_frequency); + + void setRate(float32_t rate); + float32_t getRate() const; + + void setDepth(float32_t depth); + float32_t getDepth() const; + + void setFeedback(float32_t depth); + float32_t getFeedback() const; - void setResonance(float32_t resonance); - float32_t getResonance() const; + void setNbStages(unsigned nb_stages); + unsigned getNbStages() const; private: - PhaserParameter params_; LFO lfo_; - PhaserStage* stages_[NUM_PHASER_STAGES]; + float32_t depth_; + float32_t feedback_; + float32_t dmin_; + float32_t dmax_; + unsigned nb_stages_; + AllpassDelay stages_[MAX_NB_PHASES]; + float32_t z_[2]; }; \ No newline at end of file diff --git a/src/minidexed.cpp b/src/minidexed.cpp index 1cab8dc..fc07eec 100644 --- a/src/minidexed.cpp +++ b/src/minidexed.cpp @@ -195,7 +195,7 @@ CMiniDexed::CMiniDexed (CConfig *pConfig, CInterruptSystem *pInterrupt, this->SetParameter(ParameterFXChainPhaserEnable, 1); this->SetParameter(ParameterFXChainPhaserWet, 50); this->SetParameter(ParameterFXChainPhaserRate, 5); - this->SetParameter(ParameterFXChainPhaserResonance, 45); + this->SetParameter(ParameterFXChainPhaserDepth, 45); // FXChain > Delay parameters this->SetParameter(ParameterFXChainDelayEnable, 1); @@ -883,16 +883,28 @@ void CMiniDexed::SetParameter (TParameter Parameter, int nValue) case ParameterFXChainPhaserRate: nValue = constrain((int)nValue, 0, 99); this->m_FXSpinLock.Acquire(); - this->fx_rack->getPhaser()->setFrequency(nValue / 99.0f); + this->fx_rack->getPhaser()->setRate(nValue / 99.0f); this->m_FXSpinLock.Release(); break; - case ParameterFXChainPhaserResonance: + case ParameterFXChainPhaserDepth: nValue = constrain((int)nValue, 0, 99); this->m_FXSpinLock.Acquire(); - this->fx_rack->getPhaser()->setResonance(mapfloat(nValue, 0, 99, 0.5f, 10.0f)); + this->fx_rack->getPhaser()->setDepth(nValue / 99.0f); this->m_FXSpinLock.Release(); break; - + case ParameterFXChainPhaserFeedback: + nValue = constrain((int)nValue, 0, 99); + this->m_FXSpinLock.Acquire(); + this->fx_rack->getPhaser()->setFeedback(mapfloat(nValue, 0, 99, 0.0f, 0.97f)); + this->m_FXSpinLock.Release(); + break; + case ParameterFXChainPhaserNbStages: + nValue = constrain((int)nValue, 2, MAX_NB_PHASES); + this->m_FXSpinLock.Acquire(); + this->fx_rack->getPhaser()->setNbStages(nValue); + this->m_FXSpinLock.Release(); + break; + // FXChain > Delay parameters case ParameterFXChainDelayEnable: nValue = constrain((int)nValue, 0, 1); @@ -1406,7 +1418,9 @@ bool CMiniDexed::DoSavePerformance (void) this->m_PerformanceConfig.SetFXChainPhaserEnable(!!this->m_nParameter[ParameterFXChainPhaserEnable]); this->m_PerformanceConfig.SetFXChainPhaserWet(this->m_nParameter[ParameterFXChainPhaserWet]); this->m_PerformanceConfig.SetFXChainPhaserRate(this->m_nParameter[ParameterFXChainPhaserRate]); - this->m_PerformanceConfig.SetFXChainPhaserResonance(this->m_nParameter[ParameterFXChainPhaserResonance]); + this->m_PerformanceConfig.SetFXChainPhaserDepth(this->m_nParameter[ParameterFXChainPhaserDepth]); + this->m_PerformanceConfig.SetFXChainPhaserFeedback(this->m_nParameter[ParameterFXChainPhaserFeedback]); + this->m_PerformanceConfig.SetFXChainPhaserNbStages(this->m_nParameter[ParameterFXChainPhaserNbStages]); this->m_PerformanceConfig.SetFXChainDelayEnable(!!this->m_nParameter[ParameterFXChainDelayEnable]); this->m_PerformanceConfig.SetFXChainDelayWet(this->m_nParameter[ParameterFXChainDelayWet]); this->m_PerformanceConfig.SetFXChainDelayLeftDelayTime(this->m_nParameter[ParameterFXChainDelayLeftDelayTime]); @@ -1833,7 +1847,9 @@ void CMiniDexed::LoadPerformanceParameters(void) this->SetParameter(ParameterFXChainPhaserEnable, this->m_PerformanceConfig.GetFXChainPhaserEnable()); this->SetParameter(ParameterFXChainPhaserWet, this->m_PerformanceConfig.GetFXChainPhaserWet()); this->SetParameter(ParameterFXChainPhaserRate, this->m_PerformanceConfig.GetFXChainPhaserRate()); - this->SetParameter(ParameterFXChainPhaserResonance, this->m_PerformanceConfig.GetFXChainPhaserResonance()); + this->SetParameter(ParameterFXChainPhaserDepth, this->m_PerformanceConfig.GetFXChainPhaserDepth()); + this->SetParameter(ParameterFXChainPhaserFeedback, this->m_PerformanceConfig.GetFXChainPhaserFeedback()); + this->SetParameter(ParameterFXChainPhaserNbStages, this->m_PerformanceConfig.GetFXChainPhaserNbStages()); this->SetParameter(ParameterFXChainDelayEnable, this->m_PerformanceConfig.GetFXChainDelayEnable()); this->SetParameter(ParameterFXChainDelayWet, this->m_PerformanceConfig.GetFXChainDelayWet()); this->SetParameter(ParameterFXChainDelayLeftDelayTime, this->m_PerformanceConfig.GetFXChainDelayLeftDelayTime()); diff --git a/src/minidexed.h b/src/minidexed.h index 8d7aecc..728d69a 100644 --- a/src/minidexed.h +++ b/src/minidexed.h @@ -175,7 +175,9 @@ public: ParameterFXChainPhaserEnable, ParameterFXChainPhaserWet, ParameterFXChainPhaserRate, - ParameterFXChainPhaserResonance, + ParameterFXChainPhaserDepth, + ParameterFXChainPhaserFeedback, + ParameterFXChainPhaserNbStages, // FXChain > Delay parameters ParameterFXChainDelayEnable, diff --git a/src/performance.ini b/src/performance.ini index a36379c..332874f 100644 --- a/src/performance.ini +++ b/src/performance.ini @@ -306,7 +306,9 @@ FXChainOrbitoneDepth=50 FXChainPhaserEnable=0 FXChainPhaserWet=50 FXChainPhaserRate=5 -FXChainPhaserResonance=45 +FXChainPhaserDepth=99 +FXChainPhaserFeedback=70 +FXChainPhaserNbStages=12 FXChainDelayEnable=0 FXChainDelayWet=50 FXChainDelayLeftDelayTime=15 diff --git a/src/performanceconfig.cpp b/src/performanceconfig.cpp index a39b7a6..dc17b19 100644 --- a/src/performanceconfig.cpp +++ b/src/performanceconfig.cpp @@ -182,7 +182,9 @@ bool CPerformanceConfig::Load (void) this->m_bFXChainPhaserEnable = this->m_Properties.GetNumber("FXChainPhaserEnable", 1); this->m_nFXChainPhaserWet = this->m_Properties.GetNumber("FXChainPhaserWet", 50); this->m_nFXChainPhaserRate = this->m_Properties.GetNumber("FXChainPhaserRate", 5); - this->m_nFXChainPhaserResonance = this->m_Properties.GetNumber("FXChainPhaserResonance", 45); + this->m_nFXChainPhaserDepth = this->m_Properties.GetNumber("FXChainPhaserDepth", 99); + this->m_nFXChainPhaserFeedback = this->m_Properties.GetNumber("FXChainPhaserFeedback", 50); + this->m_nFXChainPhaserNbStages = this->m_Properties.GetNumber("FXChainPhaserNbStages", 12); this->m_bFXChainDelayEnable = this->m_Properties.GetNumber("FXChainDelayEnable", 1); this->m_nFXChainDelayWet = this->m_Properties.GetNumber("FXChainDelayWet", 50); this->m_nFXChainDelayLeftDelayTime = this->m_Properties.GetNumber("FXChainDelayLeftDelayTime", 15); @@ -337,7 +339,9 @@ bool CPerformanceConfig::Save (void) this->m_Properties.SetNumber("FXChainPhaserEnable", m_bFXChainPhaserEnable ? 1 : 0); this->m_Properties.SetNumber("FXChainPhaserWet", m_nFXChainPhaserWet); this->m_Properties.SetNumber("FXChainPhaserRate", m_nFXChainPhaserRate); - this->m_Properties.SetNumber("FXChainPhaserResonance", m_nFXChainPhaserResonance); + this->m_Properties.SetNumber("FXChainPhaserDepth", m_nFXChainPhaserDepth); + this->m_Properties.SetNumber("FXChainPhaserFeedback", m_nFXChainPhaserFeedback); + this->m_Properties.SetNumber("FXChainPhaserNbStages", m_nFXChainPhaserNbStages); this->m_Properties.SetNumber("FXChainDelayEnable", m_bFXChainDelayEnable ? 1 : 0); this->m_Properties.SetNumber("FXChainDelayWet", m_nFXChainDelayWet); this->m_Properties.SetNumber("FXChainDelayLeftDelayTime", m_nFXChainDelayLeftDelayTime); @@ -1109,9 +1113,19 @@ unsigned CPerformanceConfig::GetFXChainPhaserRate(void) const return this->m_nFXChainPhaserRate; } -unsigned CPerformanceConfig::GetFXChainPhaserResonance(void) const +unsigned CPerformanceConfig::GetFXChainPhaserDepth(void) const { - return this->m_nFXChainPhaserResonance; + return this->m_nFXChainPhaserDepth; +} + +unsigned CPerformanceConfig::GetFXChainPhaserFeedback(void) const +{ + return this->m_nFXChainPhaserFeedback; +} + +unsigned CPerformanceConfig::GetFXChainPhaserNbStages(void) const +{ + return this->m_nFXChainPhaserNbStages; } bool CPerformanceConfig::GetFXChainDelayEnable(void) const @@ -1279,9 +1293,19 @@ void CPerformanceConfig::SetFXChainPhaserRate(unsigned nValue) this->m_nFXChainPhaserRate = nValue; } -void CPerformanceConfig::SetFXChainPhaserResonance(unsigned nValue) +void CPerformanceConfig::SetFXChainPhaserDepth(unsigned nValue) +{ + this->m_nFXChainPhaserDepth = nValue; +} + +void CPerformanceConfig::SetFXChainPhaserFeedback(unsigned nValue) +{ + this->m_nFXChainPhaserFeedback = nValue; +} + +void CPerformanceConfig::SetFXChainPhaserNbStages(unsigned nValue) { - this->m_nFXChainPhaserResonance = nValue; + this->m_nFXChainPhaserNbStages = nValue; } void CPerformanceConfig::SetFXChainDelayEnable(unsigned bValue) diff --git a/src/performanceconfig.h b/src/performanceconfig.h index 96dc72f..6ec286f 100644 --- a/src/performanceconfig.h +++ b/src/performanceconfig.h @@ -140,7 +140,9 @@ public: bool GetFXChainPhaserEnable(void) const; unsigned GetFXChainPhaserWet(void) const; unsigned GetFXChainPhaserRate(void) const; - unsigned GetFXChainPhaserResonance(void) const; + unsigned GetFXChainPhaserDepth(void) const; + unsigned GetFXChainPhaserFeedback(void) const; + unsigned GetFXChainPhaserNbStages(void) const; bool GetFXChainDelayEnable(void) const; unsigned GetFXChainDelayWet(void) const; unsigned GetFXChainDelayLeftDelayTime(void) const; @@ -175,7 +177,9 @@ public: void SetFXChainPhaserEnable(bool bValue); void SetFXChainPhaserWet(unsigned nValue); void SetFXChainPhaserRate(unsigned nValue); - void SetFXChainPhaserResonance(unsigned nValue); + void SetFXChainPhaserDepth(unsigned nValue); + void SetFXChainPhaserFeedback(unsigned nValue); + void SetFXChainPhaserNbStages(unsigned nValue); void SetFXChainDelayEnable(unsigned nValue); void SetFXChainDelayWet(unsigned nValue); void SetFXChainDelayLeftDelayTime(unsigned nValue); @@ -279,7 +283,9 @@ private: bool m_bFXChainPhaserEnable; unsigned m_nFXChainPhaserWet; unsigned m_nFXChainPhaserRate; - unsigned m_nFXChainPhaserResonance; + unsigned m_nFXChainPhaserDepth; + unsigned m_nFXChainPhaserFeedback; + unsigned m_nFXChainPhaserNbStages; bool m_bFXChainDelayEnable; unsigned m_nFXChainDelayWet; unsigned m_nFXChainDelayLeftDelayTime; diff --git a/src/test/fxrack_test.cpp b/src/test/fxrack_test.cpp index 29888d4..eb0edb7 100644 --- a/src/test/fxrack_test.cpp +++ b/src/test/fxrack_test.cpp @@ -151,6 +151,10 @@ void testFXRack(unsigned& step, unsigned fxSwitch) rack->getChorus()->setDepth(0.5f); rack->getPhaser()->setEnable(Active(fxSwitch, FXSitch::Phaser)); + rack->getPhaser()->setWetLevel(1.0f); + rack->getPhaser()->setRate(0.1f); + rack->getPhaser()->setDepth(1.0f); + rack->getPhaser()->setFeedback(0.75f); rack->getOrbitone()->setEnable(Active(fxSwitch, FXSitch::Orbitone)); rack->getOrbitone()->setWetLevel(0.8f); @@ -210,9 +214,9 @@ int main() // testLFO(step); // testFlutter(step); // testSVF(step); - testFXRack(step, FXSitch::Tube); + // testFXRack(step, FXSitch::Tube); // testFXRack(step, FXSitch::Flanger); // to be fixed -> feedback deletes FX effect - // testFXRack(step, FXSitch::Phaser); // to be fixed -> far too load but saturation is interested + testFXRack(step, FXSitch::Phaser); // testFXRack(step, FXSitch::Chorus); // testFXRack(step, FXSitch::Orbitone); // testFXRack(step, FXSitch::Delay); diff --git a/src/uimenu.cpp b/src/uimenu.cpp index 10e815e..6507979 100644 --- a/src/uimenu.cpp +++ b/src/uimenu.cpp @@ -198,7 +198,9 @@ const CUIMenu::TMenuItem CUIMenu::s_FXChainPhaser[] = {"Enable", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserEnable}, {"Wet Lvl", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserWet}, {"Rate", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserRate}, - {"Res", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserResonance}, + {"Depth", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserDepth}, + {"Feedbck", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserFeedback}, + {"Stages", EditGlobalParameter, 0, CMiniDexed::ParameterFXChainPhaserNbStages}, {0} }; @@ -340,7 +342,9 @@ const CUIMenu::TParameter CUIMenu::s_GlobalParameter[CMiniDexed::ParameterUnknow {0, 1, 1, ToOnOff}, // ParameterFXChainPhaserEnable {0, 99, 1}, // ParameterFXChainPhaserWet {0, 99, 1}, // ParameterFXChainPhaserRate - {0, 99, 1}, // ParameterFXChainPhaserResonance + {0, 99, 1}, // ParameterFXChainPhaserDepth + {0, 99, 1}, // ParameterFXChainPhaserFeedback + {2, MAX_NB_PHASES, 1}, // ParameterFXChainPhaserNbStages // FXChain > Delay parameters {0, 1, 1, ToOnOff}, // ParameterFXChainDelayEnable