zynaddsubfx

ZynAddSubFX open source synthesizer
Log | Files | Refs | Submodules | LICENSE

commit 9f909f7ef7d1e6a6d32b5622fb138f5f06142a14
parent d2c9a44b870679f3c2660278424a309bb1917aca
Author: fundamental <mark.d.mccurry@gmail.com>
Date:   Wed, 14 Sep 2011 18:11:57 -0400

Yoshimi: converging style in DSP

Diffstat:
Msrc/DSP/AnalogFilter.cpp | 159++++++++++++++++++++++++++++++++-----------------------------------------------
Msrc/DSP/AnalogFilter.h | 12+++++-------
Msrc/DSP/FormantFilter.cpp | 59+++++++++++++++++++++++++++--------------------------------
Msrc/DSP/FormantFilter.h | 10++++++----
Msrc/DSP/SVFilter.cpp | 40++++++++++++++++------------------------
Msrc/DSP/SVFilter.h | 15+++++++--------
Msrc/DSP/Unison.cpp | 99+++++++++++++++++++++++++++++++++++++++----------------------------------------
Msrc/DSP/Unison.h | 27++++++++++++++++-----------
Msrc/Effects/Reverb.cpp | 6+++---
9 files changed, 193 insertions(+), 234 deletions(-)

diff --git a/src/DSP/AnalogFilter.cpp b/src/DSP/AnalogFilter.cpp @@ -22,9 +22,9 @@ */ -#include <cmath> -#include <cstdio> #include <cstring> //memcpy +#include <cmath> + #include "../Misc/Util.h" #include "AnalogFilter.h" @@ -32,24 +32,20 @@ AnalogFilter::AnalogFilter(unsigned char Ftype, float Ffreq, float Fq, unsigned char Fstages) + :type(Ftype), + stages(Fstages), + freq(Ffreq), + q(Fq), + gain(1.0), + abovenq(false), + oldabovenq(false) { - stages = Fstages; - for(int i = 0; i < 3; ++i) { - coeff.c[i] = 0.0f; - coeff.d[i] = 0.0f; - oldCoeff.c[i] = 0.0f; - oldCoeff.d[i] = 0.0f; - } - type = Ftype; - freq = Ffreq; - q = Fq; - gain = 1.0f; + for(int i = 0; i < 3; ++i) + coeff.c[i] = coeff.d[i] = oldCoeff.c[i] = oldCoeff.d[i] = 0.0f; if(stages >= MAX_FILTER_STAGES) stages = MAX_FILTER_STAGES; cleanup(); firsttime = false; - abovenq = false; - oldabovenq = false; setfreq_and_q(Ffreq, Fq); firsttime = true; coeff.d[0] = 0; //this is not used @@ -71,10 +67,10 @@ void AnalogFilter::cleanup() needsinterpolation = false; } -void AnalogFilter::computefiltercoefs() +void AnalogFilter::computefiltercoefs(void) { float tmp; - bool zerocoefs = false; //this is used if the freq is too high + bool zerocoefs = false; //this is used if the freq is too high //do not allow frequencies bigger than samplerate/2 float freq = this->freq; @@ -93,7 +89,7 @@ void AnalogFilter::computefiltercoefs() tmpgain = gain; } else { - tmpq = (q > 1.0f ? powf(q, 1.0f / (stages + 1)) : q); + tmpq = (q > 1.0f) ? powf(q, 1.0f / (stages + 1)) : q; tmpgain = powf(gain, 1.0f / (stages + 1)); } @@ -137,105 +133,85 @@ void AnalogFilter::computefiltercoefs() break; case 2: //LPF 2 poles if(!zerocoefs) { - alpha = sn / (2 * tmpq); + alpha = sn / (2.0f * tmpq); tmp = 1 + alpha; - c[0] = (1.0f - cs) / 2.0f / tmp; c[1] = (1.0f - cs) / tmp; - c[2] = (1.0f - cs) / 2.0f / tmp; - d[1] = -2 * cs / tmp * (-1); - d[2] = (1 - alpha) / tmp * (-1); + c[0] = c[2] = c[1] / 2.0f; + d[1] = -2.0f * cs / tmp * -1.0f; + d[2] = (1.0f - alpha) / tmp * -1.0f; } else { c[0] = 1.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + c[1] = c[2] = d[1] = d[2] = 0.0f; } order = 2; break; case 3: //HPF 2 poles if(!zerocoefs) { - alpha = sn / (2 * tmpq); + alpha = sn / (2.0f * tmpq); tmp = 1 + alpha; c[0] = (1.0f + cs) / 2.0f / tmp; c[1] = -(1.0f + cs) / tmp; c[2] = (1.0f + cs) / 2.0f / tmp; - d[1] = -2 * cs / tmp * (-1); - d[2] = (1 - alpha) / tmp * (-1); - } - else { - c[0] = 0.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + d[1] = -2.0f * cs / tmp * -1.0f; + d[2] = (1.0f - alpha) / tmp * -1.0f; } + else + c[0] = c[1] = c[2] = d[1] = d[2] = 0.0f; order = 2; break; case 4: //BPF 2 poles if(!zerocoefs) { - alpha = sn / (2 * tmpq); - tmp = 1 + alpha; - c[0] = alpha / tmp *sqrt(tmpq + 1); - c[1] = 0; - c[2] = -alpha / tmp *sqrt(tmpq + 1); - d[1] = -2 * cs / tmp * (-1); - d[2] = (1 - alpha) / tmp * (-1); - } - else { - c[0] = 0.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + alpha = sn / (2.0f * tmpq); + tmp = 1.0f + alpha; + c[0] = alpha / tmp *sqrtf(tmpq + 1.0f); + c[1] = 0.0f; + c[2] = -alpha / tmp *sqrtf(tmpq + 1.0f); + d[1] = -2.0f * cs / tmp * -1.0f; + d[2] = (1.0f - alpha) / tmp * -1.0f; } + else + c[0] = c[1] = c[2] = d[1] = d[2] = 0.0f; order = 2; break; case 5: //NOTCH 2 poles if(!zerocoefs) { - alpha = sn / (2 * sqrt(tmpq)); - tmp = 1 + alpha; - c[0] = 1 / tmp; - c[1] = -2 * cs / tmp; - c[2] = 1 / tmp; - d[1] = -2 * cs / tmp * (-1); - d[2] = (1 - alpha) / tmp * (-1); + alpha = sn / (2.0f * sqrtf(tmpq)); + tmp = 1.0f + alpha; + c[0] = 1.0f / tmp; + c[1] = -2.0f * cs / tmp; + c[2] = 1.0f / tmp; + d[1] = -2.0f * cs / tmp * -1.0f; + d[2] = (1.0f - alpha) / tmp * -1.0f; } else { c[0] = 1.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + c[1] = c[2] = d[1] = d[2] = 0.0f; } order = 2; break; case 6: //PEAK (2 poles) if(!zerocoefs) { tmpq *= 3.0f; - alpha = sn / (2 * tmpq); - tmp = 1 + alpha / tmpgain; + alpha = sn / (2.0f * tmpq); + tmp = 1.0f + alpha / tmpgain; c[0] = (1.0f + alpha * tmpgain) / tmp; c[1] = (-2.0f * cs) / tmp; c[2] = (1.0f - alpha * tmpgain) / tmp; - d[1] = -2 * cs / tmp * (-1); - d[2] = (1 - alpha / tmpgain) / tmp * (-1); + d[1] = -2.0f * cs / tmp * -1.0f; + d[2] = (1.0f - alpha / tmpgain) / tmp * -1.0f; } else { c[0] = 1.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + c[1] = c[2] = d[1] = d[2] = 0.0f; } order = 2; break; case 7: //Low Shelf - 2 poles if(!zerocoefs) { - tmpq = sqrt(tmpq); - alpha = sn / (2 * tmpq); - beta = sqrt(tmpgain) / tmpq; + tmpq = sqrtf(tmpq); + alpha = sn / (2.0f * tmpq); + beta = sqrtf(tmpgain) / tmpq; tmp = (tmpgain + 1.0f) + (tmpgain - 1.0f) * cs + beta * sn; c[0] = tmpgain @@ -246,26 +222,22 @@ void AnalogFilter::computefiltercoefs() c[2] = tmpgain * ((tmpgain + 1.0f) - (tmpgain - 1.0f) * cs - beta * sn) / tmp; - d[1] = -2.0f - * ((tmpgain - 1.0f) + (tmpgain + 1.0f) * cs) / tmp * (-1); - d[2] = - ((tmpgain - + 1.0f) + (tmpgain - 1.0f) * cs - beta * sn) / tmp * (-1); + d[1] = -2.0f * ((tmpgain - 1.0f) + (tmpgain + 1.0f) * cs) + / tmp * -1.0f; + d[2] = ((tmpgain + 1.0f) + (tmpgain - 1.0f) * cs - beta * sn) + / tmp * -1.0f; } else { c[0] = tmpgain; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + c[1] = c[2] = d[1] = d[2] = 0.0f; } order = 2; break; case 8: //High Shelf - 2 poles if(!zerocoefs) { - tmpq = sqrt(tmpq); - alpha = sn / (2 * tmpq); - beta = sqrt(tmpgain) / tmpq; + tmpq = sqrtf(tmpq); + alpha = sn / (2.0f * tmpq); + beta = sqrtf(tmpgain) / tmpq; tmp = (tmpgain + 1.0f) - (tmpgain - 1.0f) * cs + beta * sn; c[0] = tmpgain @@ -276,18 +248,14 @@ void AnalogFilter::computefiltercoefs() c[2] = tmpgain * ((tmpgain + 1.0f) + (tmpgain - 1.0f) * cs - beta * sn) / tmp; - d[1] = 2.0f - * ((tmpgain - 1.0f) - (tmpgain + 1.0f) * cs) / tmp * (-1); - d[2] = - ((tmpgain - + 1.0f) - (tmpgain - 1.0f) * cs - beta * sn) / tmp * (-1); + d[1] = 2.0f * ((tmpgain - 1.0f) - (tmpgain + 1.0f) * cs) + / tmp * -1.0f; + d[2] = ((tmpgain + 1.0f) - (tmpgain - 1.0f) * cs - beta * sn) + / tmp * -1.0f; } else { c[0] = 1.0f; - c[1] = 0.0f; - c[2] = 0.0f; - d[1] = 0.0f; - d[2] = 0.0f; + c[1] = c[2] = d[1] = d[2] = 0.0f; } order = 2; break; @@ -370,7 +338,7 @@ void AnalogFilter::singlefilterout(float *smp, fstage &hist, hist.x1 = smp[i]; smp[i] = y0; } - if(order == 2) //Second order filter + if(order == 2) //Second order filter for(int i = 0; i < SOUND_BUFFER_SIZE; ++i) { float y0 = smp[i] * coeff.c[0] + hist.x1 * coeff.c[1] + hist.x2 * coeff.c[2] + hist.y1 * coeff.d[1] @@ -382,6 +350,7 @@ void AnalogFilter::singlefilterout(float *smp, fstage &hist, smp[i] = y0; } } + void AnalogFilter::filterout(float *smp) { for(int i = 0; i < stages + 1; ++i) diff --git a/src/DSP/AnalogFilter.h b/src/DSP/AnalogFilter.h @@ -34,9 +34,7 @@ class AnalogFilter:public Filter { public: - AnalogFilter(unsigned char Ftype, - float Ffreq, - float Fq, + AnalogFilter(unsigned char Ftype, float Ffreq, float Fq, unsigned char Fstages); ~AnalogFilter(); void filterout(float *smp); @@ -66,15 +64,15 @@ class AnalogFilter:public Filter //Apply IIR filter to Samples, with coefficients, and past history void singlefilterout(float *smp, fstage &hist, const Coeff &coeff); //Update coeff and order - void computefiltercoefs(); + void computefiltercoefs(void); - int type; //The type of the filter (LPF1,HPF1,LPF2,HPF2...) - int stages; //how many times the filter is applied (0->1,1->2,etc.) + int type; //The type of the filter (LPF1,HPF1,LPF2,HPF2...) + int stages; //how many times the filter is applied (0->1,1->2,etc.) float freq; //Frequency given in Hz float q; //Q factor (resonance or Q factor) float gain; //the gain of the filter (if are shelf/peak) filters - int order; //the order of the filter (number of poles) + int order; //the order of the filter (number of poles) bool needsinterpolation, //Interpolation between coeff changes firsttime; //First Iteration of filter diff --git a/src/DSP/FormantFilter.cpp b/src/DSP/FormantFilter.cpp @@ -96,17 +96,16 @@ void FormantFilter::setpos(float input) slowinput = slowinput * (1.0f - formantslowness) + input * formantslowness; - if((fabs(oldinput - input) < 0.001f) && (fabs(slowinput - input) < 0.001f) - && (fabs(Qfactor - oldQfactor) < 0.001f)) { -// oldinput=input; daca setez asta, o sa faca probleme la schimbari foarte lente + if((fabsf(oldinput - input) < 0.001f) && (fabsf(slowinput - input) < 0.001f) + && (fabsf(Qfactor - oldQfactor) < 0.001f)) { + // oldinput=input; daca setez asta, o sa faca probleme la schimbari foarte lente firsttime = 0; return; } else oldinput = input; - - float pos = fmod(input * sequencestretch, 1.0f); + float pos = fmodf(input * sequencestretch, 1.0f); if(pos < 0.0f) pos += 1.0f; @@ -115,7 +114,7 @@ void FormantFilter::setpos(float input) if(p1 < 0) p1 += sequencesize; - pos = fmod(pos * sequencesize, 1.0f); + pos = fmodf(pos * sequencesize, 1.0f); if(pos < 0.0f) pos = 0.0f; else @@ -131,14 +130,14 @@ void FormantFilter::setpos(float input) if(firsttime != 0) { for(int i = 0; i < numformants; ++i) { - currentformants[i].freq = formantpar[p1][i].freq - * (1.0f - - pos) + formantpar[p2][i].freq * pos; - currentformants[i].amp = formantpar[p1][i].amp - * (1.0f - - pos) + formantpar[p2][i].amp * pos; - currentformants[i].q = formantpar[p1][i].q - * (1.0f - pos) + formantpar[p2][i].q * pos; + currentformants[i].freq = + formantpar[p1][i].freq + * (1.0f - pos) + formantpar[p2][i].freq * pos; + currentformants[i].amp = + formantpar[p1][i].amp + * (1.0f - pos) + formantpar[p2][i].amp * pos; + currentformants[i].q = + formantpar[p1][i].q * (1.0f - pos) + formantpar[p2][i].q * pos; formant[i]->setfreq_and_q(currentformants[i].freq, currentformants[i].q * Qfactor); oldformantamp[i] = currentformants[i].amp; @@ -147,26 +146,22 @@ void FormantFilter::setpos(float input) } else for(int i = 0; i < numformants; ++i) { - currentformants[i].freq = currentformants[i].freq - * (1.0f - formantslowness) - + (formantpar[p1][i].freq - * (1.0f - - pos) + formantpar[p2][i].freq - * pos) * formantslowness; - - currentformants[i].amp = currentformants[i].amp - * (1.0f - formantslowness) - + (formantpar[p1][i].amp - * (1.0f - - pos) + formantpar[p2][i].amp - * pos) * formantslowness; + currentformants[i].freq = + currentformants[i].freq * (1.0f - formantslowness) + + (formantpar[p1][i].freq + * (1.0f - pos) + formantpar[p2][i].freq * pos) + * formantslowness; + + currentformants[i].amp = + currentformants[i].amp * (1.0f - formantslowness) + + (formantpar[p1][i].amp * (1.0f - pos) + + formantpar[p2][i].amp * pos) * formantslowness; currentformants[i].q = currentformants[i].q - * (1.0f - formantslowness) - + (formantpar[p1][i].q - * (1.0f - - pos) + formantpar[p2][i].q - * pos) * formantslowness; + * (1.0f - formantslowness) + + (formantpar[p1][i].q * (1.0f - pos) + + formantpar[p2][i].q * pos) * formantslowness; + formant[i]->setfreq_and_q(currentformants[i].freq, currentformants[i].q * Qfactor); diff --git a/src/DSP/FormantFilter.h b/src/DSP/FormantFilter.h @@ -38,9 +38,13 @@ class FormantFilter:public Filter void setq(float q_); void setgain(float dBgain); - void cleanup(); + void cleanup(void); + private: - class AnalogFilter * formant[FF_MAX_FORMANTS]; + void setpos(float input); + + + class AnalogFilter *formant[FF_MAX_FORMANTS]; struct { float freq, amp, q; //frequency,amplitude,Q @@ -57,8 +61,6 @@ class FormantFilter:public Filter float oldinput, slowinput; float Qfactor, formantslowness, oldQfactor; float vowelclearness, sequencestretch; - - void setpos(float input); }; #endif diff --git a/src/DSP/SVFilter.cpp b/src/DSP/SVFilter.cpp @@ -28,22 +28,19 @@ #include "../Misc/Util.h" #include "SVFilter.h" -SVFilter::SVFilter(unsigned char Ftype, - float Ffreq, - float Fq, +SVFilter::SVFilter(unsigned char Ftype, float Ffreq, float Fq, unsigned char Fstages) + :type(Ftype), + stages(Fstages), + freq(Ffreq), + q(Fq), + gain(1.0f), + needsinterpolation(false), + firsttime(true) { - assert(Ftype < 4); - stages = Fstages; - type = Ftype; - freq = Ffreq; - q = Fq; - gain = 1.0f; - outgain = 1.0f; - needsinterpolation = false; - firsttime = true; if(stages >= MAX_FILTER_STAGES) stages = MAX_FILTER_STAGES; + outgain = 1.0f; cleanup(); setfreq_and_q(Ffreq, Fq); } @@ -53,24 +50,20 @@ SVFilter::~SVFilter() void SVFilter::cleanup() { - for(int i = 0; i < MAX_FILTER_STAGES + 1; ++i) { - st[i].low = 0.0f; - st[i].high = 0.0f; - st[i].band = 0.0f; - st[i].notch = 0.0f; - } + for(int i = 0; i < MAX_FILTER_STAGES + 1; ++i) + st[i].low = st[i].high = st[i].band = st[i].notch = 0.0f; oldabovenq = false; abovenq = false; } -void SVFilter::computefiltercoefs() +void SVFilter::computefiltercoefs(void) { par.f = freq / SAMPLE_RATE * 4.0f; if(par.f > 0.99999f) par.f = 0.99999f; - par.q = 1.0f - atanf(sqrt(q)) * 2.0f / PI; + par.q = 1.0f - atanf(sqrtf(q)) * 2.0f / PI; par.q = powf(par.q, 1.0f / (stages + 1)); - par.q_sqrt = sqrt(par.q); + par.q_sqrt = sqrtf(par.q); } @@ -89,9 +82,9 @@ void SVFilter::setfreq(float frequency) //if the frequency is changed fast, it needs interpolation if((rap > 3.0f) || nyquistthresh) { //(now, filter and coeficients backup) - ipar = par; if(!firsttime) needsinterpolation = true; + ipar = par; } freq = frequency; computefiltercoefs(); @@ -156,8 +149,7 @@ void SVFilter::singlefilterout(float *smp, fstage &x, parameters &par) x.high = par.q_sqrt * smp[i] - x.low - par.q * x.band; x.band = par.f * x.high + x.band; x.notch = x.high + x.low; - - smp[i] = *out; + smp[i] = *out; } } diff --git a/src/DSP/SVFilter.h b/src/DSP/SVFilter.h @@ -25,6 +25,7 @@ #include "../globals.h" #include "Filter.h" + class SVFilter:public Filter { public: @@ -52,19 +53,17 @@ class SVFilter:public Filter float f, q, q_sqrt; } par, ipar; - void singlefilterout(float *smp, fstage &x, parameters &par); - void computefiltercoefs(); - int type; //The type of the filter (LPF1,HPF1,LPF2,HPF2...) - int stages; //how many times the filter is applied (0->1,1->2,etc.) - float freq; //Frequency given in Hz - float q; //Q factor (resonance or Q factor) - float gain; //the gain of the filter (if are shelf/peak) filters + void computefiltercoefs(void); + int type; // The type of the filter (LPF1,HPF1,LPF2,HPF2...) + int stages; // how many times the filter is applied (0->1,1->2,etc.) + float freq; // Frequency given in Hz + float q; // Q factor (resonance or Q factor) + float gain; // the gain of the filter (if are shelf/peak) filters bool abovenq, //if the frequency is above the nyquist oldabovenq; bool needsinterpolation, firsttime; }; - #endif diff --git a/src/DSP/Unison.cpp b/src/DSP/Unison.cpp @@ -19,36 +19,38 @@ Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ -#include <math.h> -#include <stdio.h> +#include <cmath> +#include <cstring> + #include "Unison.h" -Unison::Unison(int update_period_samples_, float max_delay_sec_) { - update_period_samples = update_period_samples_; - max_delay = (int)(max_delay_sec_ * (float)SAMPLE_RATE + 1); +Unison::Unison(int update_period_samples_, float max_delay_sec_) + :unison_size(0), + base_freq(1.0f), + uv(NULL), + update_period_samples(update_period_samples_), + update_period_sample_k(0), + max_delay((int)(max_delay_sec_ * (float)SAMPLE_RATE + 1)), + delay_k(0), + first_time(false), + delay_buffer(NULL), + unison_amplitude_samples(0.0f), + unison_bandwidth_cents(10.0f) +{ if(max_delay < 10) max_delay = 10; delay_buffer = new float[max_delay]; - delay_k = 0; - base_freq = 1.0f; - unison_bandwidth_cents = 10.0f; - - ZERO_float(delay_buffer, max_delay); - - uv = NULL; - update_period_sample_k = 0; - first_time = 0; - - set_size(1); + memset(delay_buffer, 0, max_delay * sizeof(float)); + setSize(1); } Unison::~Unison() { delete [] delay_buffer; - if(uv) - delete [] uv; + delete [] uv; } -void Unison::set_size(int new_size) { +void Unison::setSize(int new_size) +{ if(new_size < 1) new_size = 1; unison_size = new_size; @@ -56,28 +58,30 @@ void Unison::set_size(int new_size) { delete [] uv; uv = new UnisonVoice[unison_size]; first_time = true; - update_parameters(); + updateParameters(); } -void Unison::set_base_frequency(float freq) { +void Unison::setBaseFrequency(float freq) +{ base_freq = freq; - update_parameters(); + updateParameters(); } -void Unison::set_bandwidth(float bandwidth) { +void Unison::setBandwidth(float bandwidth) +{ if(bandwidth < 0) bandwidth = 0.0f; if(bandwidth > 1200.0f) bandwidth = 1200.0f; - printf("bandwidth %g\n", bandwidth); #warning \ : todo: if bandwidth is too small the audio will be self canceled (because of the sign change of the outputs) unison_bandwidth_cents = bandwidth; - update_parameters(); + updateParameters(); } -void Unison::update_parameters() { +void Unison::updateParameters(void) +{ if(!uv) return; float increments_per_second = SAMPLE_RATE @@ -95,47 +99,44 @@ void Unison::update_parameters() { } float max_speed = powf(2.0f, unison_bandwidth_cents / 1200.0f); - unison_amplitude_samples = 0.125f - * (max_speed - 1.0f) * SAMPLE_RATE / base_freq; - printf("unison_amplitude_samples %g\n", unison_amplitude_samples); + unison_amplitude_samples = 0.125f * (max_speed - 1.0f) + * SAMPLE_RATE / base_freq; #warning \ todo: test if unison_amplitude_samples is to big and reallocate bigger memory if(unison_amplitude_samples >= max_delay - 1) unison_amplitude_samples = max_delay - 2; - update_unison_data(); + updateUnisonData(); } -void Unison::process(int bufsize, float *inbuf, float *outbuf) { +void Unison::process(int bufsize, float *inbuf, float *outbuf) +{ if(!uv) return; if(!outbuf) outbuf = inbuf; - float volume = 1.0f / sqrt(unison_size); + float volume = 1.0f / sqrtf(unison_size); float xpos_step = 1.0f / (float) update_period_samples; float xpos = (float) update_period_sample_k * xpos_step; for(int i = 0; i < bufsize; ++i) { - if((update_period_sample_k++) >= update_period_samples) { - update_unison_data(); + if(update_period_sample_k++ >= update_period_samples) { + updateUnisonData(); update_period_sample_k = 0; xpos = 0.0f; } xpos += xpos_step; - float in = inbuf[i], out = 0.0f; - + float in = inbuf[i], out = 0.0f; float sign = 1.0f; for(int k = 0; k < unison_size; ++k) { - float vpos = uv[k].realpos1 - * (1.0f - xpos) + uv[k].realpos2 * xpos; //optimize - float pos = delay_k + max_delay - vpos - 1.0f; //optimize + float vpos = uv[k].realpos1 * (1.0f - xpos) + uv[k].realpos2 * xpos; //optimize + float pos = (float)(delay_k + max_delay) - vpos - 1.0f; int posi; - float posf; F2I(pos, posi); //optimize! if(posi >= max_delay) posi -= max_delay; - posf = pos - floor(pos); + float posf = pos - floorf(pos); out += ((1.0f - posf) * delay_buffer[posi] + posf @@ -145,12 +146,12 @@ void Unison::process(int bufsize, float *inbuf, float *outbuf) { outbuf[i] = out * volume; // printf("%d %g\n",i,outbuf[i]); delay_buffer[delay_k] = in; - if((++delay_k) >= max_delay) - delay_k = 0; + delay_k = (++delay_k < max_delay) ? delay_k : 0; } } -void Unison::update_unison_data() { +void Unison::updateUnisonData() +{ if(!uv) return; @@ -162,7 +163,7 @@ void Unison::update_unison_data() { pos = -1.0f; step = -step; } - if(pos >= 1.0f) { + else if(pos >= 1.0f) { pos = 1.0f; step = -step; } @@ -172,9 +173,8 @@ void Unison::update_unison_data() { #warning \ I have to enlarge (reallocate) the buffer to make place for the whole delay float newval = 1.0f + 0.5f - * (vibratto_val - + 1.0f) * unison_amplitude_samples - * uv[k].relative_amplitude; + * (vibratto_val + 1.0f) * unison_amplitude_samples + * uv[k].relative_amplitude; if(first_time) uv[k].realpos1 = uv[k].realpos2 = newval; @@ -186,6 +186,5 @@ void Unison::update_unison_data() { uv[k].position = pos; uv[k].step = step; } - if(first_time) - first_time = false; + first_time = false; } diff --git a/src/DSP/Unison.h b/src/DSP/Unison.h @@ -21,11 +21,11 @@ #ifndef UNISON_H #define UNISON_H -#include <stdlib.h> + #include "../Misc/Util.h" +//how much the unison frequencies varies (always >= 1.0) #define UNISON_FREQ_SPAN 2.0f -//how much the unison frequencies varies (always >= 1.0f) class Unison { @@ -33,23 +33,26 @@ class Unison Unison(int update_period_samples_, float max_delay_sec_); ~Unison(); - void set_size(int new_size); - void set_base_frequency(float freq); - void set_bandwidth(float bandwidth_cents); + void setSize(int new_size); + void setBaseFrequency(float freq); + void setBandwidth(float bandwidth_cents); void process(int bufsize, float *inbuf, float *outbuf = NULL); private: - void update_parameters(); - void update_unison_data(); + void updateParameters(void); + void updateUnisonData(void); int unison_size; float base_freq; struct UnisonVoice { - float step, position; //base LFO - float realpos1, realpos2; //the position regarding samples + float step; //base LFO + float position; + float realpos1; //the position regarding samples + float realpos2; float relative_amplitude; - float lin_fpos, lin_ffreq; + float lin_fpos; + float lin_ffreq; UnisonVoice() { position = RND * 1.8f - 0.9f; realpos1 = 0.0f; @@ -58,7 +61,9 @@ class Unison relative_amplitude = 1.0f; } } *uv; - int update_period_samples, update_period_sample_k; + + int update_period_samples; + int update_period_sample_k; int max_delay, delay_k; bool first_time; float *delay_buffer; diff --git a/src/Effects/Reverb.cpp b/src/Effects/Reverb.cpp @@ -379,8 +379,8 @@ void Reverb::settype(unsigned char Ptype) bandwidth = NULL; if(Ptype == 2) { //bandwidth bandwidth = new Unison(SOUND_BUFFER_SIZE / 4 + 1, 2.0f); - bandwidth->set_size(50); - bandwidth->set_base_frequency(1.0f); + bandwidth->setSize(50); + bandwidth->setBaseFrequency(1.0f); #warning sa schimb size-ul } } @@ -402,7 +402,7 @@ void Reverb::setbandwidth(unsigned char Pbandwidth) { this->Pbandwidth = Pbandwidth; float v = Pbandwidth / 127.0f; if(bandwidth) - bandwidth->set_bandwidth(powf(v, 2.0f) * 200.0f); + bandwidth->setBandwidth(powf(v, 2.0f) * 200.0f); } void Reverb::setpreset(unsigned char npreset)