Fix Mackie control metering (fixes #6608).
authorLen Ovens <len@ovenwerks.net>
Tue, 29 Sep 2015 03:13:15 +0000 (20:13 -0700)
committerLen Ovens <len@ovenwerks.net>
Tue, 29 Sep 2015 03:13:15 +0000 (20:13 -0700)
libs/ardour/ardour/meter.h
libs/ardour/ardour/types.h
libs/ardour/enums.cc
libs/ardour/meter.cc
libs/surfaces/mackie/strip.cc

index 7539db2140c5e0be36654e36d364579e0e073cb0..a3bd34e1b78bbfc3e79298444ac1bbae50bd6d31 100644 (file)
@@ -97,6 +97,7 @@ private:
        std::vector<float> _peak_buffer; // internal, integrate
        std::vector<float> _peak_power;  // includes accurate falloff, hence dB
        std::vector<float> _max_peak_signal; // dB calculation is done on demand
+       float _combined_peak; // Mackie surfaces expect the highest peak of all track channels
 
        std::vector<Kmeterdsp *> _kmeter;
        std::vector<Iec1ppmdsp *> _iec1meter;
index f2facd340b2e4cc6d75e3692b9436502c3b2b0b6..5bd7b879290c416f0c0a99950f458b3c8c489068 100644 (file)
@@ -192,7 +192,8 @@ namespace ARDOUR {
                MeterIEC2EBU   = 0x0200,
                MeterVU        = 0x0400,
                MeterK12       = 0x0800,
-               MeterPeak0dB   = 0x1000
+               MeterPeak0dB   = 0x1000,
+               MeterMCP       = 0x2000
        };
 
        enum TrackMode {
index f3972f346c913850ea4a21dc7489e7d85231f042..d436200222097a9883bb4b46005d997570cd5381 100644 (file)
@@ -192,6 +192,7 @@ setup_enum_writer ()
        REGISTER_ENUM (MeterIEC2EBU);
        REGISTER_ENUM (MeterVU);
        REGISTER_ENUM (MeterPeak0dB);
+       REGISTER_ENUM (MeterMCP);
        REGISTER (_MeterType);
 
        REGISTER_ENUM (Normal);
index 8de49140962f3b9de99e54b665cd6530d4c84e76..fa9ee2fc6b1a7c13433021f283809312869d87a9 100644 (file)
@@ -47,6 +47,7 @@ PeakMeter::PeakMeter (Session& s, const std::string& name)
        _reset_dpm = true;
        _reset_max = true;
        _bufcnt = 0;
+       _combined_peak = 0;
 }
 
 PeakMeter::~PeakMeter ()
@@ -102,7 +103,7 @@ PeakMeter::run (BufferSet& bufs, framepos_t /*start_frame*/, framepos_t /*end_fr
        for (uint32_t i = 0; i < n_midi; ++i, ++n) {
                float val = 0.0f;
                const MidiBuffer& buf (bufs.get_midi(i));
-               
+
                for (MidiBuffer::const_iterator e = buf.begin(); e != buf.end(); ++e) {
                        const Evoral::MIDIEvent<framepos_t> ev(*e, false);
                        if (ev.is_note_on()) {
@@ -110,6 +111,11 @@ PeakMeter::run (BufferSet& bufs, framepos_t /*start_frame*/, framepos_t /*end_fr
                                if (this_vel > val) {
                                        val = this_vel;
                                }
+                               if (val > 0.01) {
+                                       if (_combined_peak < 0.01) {
+                                               _combined_peak = 0.01;
+                                       }
+                               }
                        } else {
                                val += 1.0 / bufs.get_midi(n).capacity();
                                if (val > 1.0) {
@@ -134,6 +140,7 @@ PeakMeter::run (BufferSet& bufs, framepos_t /*start_frame*/, framepos_t /*end_fr
                } else {
                        _peak_buffer[n] = compute_peak (bufs.get_audio(i).data(), nframes, _peak_buffer[n]);
                        _max_peak_signal[n] = std::max(_peak_buffer[n], _max_peak_signal[n]); // todo sync reset
+                       _combined_peak =std::max(_peak_buffer[n], _combined_peak);
                }
 
                if (do_reset_max) {
@@ -310,6 +317,7 @@ PeakMeter::set_max_channels (const ChanCount& chn)
 
 float
 PeakMeter::meter_level(uint32_t n, MeterType type) {
+       float mcptmp;
        switch (type) {
                case MeterKrms:
                case MeterK20:
@@ -354,6 +362,10 @@ PeakMeter::meter_level(uint32_t n, MeterType type) {
                                return _peak_power[n];
                        }
                        break;
+               case MeterMCP:
+                       mcptmp = _combined_peak;
+                       _combined_peak = 0;
+                       return accurate_coefficient_to_dB(mcptmp);
                case MeterMaxSignal:
                        assert(0);
                        break;
index 15459336737e5a6326e472da99c3ca7e591e35b1..9447b4121cf870f7acbe4b1bd1cf87071a56a1f4 100644 (file)
@@ -719,7 +719,7 @@ void
 Strip::update_meter ()
 {
        if (_meter && _transport_is_rolling && _metering_active) {
-               float dB = const_cast<PeakMeter&> (_route->peak_meter()).meter_level (0, MeterPeak);
+               float dB = const_cast<PeakMeter&> (_route->peak_meter()).meter_level (0, MeterMCP);
                _meter->send_update (*_surface, dB);
        }
 }