[SCM] calf/master: + MultiChorus: change multilfo interface to output value instead of phase (+update multichorus), make scale 1/sqrt(N) instead of 1/N, move scale calculation outside the loop, remove leftover printf
js at users.alioth.debian.org
js at users.alioth.debian.org
Tue May 7 15:37:48 UTC 2013
The following commit has been merged in the master branch:
commit b7146740bb399dad9e309bf0d645ba2175a3c3dc
Author: Krzysztof Foltman <wdev at foltman.com>
Date: Tue Oct 28 19:42:16 2008 +0000
+ MultiChorus: change multilfo interface to output value instead of phase (+update multichorus), make scale 1/sqrt(N) instead of 1/N, move scale calculation outside the loop, remove leftover printf
diff --git a/src/calf/multichorus.h b/src/calf/multichorus.h
index d737cb0..e5b7ef7 100644
--- a/src/calf/multichorus.h
+++ b/src/calf/multichorus.h
@@ -35,21 +35,32 @@ protected:
enum { Multiplier = (65536 / Voices) << 16 };
public:
- chorus_phase phase, dphase;
+ /// Current LFO phase
+ chorus_phase phase;
+ /// LFO phase increment
+ chorus_phase dphase;
public:
inline uint32_t get_voices() const
{
return Voices;
}
- inline chorus_phase get_phase(uint32_t voice) const {
- return phase + chorus_phase::from_base(Multiplier * voice);
+ /// Get LFO value for given voice, returns a values in range of [-65536, 65536]
+ inline int get_value(uint32_t voice) {
+ // find this voice's phase (= phase + voice * 360 degrees / number of voices)
+ chorus_phase voice_phase = phase + chorus_phase::from_base(Multiplier * voice);
+ // find table offset
+ unsigned int ipart = voice_phase.ipart();
+ // interpolate (use 14 bits of precision - because the table itself uses 18 bits and the result of multiplication must fit in int32_t)
+ // note, the result is still -65536 .. 65536, it's just interpolated
+ return voice_phase.lerp_by_fract_int<int, 14, int>(sine.data[ipart], sine.data[ipart+1]);
}
inline void step() {
phase += dphase;
}
inline T get_scale() const {
- return 1.0 / Voices;
+ // use sqrt, because some phases will cancel each other - so 1 / N is usually too low
+ return sqrt(1.0 / Voices);
}
void reset() {
phase = 0.f;
@@ -84,7 +95,6 @@ public:
lfo.dphase = dphase;
}
virtual void setup(int sample_rate) {
- printf("setting sample rate = %d\n", sample_rate);
modulation_effect::setup(sample_rate);
delay.reset();
lfo.reset();
@@ -94,7 +104,8 @@ public:
template<class OutIter, class InIter>
void process(OutIter buf_out, InIter buf_in, int nsamples) {
int mds = min_delay_samples + mod_depth_samples * 1024 + 2*65536;
- int mdepth = mod_depth_samples;
+ int mdepth = mod_depth_samples; // 1 sample peak-to-peak = mdepth of 32 (this scaling stuff is tricky and may - but shouldn't - be wrong)
+ T scale = lfo.get_scale();
for (int i=0; i<nsamples; i++) {
phase += dphase;
@@ -106,17 +117,15 @@ public:
// add up values from all voices, each voice tell its LFO phase and the buffer value is picked at that location
for (unsigned int v = 0; v < nvoices; v++)
{
- chorus_phase phase = lfo.get_phase(v);
- unsigned int ipart = phase.ipart();
- int lfo = phase.lerp_by_fract_int<int, 14, int>(sine.data[ipart], sine.data[ipart+1]);
- int v = mds + (mdepth * lfo >> 6);
+ int lfo_output = lfo.get_value(v);
+ int v = mds + (mdepth * lfo_output >> 6);
int ifv = v >> 16;
T fd; // signal from delay's output
delay.get_interp(fd, ifv, (v & 0xFFFF)*(1.0/65536.0));
out += fd;
}
T sdry = in * gs_dry.get();
- T swet = out * gs_wet.get() * lfo.get_scale();
+ T swet = out * gs_wet.get() * scale;
*buf_out++ = sdry + swet;
lfo.step();
}
--
calf audio plugins packaging
More information about the pkg-multimedia-commits
mailing list