]> git.sesse.net Git - nageru/commitdiff
Add a stereo correlation meter.
authorSteinar H. Gunderson <sgunderson@bigfoot.com>
Fri, 15 Jan 2016 00:42:19 +0000 (01:42 +0100)
committerSteinar H. Gunderson <sgunderson@bigfoot.com>
Fri, 15 Jan 2016 00:42:19 +0000 (01:42 +0100)
Makefile
correlation_measurer.cpp
correlation_measurer.h
correlation_meter.cpp [new file with mode: 0644]
correlation_meter.h [new file with mode: 0644]
mainwindow.cpp
mainwindow.h
mixer.cpp
mixer.h
ui_mainwindow.ui

index 0ef287e454d4a2431baceeee40804438bcea9266..27d075041cf7b33fcd2d4bf6258c3098e18fc29a 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,11 +1,11 @@
 CXX=g++
 PKG_MODULES = Qt5Core Qt5Gui Qt5Widgets Qt5OpenGLExtensions Qt5OpenGL libusb-1.0 movit lua5.2 libmicrohttpd
-CXXFLAGS := -O2 -march=native -g -std=gnu++11 -Wall -Wno-deprecated-declarations -fPIC $(shell pkg-config --cflags $(PKG_MODULES)) -pthread -DMOVIT_SHADER_DIR=\"$(shell pkg-config --variable=shaderdir movit)\"
+CXXFLAGS := -O2 -march=native -g -std=gnu++11 -Wall -Wno-deprecated-declarations -Werror -fPIC $(shell pkg-config --cflags $(PKG_MODULES)) -pthread -DMOVIT_SHADER_DIR=\"$(shell pkg-config --variable=shaderdir movit)\"
 LDFLAGS=$(shell pkg-config --libs $(PKG_MODULES)) -lEGL -lGL -pthread -lva -lva-drm -lva-x11 -lX11 -lavformat -lavcodec -lavutil -lswscale -lzita-resampler -lasound
 
 # Qt objects
-OBJS=glwidget.o main.o mainwindow.o vumeter.o lrameter.o vu_common.o aboutdialog.o
-OBJS += glwidget.moc.o mainwindow.moc.o vumeter.moc.o lrameter.moc.o aboutdialog.moc.o
+OBJS=glwidget.o main.o mainwindow.o vumeter.o lrameter.o vu_common.o correlation_meter.o aboutdialog.o
+OBJS += glwidget.moc.o mainwindow.moc.o vumeter.moc.o lrameter.moc.o correlation_meter.moc.o aboutdialog.moc.o
 
 # Mixer objects
 OBJS += h264encode.o mixer.o bmusb/bmusb.o pbo_frame_allocator.o context.o ref_counted_frame.o theme.o resampling_queue.o httpd.o ebu_r128_proc.o flags.o image_input.o stereocompressor.o filter.o alsa_output.o correlation_measurer.o
index 888ebfff96aba810b7618b28736198466a573759..1e8ff750bb74f51f6a95c1da0ffec56ea992a0e0 100644 (file)
@@ -32,6 +32,11 @@ CorrelationMeasurer::CorrelationMeasurer(unsigned sample_rate,
 {
 }
 
+void CorrelationMeasurer::reset()
+{
+       zl = zr = zll = zlr = zrr = 0.0f;
+}
+
 void CorrelationMeasurer::process_samples(const std::vector<float> &samples)
 {
        assert(samples.size() % 2 == 0);
index 6d843408c04e9983b4f9eb7661e7e4c6e2377c0d..0c0ac72cc3dd6b37415f79b65ff9ff05a4a57f28 100644 (file)
@@ -38,6 +38,7 @@ public:
        CorrelationMeasurer(unsigned sample_rate, float lowpass_cutoff_hz = 1000.0f,
                            float falloff_seconds = 0.150f);
        void process_samples(const std::vector<float> &samples);  // Taken to be stereo, interleaved.
+       void reset();
        float get_correlation() const;
 
 private:
diff --git a/correlation_meter.cpp b/correlation_meter.cpp
new file mode 100644 (file)
index 0000000..b1080ca
--- /dev/null
@@ -0,0 +1,54 @@
+#include <QPainter>
+
+#include "correlation_meter.h"
+
+using namespace std;
+
+CorrelationMeter::CorrelationMeter(QWidget *parent)
+       : QWidget(parent)
+{
+}
+
+void CorrelationMeter::resizeEvent(QResizeEvent *event)
+{
+       on_pixmap = QPixmap(width(), height());
+       QPainter on_painter(&on_pixmap);
+       QLinearGradient on(0, 0, width(), 0);
+       on.setColorAt(0.0f, QColor(255, 0, 0));
+       on.setColorAt(0.5f, QColor(255, 255, 0));
+       on.setColorAt(0.8f, QColor(0, 255, 0));
+       on.setColorAt(0.95f, QColor(255, 255, 0));
+       on_painter.fillRect(0, 0, width(), height(), Qt::black);
+       on_painter.fillRect(1, 1, width() - 2, height() - 2, on);
+
+       off_pixmap = QPixmap(width(), height());
+       QPainter off_painter(&off_pixmap);
+       QLinearGradient off(0, 0, width(), 0);
+       off.setColorAt(0.0f, QColor(127, 0, 0));
+       off.setColorAt(0.5f, QColor(127, 127, 0));
+       off.setColorAt(0.8f, QColor(0, 127, 0));
+       off.setColorAt(0.95f, QColor(127, 127, 0));
+       off_painter.fillRect(0, 0, width(), height(), Qt::black);
+       off_painter.fillRect(1, 1, width() - 2, height() - 2, off);
+}
+
+void CorrelationMeter::paintEvent(QPaintEvent *event)
+{
+       QPainter painter(this);
+
+       float correlation;
+       {
+               unique_lock<mutex> lock(correlation_mutex);
+               correlation = this->correlation;
+       }
+
+       // Just in case.
+       correlation = std::min(std::max(correlation, -1.0f), 1.0f);
+
+       int pos = 3 + lrintf(0.5f * (correlation + 1.0f) * (width() - 6));
+       QRect off_rect(0, 0, width(), height());
+       QRect on_rect(pos - 2, 0, 5, height());
+
+       painter.drawPixmap(off_rect, off_pixmap, off_rect);
+       painter.drawPixmap(on_rect, on_pixmap, on_rect);
+}
diff --git a/correlation_meter.h b/correlation_meter.h
new file mode 100644 (file)
index 0000000..6dc0684
--- /dev/null
@@ -0,0 +1,31 @@
+#ifndef CORRELATION_METER_H
+#define CORRELATION_METER_H
+
+#include <QPaintEvent>
+#include <QWidget>
+#include <mutex>
+
+class CorrelationMeter : public QWidget
+{
+       Q_OBJECT
+
+public:
+       CorrelationMeter(QWidget *parent);
+
+       void set_correlation(float correlation) {
+               std::unique_lock<std::mutex> lock(correlation_mutex);
+               this->correlation = correlation;
+               QMetaObject::invokeMethod(this, "update", Qt::AutoConnection);
+       }
+
+private:
+       void resizeEvent(QResizeEvent *event) override;
+       void paintEvent(QPaintEvent *event) override;
+
+       std::mutex correlation_mutex;
+       float correlation = 0.0f;
+
+       QPixmap on_pixmap, off_pixmap;
+};
+
+#endif
index 311e573272de89d97f36173af23fca1dd5f81de0..77daf078b0000e643e2b7a5c2bc2aa0e931bed8a 100644 (file)
@@ -130,7 +130,7 @@ void MainWindow::mixer_created(Mixer *mixer)
                global_mixer->set_compressor_enabled(state == Qt::Checked);
        });
        connect(ui->reset_meters_button, &QPushButton::clicked, this, &MainWindow::reset_meters_button_clicked);
-       mixer->set_audio_level_callback(bind(&MainWindow::audio_level_callback, this, _1, _2, _3, _4, _5, _6, _7));
+       mixer->set_audio_level_callback(bind(&MainWindow::audio_level_callback, this, _1, _2, _3, _4, _5, _6, _7, _8));
 }
 
 void MainWindow::mixer_shutting_down()
@@ -215,7 +215,10 @@ void MainWindow::reset_meters_button_clicked()
        ui->peak_display->setStyleSheet("");
 }
 
-void MainWindow::audio_level_callback(float level_lufs, float peak_db, float global_level_lufs, float range_low_lufs, float range_high_lufs, float gain_staging_db, float final_makeup_gain_db)
+void MainWindow::audio_level_callback(float level_lufs, float peak_db, float global_level_lufs,
+                                      float range_low_lufs, float range_high_lufs,
+                                      float gain_staging_db, float final_makeup_gain_db,
+                                      float correlation)
 {
        timeval now;
        gettimeofday(&now, nullptr);
@@ -232,6 +235,7 @@ void MainWindow::audio_level_callback(float level_lufs, float peak_db, float glo
        post_to_main_thread([=]() {
                ui->vu_meter->set_level(level_lufs);
                ui->lra_meter->set_levels(global_level_lufs, range_low_lufs, range_high_lufs);
+               ui->correlation_meter->set_correlation(correlation);
 
                char buf[256];
                snprintf(buf, sizeof(buf), "%.1f", peak_db);
index 013217599efe2596c0f253b0af93ab3c354bd8b2..8ca728ae11196cc610c18d339db353314a931bf7 100644 (file)
@@ -53,7 +53,7 @@ private:
        void set_white_balance(int channel_number, int x, int y);
 
        // Called from the mixer.
-       void audio_level_callback(float level_lufs, float peak_db, float global_level_lufs, float range_low_lufs, float range_high_lufs, float gain_staging_db, float final_makeup_gain_db);
+       void audio_level_callback(float level_lufs, float peak_db, float global_level_lufs, float range_low_lufs, float range_high_lufs, float gain_staging_db, float final_makeup_gain_db, float correlation);
        timeval last_audio_level_callback{0, 0};
 
        Ui::MainWindow *ui;
index 00b3efef5032ef3ecfb0fd0c2100c506009bde96..39bae192c5bda7722f2aa527da80e62b990ba7fe 100644 (file)
--- a/mixer.cpp
+++ b/mixer.cpp
@@ -98,6 +98,7 @@ Mixer::Mixer(const QSurfaceFormat &format, unsigned num_cards)
          num_cards(num_cards),
          mixer_surface(create_surface(format)),
          h264_encoder_surface(create_surface(format)),
+         correlation(OUTPUT_FREQUENCY),
          level_compressor(OUTPUT_FREQUENCY),
          limiter(OUTPUT_FREQUENCY),
          compressor(OUTPUT_FREQUENCY)
@@ -534,7 +535,8 @@ void Mixer::thread_func()
 
                        audio_level_callback(loudness_s, 20.0 * log10(peak),
                                             loudness_i, loudness_range_low, loudness_range_high,
-                                            gain_staging_db, 20.0 * log10(final_makeup_gain));
+                                            gain_staging_db, 20.0 * log10(final_makeup_gain),
+                                            correlation.get_correlation());
                }
 
                for (unsigned card_index = 1; card_index < num_cards; ++card_index) {
@@ -822,13 +824,14 @@ void Mixer::process_audio_one_frame(int64_t frame_pts_int, int num_samples)
                final_makeup_gain = m;
        }
 
-       // Find R128 levels.
+       // Find R128 levels and L/R correlation.
        vector<float> left, right;
        deinterleave_samples(samples_out, &left, &right);
        float *ptrs[] = { left.data(), right.data() };
        {
                unique_lock<mutex> lock(compressor_mutex);
                r128.process(left.size(), ptrs);
+               correlation.process_samples(samples_out);
        }
 
        // Send the samples to the sound card.
@@ -933,6 +936,7 @@ void Mixer::reset_meters()
        peak = 0.0f;
        r128.reset();
        r128.integr_start();
+       correlation.reset();
 }
 
 Mixer::OutputChannel::~OutputChannel()
diff --git a/mixer.h b/mixer.h
index ffae67a6e398687640c155ae12d8dd81c33f11e0..961c2a6c20948d72db4ca150aa7ec8c570d8e44d 100644 (file)
--- a/mixer.h
+++ b/mixer.h
@@ -35,6 +35,7 @@
 #include "stereocompressor.h"
 #include "filter.h"
 #include "input_state.h"
+#include "correlation_measurer.h"
 
 class H264Encoder;
 class QSurface;
@@ -103,7 +104,8 @@ public:
 
        typedef std::function<void(float level_lufs, float peak_db,
                                   float global_level_lufs, float range_low_lufs, float range_high_lufs,
-                                  float gain_staging_db, float final_makeup_gain_db)> audio_level_callback_t;
+                                  float gain_staging_db, float final_makeup_gain_db,
+                                  float correlation)> audio_level_callback_t;
        void set_audio_level_callback(audio_level_callback_t callback)
        {
                audio_level_callback = callback;
@@ -288,6 +290,7 @@ private:
        audio_level_callback_t audio_level_callback = nullptr;
        std::mutex compressor_mutex;
        Ebu_r128_proc r128;  // Under compressor_mutex.
+       CorrelationMeasurer correlation;  // Under compressor_mutex.
 
        Resampler peak_resampler;
        std::atomic<float> peak{0.0f};
index c175c1d24632ab657cd5ea0e0bbdcde6050c21a0..cc041a8d95edbbc06bd25eaf370f95cc96e37afe 100644 (file)
@@ -27,7 +27,7 @@
     <item row="0" column="0">
      <layout class="QVBoxLayout" name="vertical_layout" stretch="0,0,0,0">
       <item>
-       <layout class="QHBoxLayout" name="me_displays" stretch="0,0,0,0,0">
+       <layout class="QHBoxLayout" name="me_displays" stretch="0,0,0,0">
         <item>
          <layout class="QVBoxLayout" name="preview_vertical_layout">
           <property name="leftMargin">
          </layout>
         </item>
         <item>
-         <layout class="QVBoxLayout" name="vu_meter_vertical_layout" stretch="1,0">
-          <property name="leftMargin">
+         <layout class="QVBoxLayout" name="audio_meters">
+          <property name="rightMargin">
            <number>0</number>
           </property>
-          <property name="bottomMargin">
-           <number>4</number>
-          </property>
           <item>
-           <layout class="QHBoxLayout" name="horizontalLayout">
-            <property name="bottomMargin">
-             <number>0</number>
+           <widget class="CorrelationMeter" name="correlation_meter" native="true">
+            <property name="sizePolicy">
+             <sizepolicy hsizetype="Preferred" vsizetype="Fixed">
+              <horstretch>0</horstretch>
+              <verstretch>0</verstretch>
+             </sizepolicy>
             </property>
-            <item>
-             <widget class="VUMeter" name="vu_meter" native="true">
-              <property name="sizePolicy">
-               <sizepolicy hsizetype="Fixed" vsizetype="Preferred">
-                <horstretch>0</horstretch>
-                <verstretch>1</verstretch>
-               </sizepolicy>
-              </property>
-              <property name="minimumSize">
-               <size>
-                <width>16</width>
-                <height>0</height>
-               </size>
-              </property>
-              <property name="sizeIncrement">
-               <size>
-                <width>1</width>
-                <height>0</height>
-               </size>
-              </property>
-              <property name="baseSize">
-               <size>
-                <width>0</width>
-                <height>0</height>
-               </size>
-              </property>
-              <property name="palette">
-               <palette>
-                <active>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>255</red>
-                    <green>255</green>
-                    <blue>255</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>5</red>
-                    <green>239</green>
-                    <blue>111</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </active>
-                <inactive>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>255</red>
-                    <green>255</green>
-                    <blue>255</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>5</red>
-                    <green>239</green>
-                    <blue>111</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </inactive>
-                <disabled>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>5</red>
-                    <green>239</green>
-                    <blue>111</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>5</red>
-                    <green>239</green>
-                    <blue>111</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </disabled>
-               </palette>
-              </property>
-              <property name="autoFillBackground">
-               <bool>true</bool>
-              </property>
-             </widget>
-            </item>
-           </layout>
-          </item>
-          <item>
-           <widget class="QLabel" name="peak_display">
             <property name="minimumSize">
              <size>
-              <width>30</width>
-              <height>0</height>
+              <width>0</width>
+              <height>14</height>
              </size>
             </property>
-            <property name="text">
-             <string>-0.0</string>
+            <property name="palette">
+             <palette>
+              <active>
+               <colorrole role="Base">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>255</red>
+                  <green>255</green>
+                  <blue>255</blue>
+                 </color>
+                </brush>
+               </colorrole>
+               <colorrole role="Window">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>239</red>
+                  <green>0</green>
+                  <blue>4</blue>
+                 </color>
+                </brush>
+               </colorrole>
+              </active>
+              <inactive>
+               <colorrole role="Base">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>255</red>
+                  <green>255</green>
+                  <blue>255</blue>
+                 </color>
+                </brush>
+               </colorrole>
+               <colorrole role="Window">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>239</red>
+                  <green>0</green>
+                  <blue>4</blue>
+                 </color>
+                </brush>
+               </colorrole>
+              </inactive>
+              <disabled>
+               <colorrole role="Base">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>239</red>
+                  <green>0</green>
+                  <blue>4</blue>
+                 </color>
+                </brush>
+               </colorrole>
+               <colorrole role="Window">
+                <brush brushstyle="SolidPattern">
+                 <color alpha="255">
+                  <red>239</red>
+                  <green>0</green>
+                  <blue>4</blue>
+                 </color>
+                </brush>
+               </colorrole>
+              </disabled>
+             </palette>
             </property>
-            <property name="alignment">
-             <set>Qt::AlignCenter</set>
+            <property name="autoFillBackground">
+             <bool>true</bool>
             </property>
            </widget>
           </item>
-         </layout>
-        </item>
-        <item>
-         <layout class="QVBoxLayout" name="lra_vertical_layout" stretch="1,0">
-          <property name="spacing">
-           <number>3</number>
-          </property>
-          <property name="leftMargin">
-           <number>0</number>
-          </property>
           <item>
-           <layout class="QHBoxLayout" name="horizontalLayout_2">
+           <layout class="QHBoxLayout" name="vu_meters">
             <item>
-             <widget class="LRAMeter" name="lra_meter" native="true">
-              <property name="sizePolicy">
-               <sizepolicy hsizetype="Fixed" vsizetype="Preferred">
-                <horstretch>0</horstretch>
-                <verstretch>0</verstretch>
-               </sizepolicy>
+             <layout class="QVBoxLayout" name="vu_meter_vertical_layout" stretch="1,0">
+              <property name="leftMargin">
+               <number>0</number>
               </property>
-              <property name="minimumSize">
-               <size>
-                <width>24</width>
-                <height>0</height>
-               </size>
+              <property name="bottomMargin">
+               <number>4</number>
               </property>
-              <property name="palette">
-               <palette>
-                <active>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>255</red>
-                    <green>255</green>
-                    <blue>255</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>0</red>
-                    <green>239</green>
-                    <blue>219</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </active>
-                <inactive>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>255</red>
-                    <green>255</green>
-                    <blue>255</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>0</red>
-                    <green>239</green>
-                    <blue>219</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </inactive>
-                <disabled>
-                 <colorrole role="Base">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>0</red>
-                    <green>239</green>
-                    <blue>219</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                 <colorrole role="Window">
-                  <brush brushstyle="SolidPattern">
-                   <color alpha="255">
-                    <red>0</red>
-                    <green>239</green>
-                    <blue>219</blue>
-                   </color>
-                  </brush>
-                 </colorrole>
-                </disabled>
-               </palette>
+              <item>
+               <layout class="QHBoxLayout" name="horizontalLayout">
+                <property name="bottomMargin">
+                 <number>0</number>
+                </property>
+                <item>
+                 <widget class="VUMeter" name="vu_meter" native="true">
+                  <property name="sizePolicy">
+                   <sizepolicy hsizetype="Fixed" vsizetype="Preferred">
+                    <horstretch>0</horstretch>
+                    <verstretch>1</verstretch>
+                   </sizepolicy>
+                  </property>
+                  <property name="minimumSize">
+                   <size>
+                    <width>16</width>
+                    <height>0</height>
+                   </size>
+                  </property>
+                  <property name="sizeIncrement">
+                   <size>
+                    <width>1</width>
+                    <height>0</height>
+                   </size>
+                  </property>
+                  <property name="baseSize">
+                   <size>
+                    <width>0</width>
+                    <height>0</height>
+                   </size>
+                  </property>
+                  <property name="palette">
+                   <palette>
+                    <active>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>255</red>
+                        <green>255</green>
+                        <blue>255</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>5</red>
+                        <green>239</green>
+                        <blue>111</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </active>
+                    <inactive>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>255</red>
+                        <green>255</green>
+                        <blue>255</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>5</red>
+                        <green>239</green>
+                        <blue>111</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </inactive>
+                    <disabled>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>5</red>
+                        <green>239</green>
+                        <blue>111</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>5</red>
+                        <green>239</green>
+                        <blue>111</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </disabled>
+                   </palette>
+                  </property>
+                  <property name="autoFillBackground">
+                   <bool>true</bool>
+                  </property>
+                 </widget>
+                </item>
+               </layout>
+              </item>
+              <item>
+               <widget class="QLabel" name="peak_display">
+                <property name="minimumSize">
+                 <size>
+                  <width>30</width>
+                  <height>0</height>
+                 </size>
+                </property>
+                <property name="text">
+                 <string>-0.0</string>
+                </property>
+                <property name="alignment">
+                 <set>Qt::AlignCenter</set>
+                </property>
+               </widget>
+              </item>
+             </layout>
+            </item>
+            <item>
+             <layout class="QVBoxLayout" name="lra_vertical_layout" stretch="1,0">
+              <property name="spacing">
+               <number>3</number>
               </property>
-              <property name="autoFillBackground">
-               <bool>true</bool>
+              <property name="leftMargin">
+               <number>0</number>
               </property>
-             </widget>
+              <item>
+               <layout class="QHBoxLayout" name="horizontalLayout_2">
+                <item>
+                 <widget class="LRAMeter" name="lra_meter" native="true">
+                  <property name="sizePolicy">
+                   <sizepolicy hsizetype="Fixed" vsizetype="Preferred">
+                    <horstretch>0</horstretch>
+                    <verstretch>0</verstretch>
+                   </sizepolicy>
+                  </property>
+                  <property name="minimumSize">
+                   <size>
+                    <width>24</width>
+                    <height>0</height>
+                   </size>
+                  </property>
+                  <property name="palette">
+                   <palette>
+                    <active>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>255</red>
+                        <green>255</green>
+                        <blue>255</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>0</red>
+                        <green>239</green>
+                        <blue>219</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </active>
+                    <inactive>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>255</red>
+                        <green>255</green>
+                        <blue>255</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>0</red>
+                        <green>239</green>
+                        <blue>219</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </inactive>
+                    <disabled>
+                     <colorrole role="Base">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>0</red>
+                        <green>239</green>
+                        <blue>219</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                     <colorrole role="Window">
+                      <brush brushstyle="SolidPattern">
+                       <color alpha="255">
+                        <red>0</red>
+                        <green>239</green>
+                        <blue>219</blue>
+                       </color>
+                      </brush>
+                     </colorrole>
+                    </disabled>
+                   </palette>
+                  </property>
+                  <property name="autoFillBackground">
+                   <bool>true</bool>
+                  </property>
+                 </widget>
+                </item>
+               </layout>
+              </item>
+              <item>
+               <widget class="QPushButton" name="reset_meters_button">
+                <property name="maximumSize">
+                 <size>
+                  <width>30</width>
+                  <height>20</height>
+                 </size>
+                </property>
+                <property name="text">
+                 <string>RST</string>
+                </property>
+                <property name="checked">
+                 <bool>false</bool>
+                </property>
+               </widget>
+              </item>
+             </layout>
             </item>
            </layout>
           </item>
-          <item>
-           <widget class="QPushButton" name="reset_meters_button">
-            <property name="maximumSize">
-             <size>
-              <width>30</width>
-              <height>20</height>
-             </size>
-            </property>
-            <property name="text">
-             <string>RST</string>
-            </property>
-            <property name="checked">
-             <bool>false</bool>
-            </property>
-           </widget>
-          </item>
          </layout>
         </item>
        </layout>
    <header>lrameter.h</header>
    <container>1</container>
   </customwidget>
+  <customwidget>
+   <class>CorrelationMeter</class>
+   <extends>QWidget</extends>
+   <header>correlation_meter.h</header>
+   <container>1</container>
+  </customwidget>
  </customwidgets>
  <resources/>
  <connections/>