[SCM] calf/master: Simplify Multiband Compressor code and fix several bugs.

js at users.alioth.debian.org js at users.alioth.debian.org
Tue May 7 15:39:58 UTC 2013


The following commit has been merged in the master branch:
commit 3be583385b0bfb69bb7e52ee7426fe27d515560c
Author: Krzysztof Foltman <wdev at foltman.com>
Date:   Sat Apr 3 01:35:22 2010 +0100

    Simplify Multiband Compressor code and fix several bugs.
    
    Eliminated some (not all) repetition in the code. Fixed a bug where old value
    for Q and separation was taken from the wrong variable. Fixed a bug where
    having a band bypassed or muted caused the graph to stop redrawing properly.

diff --git a/src/calf/modules.h b/src/calf/modules.h
index b3ed83b..6bce138 100644
--- a/src/calf/modules.h
+++ b/src/calf/modules.h
@@ -792,6 +792,7 @@ private:
 public:
     gain_reduction_audio_module();
     void set_params(float att, float rel, float thr, float rat, float kn, float mak, float det, float stl, float byp, float mu);
+    void update_curve();
     void process(float &left, float &right, float det_left = NULL, float det_right = NULL);
     void activate();
     void deactivate();
@@ -910,6 +911,7 @@ public:
 /// Multibandcompressor by Markus Schmidt
 class multibandcompressor_audio_module: public audio_module<multibandcompressor_metadata>, public line_graph_iface {
 private:
+    typedef multibandcompressor_audio_module AM;
     static const int strips = 4;
     bool mute[strips];
     uint32_t clip_inL, clip_inR, clip_outL, clip_outR;
@@ -929,6 +931,7 @@ public:
     void params_changed();
     uint32_t process(uint32_t offset, uint32_t numsamples, uint32_t inputs_mask, uint32_t outputs_mask);
     void set_sample_rate(uint32_t sr);
+    const gain_reduction_audio_module *get_strip_by_param_index(int index) const;
     virtual bool get_graph(int index, int subindex, float *data, int points, cairo_iface *context) const;
     virtual bool get_dot(int index, int subindex, float &x, float &y, int &size, cairo_iface *context) const;
     virtual bool get_gridline(int index, int subindex, float &pos, bool &vertical, std::string &legend, cairo_iface *context) const;
diff --git a/src/modules_dsp.cpp b/src/modules_dsp.cpp
index 450a78c..69b98ed 100644
--- a/src/modules_dsp.cpp
+++ b/src/modules_dsp.cpp
@@ -32,6 +32,8 @@
 using namespace dsp;
 using namespace calf_plugins;
 
+#define SET_IF_CONNECTED(name) if (params[AM::param_##name] != NULL) *params[AM::param_##name] = name;
+
 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
 
 bool frequency_response_line_graph::get_gridline(int index, int subindex, float &pos, bool &vertical, std::string &legend, cairo_iface *context) const
@@ -399,8 +401,8 @@ void multibandcompressor_audio_module::params_changed()
         hpL0.set_hp_rbj((float)(*params[param_freq0] * (1 + *params[param_sep0])), *params[param_q0], (float)srate);
         hpR0.copy_coeffs(hpL0);
         freq_old[0] = *params[param_freq0];
-        sep_old[0]  = *params[param_sep2];
-        q_old[0]    = *params[param_q2];
+        sep_old[0]  = *params[param_sep0];
+        q_old[0]    = *params[param_q0];
     }
     if(*params[param_freq1] != freq_old[1] or *params[param_sep1] != sep_old[1] or *params[param_q1] != q_old[1]) {
         lpL1.set_lp_rbj((float)(*params[param_freq1] * (1 - *params[param_sep1])), *params[param_q1], (float)srate);
@@ -408,8 +410,8 @@ void multibandcompressor_audio_module::params_changed()
         hpL1.set_hp_rbj((float)(*params[param_freq1] * (1 + *params[param_sep1])), *params[param_q1], (float)srate);
         hpR1.copy_coeffs(hpL1);
         freq_old[1] = *params[param_freq1];
-        sep_old[1]  = *params[param_sep2];
-        q_old[1]    = *params[param_q2];
+        sep_old[1]  = *params[param_sep1];
+        q_old[1]    = *params[param_q1];
     }
     if(*params[param_freq2] != freq_old[2] or *params[param_sep2] != sep_old[2] or *params[param_q2] != q_old[2]) {
         lpL2.set_lp_rbj((float)(*params[param_freq2] * (1 - *params[param_sep2])), *params[param_q2], (float)srate);
@@ -421,22 +423,10 @@ void multibandcompressor_audio_module::params_changed()
         q_old[2]    = *params[param_q2];
     }
     // set the params of all strips
-    for (int j = 0; j < strips; j ++) {
-        switch (j) {
-            case 0:
-                strip[j].set_params(*params[param_attack0], *params[param_release0], *params[param_threshold0], *params[param_ratio0], *params[param_knee0], *params[param_makeup0], *params[param_detection0], 1.f, *params[param_bypass0], *params[param_mute0]);
-                break;
-            case 1:
-                strip[j].set_params(*params[param_attack1], *params[param_release1], *params[param_threshold1], *params[param_ratio1], *params[param_knee1], *params[param_makeup1], *params[param_detection1], 1.f, *params[param_bypass1], *params[param_mute1]);
-                break;
-            case 2:
-                strip[j].set_params(*params[param_attack2], *params[param_release2], *params[param_threshold2], *params[param_ratio2], *params[param_knee2], *params[param_makeup2], *params[param_detection2], 1.f, *params[param_bypass2], *params[param_mute2]);
-                break;
-            case 3:
-                strip[j].set_params(*params[param_attack3], *params[param_release3], *params[param_threshold3], *params[param_ratio3], *params[param_knee3], *params[param_makeup3], *params[param_detection3], 1.f, *params[param_bypass3], *params[param_mute3]);
-                break;
-        }
-    }
+    strip[0].set_params(*params[param_attack0], *params[param_release0], *params[param_threshold0], *params[param_ratio0], *params[param_knee0], *params[param_makeup0], *params[param_detection0], 1.f, *params[param_bypass0], *params[param_mute0]);
+    strip[1].set_params(*params[param_attack1], *params[param_release1], *params[param_threshold1], *params[param_ratio1], *params[param_knee1], *params[param_makeup1], *params[param_detection1], 1.f, *params[param_bypass1], *params[param_mute1]);
+    strip[2].set_params(*params[param_attack2], *params[param_release2], *params[param_threshold2], *params[param_ratio2], *params[param_knee2], *params[param_makeup2], *params[param_detection2], 1.f, *params[param_bypass2], *params[param_mute2]);
+    strip[3].set_params(*params[param_attack3], *params[param_release3], *params[param_threshold3], *params[param_ratio3], *params[param_knee3], *params[param_makeup3], *params[param_detection3], 1.f, *params[param_bypass3], *params[param_mute3]);
 }
 
 void multibandcompressor_audio_module::set_sample_rate(uint32_t sr)
@@ -448,10 +438,24 @@ void multibandcompressor_audio_module::set_sample_rate(uint32_t sr)
     }
 }
 
+#define BYPASSED_COMPRESSION(index) \
+    if(params[param_compression##index] != NULL) \
+        *params[param_compression##index] = 1.0; \
+    if(params[param_output##index] != NULL) \
+        *params[param_output##index] = 0.0; 
+
+#define ACTIVE_COMPRESSION(index) \
+    if(params[param_compression##index] != NULL) \
+        *params[param_compression##index] = strip[index].get_comp_level(); \
+    if(params[param_output##index] != NULL) \
+        *params[param_output##index] = strip[index].get_output_level();
+
 uint32_t multibandcompressor_audio_module::process(uint32_t offset, uint32_t numsamples, uint32_t inputs_mask, uint32_t outputs_mask)
 {
     bool bypass = *params[param_bypass] > 0.5f;
     numsamples += offset;
+    for (int i = 0; i < strips; i++)
+        strip[i].update_curve();
     if(bypass) {
         // everything bypassed
         while(offset < numsamples) {
@@ -596,165 +600,75 @@ uint32_t multibandcompressor_audio_module::process(uint32_t offset, uint32_t num
     } // process all strips (no bypass)
     
     // draw meters
-    if(params[param_clip_inL] != NULL) {
-        *params[param_clip_inL] = clip_inL;
-    }
-    if(params[param_clip_inR] != NULL) {
-        *params[param_clip_inR] = clip_inR;
-    }
-    if(params[param_clip_outL] != NULL) {
-        *params[param_clip_outL] = clip_outL;
-    }
-    if(params[param_clip_outR] != NULL) {
-        *params[param_clip_outR] = clip_outR;
-    }
-    
-    if(params[param_meter_inL] != NULL) {
-        *params[param_meter_inL] = meter_inL;
-    }
-    if(params[param_meter_inR] != NULL) {
-        *params[param_meter_inR] = meter_inR;
-    }
-    if(params[param_meter_outL] != NULL) {
-        *params[param_meter_outL] = meter_outL;
-    }
-    if(params[param_meter_outR] != NULL) {
-        *params[param_meter_outR] = meter_outR;
-    }
+    SET_IF_CONNECTED(clip_inL);
+    SET_IF_CONNECTED(clip_inR);
+    SET_IF_CONNECTED(clip_outL);
+    SET_IF_CONNECTED(clip_outR);
+    SET_IF_CONNECTED(meter_inL);
+    SET_IF_CONNECTED(meter_inR);
+    SET_IF_CONNECTED(meter_outL);
+    SET_IF_CONNECTED(meter_outR);
     // draw strip meters
     if(bypass > 0.5f) {
-        if(params[param_compression0] != NULL) {
-            *params[param_compression0] = 1.0f;
-        }
-        if(params[param_compression1] != NULL) {
-            *params[param_compression1] = 1.0f;
-        }
-        if(params[param_compression2] != NULL) {
-            *params[param_compression2] = 1.0f;
-        }
-        if(params[param_compression3] != NULL) {
-            *params[param_compression3] = 1.0f;
-        }
-
-        if(params[param_output0] != NULL) {
-            *params[param_output0] = 0.0f;
-        }
-        if(params[param_output1] != NULL) {
-            *params[param_output1] = 0.0f;
-        }
-        if(params[param_output2] != NULL) {
-            *params[param_output2] = 0.0f;
-        }
-        if(params[param_output3] != NULL) {
-            *params[param_output3] = 0.0f;
-        }
+        BYPASSED_COMPRESSION(0)
+        BYPASSED_COMPRESSION(1)
+        BYPASSED_COMPRESSION(2)
+        BYPASSED_COMPRESSION(3)
     } else {
-        if(params[param_compression0] != NULL) {
-            *params[param_compression0] = strip[0].get_comp_level();
-        }
-        if(params[param_compression1] != NULL) {
-            *params[param_compression1] = strip[1].get_comp_level();
-        }
-        if(params[param_compression2] != NULL) {
-            *params[param_compression2] = strip[2].get_comp_level();
-        }
-        if(params[param_compression3] != NULL) {
-            *params[param_compression3] = strip[3].get_comp_level();
-        }
-
-        if(params[param_output0] != NULL) {
-            *params[param_output0] = strip[0].get_output_level();
-        }
-        if(params[param_output1] != NULL) {
-            *params[param_output1] = strip[1].get_output_level();
-        }
-        if(params[param_output2] != NULL) {
-            *params[param_output2] = strip[2].get_output_level();
-        }
-        if(params[param_output3] != NULL) {
-            *params[param_output3] = strip[3].get_output_level();
-        }
+        ACTIVE_COMPRESSION(0)
+        ACTIVE_COMPRESSION(1)
+        ACTIVE_COMPRESSION(2)
+        ACTIVE_COMPRESSION(3)
     }
     // whatever has to be returned x)
     return outputs_mask;
 }
-bool multibandcompressor_audio_module::get_graph(int index, int subindex, float *data, int points, cairo_iface *context) const
+
+const gain_reduction_audio_module *multibandcompressor_audio_module::get_strip_by_param_index(int index) const
 {
     // let's handle by the corresponding strip
     switch (index) {
         case param_compression0:
-            return strip[0].get_graph(subindex, data, points, context);
-            break;
+            return &strip[0];
         case param_compression1:
-            return strip[1].get_graph(subindex, data, points, context);
-            break;
+            return &strip[1];
         case param_compression2:
-            return strip[2].get_graph(subindex, data, points, context);
-            break;
+            return &strip[2];
         case param_compression3:
-            return strip[3].get_graph(subindex, data, points, context);
-            break;
+            return &strip[3];
     }
+    return NULL;
+}
+
+bool multibandcompressor_audio_module::get_graph(int index, int subindex, float *data, int points, cairo_iface *context) const
+{
+    const gain_reduction_audio_module *m = get_strip_by_param_index(index);
+    if (m)
+        return m->get_graph(subindex, data, points, context);
     return false;
 }
 
 bool multibandcompressor_audio_module::get_dot(int index, int subindex, float &x, float &y, int &size, cairo_iface *context) const
 {
-    // let's handle by the corresponding strip
-    switch (index) {
-        case param_compression0:
-            return strip[0].get_dot(subindex, x, y, size, context);
-            break;
-        case param_compression1:
-            return strip[1].get_dot(subindex, x, y, size, context);
-            break;
-        case param_compression2:
-            return strip[2].get_dot(subindex, x, y, size, context);
-            break;
-        case param_compression3:
-            return strip[3].get_dot(subindex, x, y, size, context);
-            break;
-    }
+    const gain_reduction_audio_module *m = get_strip_by_param_index(index);
+    if (m)
+        return m->get_dot(subindex, x, y, size, context);
     return false;
 }
 
 bool multibandcompressor_audio_module::get_gridline(int index, int subindex, float &pos, bool &vertical, std::string &legend, cairo_iface *context) const
 { 
-    // let's handle by the corresponding strip
-    switch (index) {
-        case param_compression0:
-            return strip[0].get_gridline(subindex, pos, vertical, legend, context);
-            break;
-        case param_compression1:
-            return strip[1].get_gridline(subindex, pos, vertical, legend, context);
-            break;
-        case param_compression2:
-            return strip[2].get_gridline(subindex, pos, vertical, legend, context);
-            break;
-        case param_compression3:
-            return strip[3].get_gridline(subindex, pos, vertical, legend, context);
-            break;
-    }
+    const gain_reduction_audio_module *m = get_strip_by_param_index(index);
+    if (m)
+        return m->get_gridline(subindex, pos, vertical, legend, context);
     return false;
 }
 
 int multibandcompressor_audio_module::get_changed_offsets(int index, int generation, int &subindex_graph, int &subindex_dot, int &subindex_gridline) const
 {
-    // let's handle by the corresponding strip
-    switch (index) {
-        case param_compression0:
-            return strip[0].get_changed_offsets(generation, subindex_graph, subindex_dot, subindex_gridline);
-            break;
-        case param_compression1:
-            return strip[1].get_changed_offsets(generation, subindex_graph, subindex_dot, subindex_gridline);
-            break;
-        case param_compression2:
-            return strip[2].get_changed_offsets(generation, subindex_graph, subindex_dot, subindex_gridline);
-            break;
-        case param_compression3:
-            return strip[3].get_changed_offsets(generation, subindex_graph, subindex_dot, subindex_gridline);
-            break;
-    }
+    const gain_reduction_audio_module *m = get_strip_by_param_index(index);
+    if (m)
+        return m->get_changed_offsets(generation, subindex_graph, subindex_dot, subindex_gridline);
     return 0;
 }
 
@@ -1534,6 +1448,19 @@ void gain_reduction_audio_module::deactivate()
     is_active = false;
 }
 
+void gain_reduction_audio_module::update_curve()
+{
+    float linThreshold = threshold;
+    float linKneeSqrt = sqrt(knee);
+    linKneeStart = linThreshold / linKneeSqrt;
+    adjKneeStart = linKneeStart*linKneeStart;
+    float linKneeStop = linThreshold * linKneeSqrt;
+    thres = log(linThreshold);
+    kneeStart = log(linKneeStart);
+    kneeStop = log(linKneeStop);
+    compressedKneeStop = (kneeStop - thres) / ratio + thres;
+}
+
 void gain_reduction_audio_module::process(float &left, float &right, float det_left, float det_right)
 {
     if(!det_left) {
@@ -1548,17 +1475,9 @@ void gain_reduction_audio_module::process(float &left, float &right, float det_l
         // greatest sounding compressor I've heard!
         bool rms = detection == 0;
         bool average = stereo_link == 0;
-        float linThreshold = threshold;
         float attack_coeff = std::min(1.f, 1.f / (attack * srate / 4000.f));
         float release_coeff = std::min(1.f, 1.f / (release * srate / 4000.f));
-        float linKneeSqrt = sqrt(knee);
-        linKneeStart = linThreshold / linKneeSqrt;
-        adjKneeStart = linKneeStart*linKneeStart;
-        float linKneeStop = linThreshold * linKneeSqrt;
-        thres = log(linThreshold);
-        kneeStart = log(linKneeStart);
-        kneeStop = log(linKneeStop);
-        compressedKneeStop = (kneeStop - thres) / ratio + thres;
+        update_curve();
         
         float absample = average ? (fabs(det_left) + fabs(det_right)) * 0.5f : std::max(fabs(det_left), fabs(det_right));
         if(rms) absample *= absample;
@@ -1862,8 +1781,6 @@ inline void equalizerNband_audio_module<BaseClass, has_lphp>::process_hplp(float
     }
 }
 
-#define SET_IF_CONNECTED(param) if (params[AM::param_##param] != NULL) *params[AM::param_##param] = param;
-
 template<class BaseClass, bool has_lphp>
 uint32_t equalizerNband_audio_module<BaseClass, has_lphp>::process(uint32_t offset, uint32_t numsamples, uint32_t inputs_mask, uint32_t outputs_mask)
 {

-- 
calf audio plugins packaging



More information about the pkg-multimedia-commits mailing list