From 8c091c2a050601d13d316ec8a3ddb70afb98f48e Mon Sep 17 00:00:00 2001 From: Gordon JC Pearce Date: Sun, 21 Dec 2025 22:08:09 +0000 Subject: [PATCH] sine-based, getting close to real though --- plugin/chorus.cpp | 58 ++++++++++++++++++++--------------------------- plugin/chorus.hpp | 7 +++--- plugin/voice.cpp | 2 +- 3 files changed, 29 insertions(+), 38 deletions(-) diff --git a/plugin/chorus.cpp b/plugin/chorus.cpp index 1c7bb36..2acadcd 100644 --- a/plugin/chorus.cpp +++ b/plugin/chorus.cpp @@ -30,17 +30,16 @@ Chorus::Chorus() { ram = new float[DELAYSIZE]; // probably needs to be calculated based on sample rate fastPhase = 0; - slowPhase = 0; - postFilter1l = new SVF(POSTCUTOFF, .546); - postFilter2l = new SVF(POSTCUTOFF, 1.324); - postFilter1r = new SVF(POSTCUTOFF, .546); - postFilter2r = new SVF(POSTCUTOFF, 1.324); + // not quite Butterworth but you'd never hear the difference + postFilter1l = new SVF(9688, .549); + postFilter2l = new SVF(10377, 1.291); + postFilter1r = new SVF(9688, .549); + postFilter2r = new SVF(10377, 1.291); // lfo values taken from a rough simulation - fastOmega = 6.283 * 5.7 / sampleRate; // approximate, can be adjusted - slowOmega = 6.283 * 0.7 / sampleRate; // again approximate - + fastOmega = 6.283 * 0.7 / sampleRate; // approximate, can be adjusted + // zero out the delay buffer memset(ram, 0, sizeof(float) * DELAYSIZE); memset(lpfOut1, 0, sizeof(float) * bufferSize); @@ -62,7 +61,7 @@ void Chorus::run(const float* input, float** outputs, uint32_t frames) { // actual effects here // now run the DSP - float out0 = 0, out120 = 0, out240 = 0, s0 = 0, s1 = 0; + float s0 = 0, s1 = 0; float lfoMod, dly1, frac; uint16_t tap, delay; @@ -70,16 +69,14 @@ void Chorus::run(const float* input, float** outputs, uint32_t frames) { // run a step of LFO fastPhase += fastOmega; if (fastPhase > 6.283) fastPhase -= 6.283; - slowPhase += slowOmega; - if (slowPhase > 6.283) slowPhase -= 6.283; ram[delayptr] = input[i]; #define BASE 0.05 -#define AMT 0.00175 +#define AMT 0.003175 // 0 degree delay line - lfoMod = 0.203 * sin(fastPhase) + 0.835 * sin(slowPhase); + lfoMod = 0.603 * sin(fastPhase); dly1 = (BASE + (AMT * lfoMod)) * sampleRate; delay = (int)dly1; frac = dly1 - delay; @@ -87,39 +84,34 @@ void Chorus::run(const float* input, float** outputs, uint32_t frames) { tap = delayptr - delay; s1 = ram[(tap - 1) & 0x3ff]; s0 = ram[tap & 0x3ff]; - out0 = ((s1 - s0) * frac) + s0; + lpfOut1[i] = ((s1 - s0) * frac) + s0; - // 120 degree delay line - lfoMod = 0.248 * sin(fastPhase + 2.09) + 0.745 * sin(slowPhase + 2.09); - dly1 = (BASE + (AMT * lfoMod)) * sampleRate; + dly1 = (BASE - (AMT * lfoMod)) * sampleRate; delay = (int)dly1; frac = dly1 - delay; tap = delayptr - delay; s1 = ram[(tap - 1) & 0x3ff]; s0 = ram[tap & 0x3ff]; - out120 = ((s1 - s0) * frac) + s0; + lpfOut2[i] = ((s1 - s0) * frac) + s0; - // 240 degree delay line - lfoMod = 0.252 * sin(fastPhase + 4.18) + 0.809 * sin(slowPhase + 4.18); - dly1 = (BASE + (AMT * lfoMod)) * sampleRate; - delay = (int)dly1; - frac = dly1 - delay; - - tap = delayptr - delay; - s1 = ram[(tap - 1) & 0x3ff]; - s0 = ram[tap & 0x3ff]; - out240 = ((s1 - s0) * frac) + s0; - - lpfOut1[i] = (out0 + (out120 * 0.66) + (out240 * 0.33)); - lpfOut2[i] = (out0 + (out120 * 0.33) + (out240 * 0.66)); + // lpfOut1[i] = input[i] + 1.2 * out0; //(out0 + (out120 * 0.66) + (out240 * 0.33)); + // lpfOut2[i] = input[i] + 1.2 * out120; //(out0 + (out120 * 0.33) + (out240 * 0.66)); delayptr++; delayptr &= 0x3ff; } postFilter1l->runSVF(lpfOut1, lpfOut1, frames); - postFilter2l->runSVF(lpfOut1, outputs[0], frames); + postFilter2l->runSVF(lpfOut1, lpfOut1, frames); postFilter1r->runSVF(lpfOut2, lpfOut2, frames); - postFilter2r->runSVF(lpfOut2, outputs[1], frames); + postFilter2r->runSVF(lpfOut2, lpfOut2, frames); + + for (uint32_t i = 0; i < frames; i++) { + float y = input[i]; + outputs[0][i] = y + (gain * lpfOut1[i]); + outputs[1][i] = y + (gain * lpfOut2[i]); + } + + } diff --git a/plugin/chorus.hpp b/plugin/chorus.hpp index e936201..3a4cdee 100644 --- a/plugin/chorus.hpp +++ b/plugin/chorus.hpp @@ -36,11 +36,10 @@ class Chorus { void run(const float* input, float** outputs, uint32_t frames); private: - double fastPhase, fastOmega; - double slowPhase, slowOmega; - double fastLfo, slowLfo; + double fastPhase = 0, fastOmega = 0; + float gain = 1.2; - uint16_t delayptr; + uint16_t delayptr = 0; float* ram; float* lpfIn; diff --git a/plugin/voice.cpp b/plugin/voice.cpp index 924264f..b734c13 100644 --- a/plugin/voice.cpp +++ b/plugin/voice.cpp @@ -52,7 +52,7 @@ void Voice::off() { void Voice::run(Module* m, float* buffer, uint32_t samples) { // carry out per-voice calculations for each block of samples - float out, t, fb, res; + float out, t, fb; //float cut = 0.00513 + 0.0000075*env;