From 2515b2f38d4a1b38f2ec69735f0a85c702684dac Mon Sep 17 00:00:00 2001 From: Bill Somerville Date: Thu, 25 Jun 2015 22:41:13 +0000 Subject: [PATCH] Make the main window more portable and font change capable The Rx meter is now a better Qt citizen and can be resized. Added a more obvious peak signal indicator. It is now a custom widget derived from QFrame and is now directly added via promotion in Designer. Added a custom widget to act as a letter spin box, this is used for sub mode control. Switched the frequency tolerance widget to a combo box with preset values so that it is more uniform across systems and font sizes. Added container widgets for group control of various UI widgets such as QSO controls, DX call controls and WSPR controls. Introduced a stacked widget to allow the WSPR controls to be swapped in in place of the "QSO" controls. The "QSO" controls are are the Rx, Tx and related controls along with the main tab widget with the message buttons and fields. This means that the WSPR version of the main window (and EME Echo mode) are now much cleaner. Increased the size of the rig control widget and styled its colour using a dynamic property so that it can be defined in the Designer UI definition. Reinstated it as a push button to do a rig control reset and retry after an error. Reset most UI widgets to default properties, particularly removing any fixed sizes so that they can resize freely when fonts are changed. The overall layout is now controlled almost exclusively by stretch factors on some of the rows and columns of the various grid layout managers. git-svn-id: svn+ssh://svn.code.sf.net/p/wsjt/wsjt/branches/wsjtx@5630 ab8295b8-cf94-4d9e-aec4-7959e3be5d79 --- CMakeLists.txt | 2 + Configuration.cpp | 4 + HelpTextWindow.cpp | 29 + HelpTextWindow.hpp | 16 + LettersSpinBox.cpp | 27 + LettersSpinBox.hpp | 31 + mainwindow.cpp | 132 +- mainwindow.h | 5 +- mainwindow.ui | 3766 ++++++++++++++++++++------------------------ meterwidget.cpp | 64 +- meterwidget.h | 34 +- signalmeter.cpp | 107 +- signalmeter.h | 29 +- 13 files changed, 1950 insertions(+), 2296 deletions(-) create mode 100644 HelpTextWindow.cpp create mode 100644 HelpTextWindow.hpp create mode 100644 LettersSpinBox.cpp create mode 100644 LettersSpinBox.hpp diff --git a/CMakeLists.txt b/CMakeLists.txt index b29a4a20b..3c366a748 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -206,6 +206,8 @@ set (wsjt_qt_CXXSRCS DXLabSuiteCommanderTransceiver.cpp NetworkMessage.cpp MessageClient.cpp + LettersSpinBox.cpp + HelpTextWindow.cpp ) set (jt9_CXXSRCS diff --git a/Configuration.cpp b/Configuration.cpp index d01a91cee..143701eb2 100644 --- a/Configuration.cpp +++ b/Configuration.cpp @@ -2465,6 +2465,10 @@ void Configuration::impl::update_audio_channels (QComboBox const * source_combo_ void Configuration::impl::set_application_font (QFont const& font) { qApp->setStyleSheet (qApp->styleSheet () + "* {" + font_as_stylesheet (font) + '}'); + for (auto& widget : qApp->topLevelWidgets ()) + { + widget->updateGeometry (); + } } // load all the supported rig names into the selection combo box diff --git a/HelpTextWindow.cpp b/HelpTextWindow.cpp new file mode 100644 index 000000000..44d1a6232 --- /dev/null +++ b/HelpTextWindow.cpp @@ -0,0 +1,29 @@ +#include "HelpTextWindow.hpp" + +#include +#include +#include +#include +#include +#include + +#include "qt_helpers.hpp" + +HelpTextWindow::HelpTextWindow (QString const& title, QString const& file_name, QFont const& font, QWidget * parent) + : QLabel {parent, Qt::WindowCloseButtonHint | Qt::WindowMinimizeButtonHint} +{ + QFile source {file_name}; + if (!source.open (QIODevice::ReadOnly | QIODevice::Text)) + { + QMessageBox::warning (this, QApplication::applicationName () + , "Cannot open \"" + source.fileName () + + "\" for reading:" + source.errorString ()); + return; + } + setText (QTextStream {&source}.readAll ()); + setWindowTitle(QApplication::applicationName () + " - " + title); + setMargin (10); + setBackgroundRole (QPalette::Base); + setAutoFillBackground (true); + setStyleSheet (font_as_stylesheet (font)); +} diff --git a/HelpTextWindow.hpp b/HelpTextWindow.hpp new file mode 100644 index 000000000..c5793ae97 --- /dev/null +++ b/HelpTextWindow.hpp @@ -0,0 +1,16 @@ +#ifndef HELP_TEXT_WINDOW_HPP__ +#define HELP_TEXT_WINDOW_HPP__ + +#include +#include + +class QString; + +class HelpTextWindow final + : public QLabel +{ +public: + HelpTextWindow (QString const& title, QString const& file_name, QFont const& = QFont {}, QWidget * parent = nullptr); +}; + +#endif diff --git a/LettersSpinBox.cpp b/LettersSpinBox.cpp new file mode 100644 index 000000000..8cbe14223 --- /dev/null +++ b/LettersSpinBox.cpp @@ -0,0 +1,27 @@ +#include "LettersSpinBox.hpp" + +#include + +#include "moc_LettersSpinBox.cpp" + +QString LettersSpinBox::textFromValue (int value) const +{ + QString text; + do + { + auto digit = value % 26; + value /= 26; + text = QChar {lowercase_ ? 'a' + digit : 'A' + digit} + text; + } while (value); + return text; +} + +int LettersSpinBox::valueFromText (QString const& text) const +{ + int value {0}; + for (int index = text.size (); index > 0; --index) + { + value = value * 26 + text[index - 1].toLatin1 () - (lowercase_ ? 'a' : 'A'); + }; + return value; +} diff --git a/LettersSpinBox.hpp b/LettersSpinBox.hpp new file mode 100644 index 000000000..aaa37d7fe --- /dev/null +++ b/LettersSpinBox.hpp @@ -0,0 +1,31 @@ +#ifndef LETTERS_SPIN_BOX_HPP_ +#define LETTERS_SPIN_BOX_HPP_ + +#include + +class QString; + +// +// LettersSpinBox - select from consecutive letters +// +class LettersSpinBox final + : public QSpinBox +{ + Q_OBJECT + Q_PROPERTY (bool lowercase MEMBER lowercase_) + +public: + LettersSpinBox (QWidget * parent = nullptr) + : QSpinBox {parent} + , lowercase_ {false} + { + } + + QString textFromValue (int) const override; + int valueFromText (QString const&) const override; + +private: + bool lowercase_; +}; + +#endif diff --git a/mainwindow.cpp b/mainwindow.cpp index bd8999a24..398e5f594 100644 --- a/mainwindow.cpp +++ b/mainwindow.cpp @@ -16,6 +16,7 @@ #include #include #include +#include #include "revision_utils.hpp" #include "qt_helpers.hpp" @@ -38,6 +39,8 @@ #include "LiveFrequencyValidator.hpp" #include "MessageClient.hpp" #include "wsprnet.h" +#include "signalmeter.h" +#include "HelpTextWindow.hpp" #include "ui_mainwindow.h" #include "moc_mainwindow.cpp" @@ -64,32 +67,6 @@ namespace } } -class HelpTextWindow - : public QLabel -{ -public: - HelpTextWindow (QString const& title, QString const& file_name, QFont const& = QFont {}, QWidget * parent = nullptr); -}; - -HelpTextWindow::HelpTextWindow (QString const& title, QString const& file_name, QFont const& font, QWidget * parent) - : QLabel {parent, Qt::WindowCloseButtonHint | Qt::WindowMinimizeButtonHint} -{ - QFile source {file_name}; - if (!source.open (QIODevice::ReadOnly | QIODevice::Text)) - { - QMessageBox::warning (this, QApplication::applicationName () - , "Cannot open \"" + source.fileName () - + "\" for reading:" + source.errorString ()); - return; - } - setText (QTextStream {&source}.readAll ()); - setWindowTitle(QApplication::applicationName () + " - " + title); - setMargin (10); - setBackgroundRole (QPalette::Base); - setAutoFillBackground (true); - setStyleSheet (font_as_stylesheet (font)); -} - //--------------------------------------------------- MainWindow constructor MainWindow::MainWindow(bool multiple, QSettings * settings, QSharedMemory *shdmem, unsigned downSampleFactor, QWidget *parent) : @@ -346,12 +323,6 @@ MainWindow::MainWindow(bool multiple, QSettings * settings, QSharedMemory *shdme , &QLineEdit::editingFinished , [this] () {on_freeTextMsg_currentTextChanged (ui->freeTextMsg->lineEdit ()->text ());}); - auto font = ui->readFreq->font(); - font.setFamily("helvetica"); - font.setPointSize(9); - font.setWeight(75); - ui->readFreq->setFont(font); - connect(&m_guiTimer, &QTimer::timeout, this, &MainWindow::guiUpdate); m_guiTimer.start(100); //### Don't change the 100 ms! ### @@ -424,14 +395,12 @@ MainWindow::MainWindow(bool multiple, QSettings * settings, QSharedMemory *shdme m_lockTxFreq=false; m_baseCall = Radio::base_callsign (m_config.my_callsign ()); - ui->readFreq->setEnabled(false); m_QSOText.clear(); decodeBusy(false); m_MinW=0; m_nSubMode=0; - m_tol=500; m_DTtol=0.5; - m_wideGraph->setTol(m_tol); + m_wideGraph->setTol(500); m_bShMsgs=false; m_bTxTime=false; m_rxDone=false; @@ -441,9 +410,6 @@ MainWindow::MainWindow(bool multiple, QSettings * settings, QSharedMemory *shdme m_bEchoTxed=false; m_nWSPRdecodes=0; - signalMeter = new SignalMeter(ui->meterFrame); - signalMeter->resize(50, 160); - for(int i=0; i<28; i++) { //Initialize dBm values float dbm=(10.0*i)/3.0 - 30.0; int ndbm=0; @@ -571,16 +537,6 @@ MainWindow::MainWindow(bool multiple, QSettings * settings, QSharedMemory *shdme on_monitorButton_clicked (!m_config.monitor_off_at_startup ()); if(m_mode=="Echo") monitor(false); //Don't auto-start Monitor in Echo mode. - ui->labTol->setStyleSheet( \ - "QLabel { background-color : white; color : black; }"); - ui->labTol->setFrameStyle(QFrame::Panel | QFrame::Sunken); - ui->labMinW->setStyleSheet( \ - "QLabel { background-color : white; color : black; }"); - ui->labMinW->setFrameStyle(QFrame::Panel | QFrame::Sunken); - ui->labSubmode->setStyleSheet( \ - "QLabel { background-color : white; color : black; }"); - ui->labSubmode->setFrameStyle(QFrame::Panel | QFrame::Sunken); - bool b=m_config.enable_VHF_features() and (m_mode=="JT4" or m_mode=="JT65"); VHF_controls_visible(b); @@ -652,7 +608,7 @@ void MainWindow::writeSettings() m_settings->setValue("minW",ui->sbMinW->value()); m_settings->setValue("SubMode",ui->sbSubmode->value()); m_settings->setValue("DTtol",m_DTtol); - m_settings->setValue("Ftol",ui->sbTol->value()); + m_settings->setValue("FTol",ui->FTol_combo_box->currentText()); m_settings->setValue("MinSync",m_minSync); m_settings->setValue("EME",m_bEME); m_settings->setValue ("DialFreq", QVariant::fromValue(m_lastMonitoredFrequency)); @@ -706,7 +662,7 @@ void MainWindow::readSettings() ui->sbMinW->setMaximum(m_nSubMode); m_DTtol=m_settings->value("DTtol",0.5).toFloat(); ui->sbDT->setValue(m_DTtol); - ui->sbTol->setValue(m_settings->value("Ftol",4).toInt()); + ui->FTol_combo_box->setCurrentText(m_settings->value("FTol","500").toString ()); ui->syncSpinBox->setValue(m_settings->value("MinSync",0).toInt()); m_bEME=m_settings->value("EME",false).toBool(); ui->cbEME->setChecked(m_bEME); @@ -770,6 +726,7 @@ void MainWindow::setDecodedTextFont (QFont const& font) auto style_sheet = "QLabel {" + font_as_stylesheet (font) + '}'; ui->decodedTextLabel->setStyleSheet (ui->decodedTextLabel->styleSheet () + style_sheet); ui->decodedTextLabel2->setStyleSheet (ui->decodedTextLabel2->styleSheet () + style_sheet); + updateGeometry (); } //-------------------------------------------------------------- dataSink() @@ -802,7 +759,7 @@ void MainWindow::dataSink(qint64 frames) QString t; m_pctZap=nzap*100.0/m_nsps; t.sprintf(" Rx noise: %5.1f ",px); - signalMeter->setValue(px); // Update thermometer + ui->signal_meter_widget->setValue(px); // Update thermometer if(m_monitoring || m_diskData) { m_wideGraph->dataSink2(s,df3,ihsym,m_diskData); } @@ -921,9 +878,6 @@ void MainWindow::showStatusMessage(const QString& statusMsg) void MainWindow::on_actionSettings_triggered() //Setup Dialog { - ui->readFreq->setStyleSheet(""); - ui->readFreq->setEnabled(false); - // things that might change that we need know about auto callsign = m_config.my_callsign (); @@ -1554,8 +1508,8 @@ void MainWindow::decode() //decode() jt9com_.nfSplit=m_wideGraph->Fmin(); jt9com_.nfb=m_wideGraph->Fmax(); if(m_mode=="JT9" or m_mode=="JT9+JT65" or - (m_mode=="JT65" and !m_config.enable_VHF_features())) m_tol=20; - jt9com_.ntol=m_tol; + (m_mode=="JT65" and !m_config.enable_VHF_features())) ui->FTol_combo_box->setCurrentText ("20"); + jt9com_.ntol=ui->FTol_combo_box->currentText ().toInt (); if(jt9com_.nutc < m_nutc0) m_RxLog = 1; //Date and Time to all.txt m_nutc0=jt9com_.nutc; jt9com_.ntxmode=9; @@ -2173,7 +2127,7 @@ void MainWindow::guiUpdate() t.time().toString() + " "; ui->labUTC->setText(utc); if(!m_monitoring and !m_diskData) { - signalMeter->setValue(0); + ui->signal_meter_widget->setValue(0); } m_sec0=nsec; } @@ -2195,7 +2149,7 @@ void MainWindow::startTx2() if(t.mid(0,1)=="#") snr=t.mid(1,5).toDouble(); if(snr>0.0 or snr < -50.0) snr=99.0; transmit (snr); - signalMeter->setValue(0); + ui->signal_meter_widget->setValue(0); if(m_mode=="Echo" and !m_tune) m_bTransmittedEcho=true; if(m_mode.mid(0,4)=="WSPR" and !m_tune) { @@ -3149,7 +3103,6 @@ void MainWindow::on_actionWSPR_2_triggered() m_wideGraph->setPeriod(m_TRperiod,m_nsps); m_wideGraph->setMode(m_mode); m_wideGraph->setModeTx(m_modeTx); - VHF_controls_visible(false); WSPR_config(true); } @@ -3204,26 +3157,13 @@ void MainWindow::WSPR_config(bool b) { ui->decodedTextBrowser2->setVisible(!b); ui->decodedTextLabel2->setVisible(!b); + ui->controls_stack_widget->setCurrentIndex (b && m_mode != "Echo" ? 1 : 0); + ui->QSO_controls_widget->setVisible (!b); + ui->DX_controls_widget->setVisible (!b); + ui->WSPR_controls_widget->setVisible (b); ui->label_6->setVisible(!b); ui->label_7->setVisible(!b); - ui->pbTxMode->setVisible(!b); - ui->TxFreqSpinBox->setVisible(!b); - ui->RxFreqSpinBox->setVisible(!b); - ui->cbTxLock->setVisible(!b); - ui->txFirstCheckBox->setVisible(!b); - ui->pbR2T->setVisible(!b); - ui->pbT2R->setVisible(!b); - ui->rptSpinBox->setVisible(!b); - ui->label_8->setVisible(!b); - ui->labAz->setVisible(!b); - ui->labDist->setVisible(!b); ui->logQSOButton->setVisible(!b); - ui->label_3->setVisible(!b); - ui->label_4->setVisible(!b); - ui->dxCallEntry->setVisible(!b); - ui->dxGridEntry->setVisible(!b); - ui->lookupButton->setVisible(!b); - ui->addButton->setVisible(!b); ui->DecodeButton->setEnabled(!b); if(b and (m_mode!="Echo")) { ui->decodedTextLabel->setText( @@ -3238,6 +3178,7 @@ void MainWindow::WSPR_config(bool b) ui->tabWidget->setCurrentIndex (m_nonWSPRTab >= 0 ? m_nonWSPRTab : 1); m_bSimplex = false; } + updateGeometry (); } void MainWindow::on_TxFreqSpinBox_valueChanged(int n) @@ -3547,12 +3488,11 @@ void MainWindow::on_stopTxButton_clicked() //Stop Tx void MainWindow::rigOpen () { - ui->readFreq->setStyleSheet (""); + update_dynamic_property (ui->readFreq, "state", "warning"); ui->readFreq->setText (""); + ui->readFreq->setEnabled (true); m_config.transceiver_online (true); Q_EMIT m_config.sync_transceiver (true); - ui->readFreq->setStyleSheet("QPushButton{background-color: orange;" - "border-width: 0px; border-radius: 5px;}"); } void MainWindow::on_pbR2T_clicked() @@ -3648,15 +3588,15 @@ void MainWindow::handle_transceiver_update (Transceiver::TransceiverState s) qsy (s.frequency ()); } - ui->readFreq->setStyleSheet("QPushButton{background-color: #00ff00;" - "border-width: 0px; border-radius: 5px;}"); + update_dynamic_property (ui->readFreq, "state", "ok"); + ui->readFreq->setEnabled (false); ui->readFreq->setText (s.split () ? "S" : ""); } void MainWindow::handle_transceiver_failure (QString reason) { - ui->readFreq->setStyleSheet("QPushButton{background-color: red;" - "border-width: 0px; border-radius: 5px;}"); + update_dynamic_property (ui->readFreq, "state", "error"); + ui->readFreq->setEnabled (true); on_stopTxButton_clicked (); rigFailure ("Rig Control Error", reason); } @@ -3846,7 +3786,7 @@ void MainWindow::transmitDisplay (bool transmitting) if (transmitting == m_transmitting) { if (transmitting) { - signalMeter->setValue(0); + ui->signal_meter_widget->setValue(0); if (m_monitoring) monitor (false); m_btxok=true; } @@ -3884,13 +3824,9 @@ void MainWindow::transmitDisplay (bool transmitting) } } -void MainWindow::on_sbTol_valueChanged(int i) +void MainWindow::on_FTol_combo_box_currentIndexChanged (QString const& text) { - static int ntol[] = {10,20,50,100,200,500,1000,2000}; - m_tol=ntol[i]; - m_wideGraph->setTol(m_tol); - QString t="F Tol " + QString::number(ntol[i]); - ui->labTol->setText(t); + m_wideGraph->setTol (text.toInt ()); } void MainWindow::on_sbDT_valueChanged(double x) @@ -3900,17 +3836,7 @@ void MainWindow::on_sbDT_valueChanged(double x) void::MainWindow::VHF_controls_visible(bool b) { - ui->sbSubmode->setVisible(b); - ui->sbMinW->setVisible(b); - ui->cbShMsgs->setVisible(b); - ui->cbTx6->setVisible(b); - ui->labMinW->setVisible(b); - ui->labSubmode->setVisible(b); - ui->cbEME->setVisible(b); - ui->sbDT->setVisible(b); - ui->labTol->setVisible(b); - ui->sbTol->setVisible(b); - ui->syncSpinBox->setVisible(b); + ui->VHFControls_widget->setVisible (b); } void::MainWindow::VHF_features_enabled(bool b) @@ -3936,8 +3862,6 @@ void MainWindow::on_sbMinW_valueChanged(int n) { m_MinW=qMin(n,m_nSubMode); ui->sbMinW->setValue(m_MinW); - QString t="MinW " + (QString)QChar(short(n+65)); - ui->labMinW->setText(t); } void MainWindow::on_sbSubmode_valueChanged(int n) @@ -3946,8 +3870,6 @@ void MainWindow::on_sbSubmode_valueChanged(int n) m_wideGraph->setSubMode(m_nSubMode); ui->sbMinW->setMaximum(m_nSubMode); QString t1=(QString)QChar(short(m_nSubMode+65)); - QString t="Submode " + t1; - ui->labSubmode->setText(t); mode_label->setText(m_mode + " " + t1); } diff --git a/mainwindow.h b/mainwindow.h index 49bf8117d..c749aacfb 100644 --- a/mainwindow.h +++ b/mainwindow.h @@ -28,7 +28,6 @@ #include "WSPRBandHopping.hpp" #include "Transceiver.hpp" #include "psk_reporter.h" -#include "signalmeter.h" #include "logbook/logbook.h" #include "Detector.hpp" #include "Modulator.hpp" @@ -202,7 +201,7 @@ private slots: void stopTuneATU(); void auto_tx_mode (bool); void on_actionMessage_averaging_triggered(); - void on_sbTol_valueChanged(int i); + void on_FTol_combo_box_currentIndexChanged(QString const&); void on_actionInclude_averaging_triggered(); void on_actionInclude_correlation_triggered(); void on_sbDT_valueChanged(double x); @@ -325,7 +324,6 @@ private: qint32 m_astroFont; qint32 m_nSubMode; qint32 m_MinW; - qint32 m_tol; qint32 m_nclearave; qint32 m_minSync; qint32 m_dBm; @@ -462,7 +460,6 @@ private: QDateTime m_dateTimeQSO; QSharedMemory *mem_jt9; - SignalMeter *signalMeter; LogBook m_logBook; DecodedText m_QSOText; unsigned m_msAudioOutputBuffered; diff --git a/mainwindow.ui b/mainwindow.ui index 98d47101e..aa052f547 100644 --- a/mainwindow.ui +++ b/mainwindow.ui @@ -6,28 +6,10 @@ 0 0 - 825 - 480 + 934 + 565 - - - 0 - 0 - - - - - 0 - 480 - - - - - 1280 - 1028 - - WSJT-X by K1JT @@ -37,12 +19,9 @@ - - - QLayout::SetDefaultConstraint - + - + 3 @@ -141,6 +120,16 @@ + + + + QFrame::Plain + + + Qt::Horizontal + + + @@ -233,26 +222,13 @@ - - - - - 500 - 16777215 - + + + + QFrame::Plain - - - 10 - 50 - false - - - - Rx Frequency - - - Qt::AlignCenter + + Qt::Horizontal @@ -279,23 +255,26 @@ - - - - QFrame::Plain + + + + + 500 + 16777215 + - - Qt::Horizontal + + + 10 + 50 + false + - - - - - - QFrame::Plain + + Rx Frequency - - Qt::Horizontal + + Qt::AlignCenter @@ -304,7 +283,7 @@ 0 - 1 + 10 @@ -336,9 +315,9 @@ true - + 0 - 1 + 10 @@ -556,702 +535,1596 @@ - - - - - + + + + + + 0 + 0 + + + + USB dial frequency + + + QLabel { + font-family: MS Shell Dlg 2; + font-size: 16pt; + color : yellow; + background-color : black; +} +QLabel[oob="true"] { + background-color: red; +} + + + + 14.078 000 + + + Qt::AlignCenter + + + 5 + + + + + + + 0 + + + + + 0 + + + 0 + + + 0 + + + 0 + - + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Qt::AlignCenter + + + MinW + + + 0 + + + 2 + + + + + + + Tolerance for expected time offset. + + + Qt::AlignCenter + + + DT Tol + + + 1 + + + 0.100000000000000 + + + 3.000000000000000 + + + 0.100000000000000 + + + 0.500000000000000 + + + + + + + Qt::AlignCenter + + + Sync + + + 10 + + + 1 + + + + + + + Qt::AlignCenter + + + Submode + + + 0 + + + 6 + + + + + + + + + F Tol: + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + FTol_combo_box + + + + + + + 10 + + + QComboBox::NoInsert + + + 8 + + + + 10 + + + + + 20 + + + + + 50 + + + + + 100 + + + + + 200 + + + + + 500 + + + + + 1000 + + + + + 2000 + + + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 60 + 16777215 + + + + Check to generate JT4 or JT65 shorthand messages. + + + Sh + + + + + + + false + + + Check to generate "@1250 (SEND MSGS)" in Tx6. + + + Tx6 + + + + + + + + 16777215 + 16777215 + + + + Check to add 2.5 s to expected propagation delay. + + + EME delay + + + + + + + + + + + + + 0 + 0 + + + + Set Tx frequency to Rx Frequency + + + Tx<Rx + + + + + + + Audio Rx frequency + + + Qt::AlignCenter + + + Hz + + + Rx + + + 200 + + + 5000 + + + 1500 + + + + + + + Check to Tx in even minutes, uncheck for odd minutes + + + Tx even + + + + + + + + 0 + 0 + + + + Set Rx frequency to Tx Frequency + + + Rx<Tx + + + + + + + false + + + Toggle Tx mode + + + Tx JT9 @ + + + + + + + 5 + + + + + <html><head/><body><p>Signal report (dB)</p></body></html> + + + Report + + + -50 + + + 49 + + + -15 + + + + + + + + + Audio Tx frequency + + + Qt::AlignCenter + + + Hz + + + Tx + + + 200 + + + 5000 + + + 1500 + + + + + + + <html><head/><body><p>Tx frequency tracks Rx frequency</p></body></html> + + + Lock Tx=Rx + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + QTabWidget::West + + + QTabWidget::Triangular + + + 1 + + + + 1 + + + + 6 + + + 6 + + + 6 + + + 6 + + + + + + 2 + 0 + + + + Generate standard messages for minimal QSO + + + Generate Std Msgs + + + + + + + Queue up the next Tx message + + + Next + + + + + + + Switch to this Tx message NOW + + + Now + + + Qt::AlignCenter + + + + + + + + 2 + 0 + + + + + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+1 + + + false + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Qt::LeftToRight + + + Tx &1 + + + Alt+1 + + + + + + + + 2 + 0 + + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+2 + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Tx &2 + + + Alt+2 + + + + + + + + 2 + 0 + + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+3 + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Tx &3 + + + Alt+3 + + + + + + + + 2 + 0 + + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+4 + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Tx &4 + + + Alt+4 + + + + + + + + 2 + 0 + + + + Enter a free text message (maximum 13 characters) +or select a predefined macro from the dropdown list. +Press ENTER to add the current text to the predefined +list. The list can be maintained in Settings (F2). + + + true + + + QComboBox::InsertAtBottom + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+5 + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Tx &5 + + + Alt+5 + + + + + + + + 2 + 0 + + + + + + + + + + + Send this message in next Tx interval + + + + + + Ctrl+6 + + + true + + + buttonGroup + + + + + + + Switch to this Tx message NOW + + + Tx &6 + + + Alt+6 + + + + + + + + 2 + + + + 6 + + + 6 + + + 6 + + + 6 + + + + + 2 + + + + + + 2 + 0 + + + + + 0 + 30 + + + + + 16777215 + 30 + + + + Calling CQ + + + Qt::AlignCenter + + + + + + + + 2 + 0 + + + + Generate a CQ message + + + CQ + + + + + + + + 2 + 0 + + + + Generate message with RRR + + + RRR + + + + + + + + 2 + 0 + + + + Generate message with report + + + dB + + + + + + + + 2 + 0 + + + + + 0 + 30 + + + + + 16777215 + 30 + + + + Answering CQ + + + Qt::AlignCenter + + + + + + + + 2 + 0 + + + + Generate message for replying to a CQ + + + Grid + + + + + + + + 2 + 0 + + + + Generate message with R+report + + + R+dB + + + + + + + + 2 + 0 + + + + Generate message with 73 + + + 73 + + + + + + + + + + + + 3 + 0 + + + + + + + + + 1 + 0 + + + + + 0 + 26 + + + + Send this standard (generated) message + + + Gen msg + + + true + + + + + + + + + + + + 3 + 0 + + + + + 150 + 0 + + + + Enter a free text message (maximum 13 characters) +or select a predefined macro from the dropdown list. +Press ENTER to add the current text to the predefined +list. The list can be maintained in Settings (F2). + + + true + + + QComboBox::InsertAtBottom + + + + + + + + 1 + 0 + + + + Send this free-text message (max 13 characters) + + + Free msg + + + + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + - Qt::Horizontal - - - QSizePolicy::Fixed + Qt::Vertical - 10 - 20 + 20 + 40 - - - - 60 - 16777215 - - - - Check to generate JT4 or JT65 shorthand messages. - - - Sh - + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Band Hopping + + + true + + + + + + Schedule ... + + + + + + + + + + Qt::AlignCenter + + + % + + + Tx Pct + + + 100 + + + 20 + + + + + + + Upload spots + + + + + + + Qt::AlignCenter + + + Hz + + + Tx + + + 1400 + + + 1600 + + + 1500 + + + + + + + QPushButton:checked { + background-color: red; + border-style: outset; + border-width: 1px; + border-radius: 5px; + border-color: black; + min-width: 5em; + padding: 3px; +} + + + Tx Next + + + true + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + - - - false + + + Qt::Vertical - - Check to generate "@1250 (SEND MSGS)" in Tx6. + + + 20 + 40 + - - Tx6 - - + - - - - - - 0 - 0 - - - - - 48 - 16777215 - - - - Set Rx frequency to Tx Frequency - - - Rx<Tx - - - - - - - <html><head/><body><p>Tx frequency tracks Rx frequency</p></body></html> - - - Lock Tx=Rx - - - - - - - 5 - - - - - - 0 - 0 - - - - Report - - - - - - - - 0 - 0 - - - - - 40 - 0 - - - - - 45 - 16777215 - - - - <html><head/><body><p>Signal report (dB)</p></body></html> - - - -50 - - - 49 - - - -15 - - - - - - - - - Tolerance for expected time offset. - - - DT Tol - - - 1 - - - 0.100000000000000 - - - 3.000000000000000 - - - 0.100000000000000 - - - 0.500000000000000 - - - - - - - - 0 - 0 - - - - - 100 - 0 - - - - - 105 - 16777215 - - - - Audio Tx frequency - - - Qt::AlignCenter - - - Hz - - - Tx - - - 200 - - - 5000 - - - 1500 - - - - - - - false - - - Toggle Tx mode - - - Tx JT9 @ - - - - - - - - - Set the active submode for JT4 or JT65 - - - Submode A - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 18 - 16777215 - - - - 0 - - - 6 - - - - - - - - - Qt::Horizontal - - - QSizePolicy::Expanding - - - - 40 - 20 - - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - Qt::AlignCenter - - - Sync - - - 10 - - - 1 - - - - - - - - - Set minimum width expected for Doppler-spread tones - - - MinW A - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 18 - 16777215 - - - - 0 - - - 6 - - - - - - - - - - 16777215 - 16777215 - - - - Check to add 2.5 s to expected propagation delay. - - - EME delay - - - - - - - - 0 - 0 - - - - - 48 - 16777215 - - - - Set Tx frequency to Rx Frequency - - - Tx<Rx - - - - - - - - 0 - 0 - - - - - 100 - 20 - - - - Audio Rx frequency - - - Qt::AlignCenter - - - Hz - - - Rx - - - 200 - - - 5000 - - - 1500 - - - - - - - - 60 - 23 - - - - - 105 - 16777215 - - - - Check to Tx in even minutes, uncheck for odd minutes - - - Tx even - - - - - - - - - - 0 - 0 - - - - - 60 - 0 - - - - Tolerance for offset from selected Rx frequency. - - - F tol 500 - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 18 - 16777215 - - - - 7 - - - 5 - - - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - + + - - + + - + 0 0 - - - 0 - 23 - + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + + + + + + 252 + 252 + 252 + + + + + + + 159 + 175 + 213 + + + + + + + + + 252 + 252 + 252 + + + + + + + 159 + 175 + 213 + + + + + + + + + 159 + 175 + 213 + + + + + + + 159 + 175 + 213 + + + + + + + + true + + + DX Call + + + Qt::AlignCenter + + + 5 + + + 2 + + + + + + + + 0 + 0 + + + + + + + + + 252 + 252 + 252 + + + + + + + 159 + 175 + 213 + + + + + + + + + 252 + 252 + 252 + + + + + + + 159 + 175 + 213 + + + + + + + + + 159 + 175 + 213 + + + + + + + 159 + 175 + 213 + + + + + + + + true + + + DX Grid + + + Qt::AlignCenter + + + 5 + + + 2 + + + + + + + Callsign of station to be worked + + + + + + Qt::AlignCenter + + + + + + + Locator of station to be worked + + + + + + Qt::AlignCenter + + + + + + + + 0 + 0 + + + + true + + + + + + Qt::AlignCenter + + + 4 + + + + + + + + 0 + 0 + + + + + + + Qt::AlignCenter + + + + + + + Search for callsign in database + + + &Lookup + + + + + + + Add callsign and locator to database + + + Add + + + + + + + + + + Digital gain for audio input - - - - - - - 252 - 252 - 252 - - - - - - - 159 - 175 - 213 - - - - - - - - - 252 - 252 - 252 - - - - - - - 159 - 175 - 213 - - - - - - - - - 159 - 175 - 213 - - - - - - - 159 - 175 - 213 - - - - - + + -50 - - true + + 50 - - DX Call + + 20 - - Qt::AlignCenter + + QSlider::TicksBelow - - 2 + + 10 - - + + - + 0 0 - - - 0 - 23 - + + QFrame::Panel - - - 16777215 - 16777215 - - - - - - - - - 252 - 252 - 252 - - - - - - - 159 - 175 - 213 - - - - - - - - - 252 - 252 - 252 - - - - - - - 159 - 175 - 213 - - - - - - - - - 159 - 175 - 213 - - - - - - - 159 - 175 - 213 - - - - - - - - true - - - DX Grid - - - Qt::AlignCenter - - - 2 + + QFrame::Sunken - + Adjust Tx audio level @@ -1279,1364 +2152,14 @@ - - - - - 50 - 0 - - - - QFrame::StyledPanel - - - QFrame::Raised - - - - - - - - 0 - 0 - - - - - 0 - 160 - - - - - 20 - 160 - - - - Digital gain for audio input - - - -50 - - - 50 - - - 20 - - - Qt::Vertical - - - false - - - false - - - QSlider::TicksBelow - - - - - - - Pwr - - - - - - - - 15 - 15 - - - - <html><head/><body><p>If orange, click to read dial frequency</p></body></html> - - - - - - - - - - - 0 - 0 - - - - - 283 - 222 - - - - QFrame::NoFrame - - - QFrame::Plain - - - 0 - - - - 0 - - - 0 - - - 0 - - - 0 - - - 0 - - - - - - 0 - 0 - - - - - 0 - 200 - - - - - 0 - 0 - - - - QTabWidget::West - - - QTabWidget::Triangular - - - 1 - - - - 1 - - - - 0 - - - 4 - - - 1 - - - 0 - - - 0 - - - - - 6 - - - 5 - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Qt::LeftToRight - - - Tx &1 - - - Alt+1 - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+4 - - - buttonGroup - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+1 - - - false - - - buttonGroup - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+3 - - - buttonGroup - - - - - - - - 200 - 0 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - - - - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Tx &3 - - - Alt+3 - - - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Tx &4 - - - Alt+4 - - - - - - - Queue up the next Tx message - - - Next - - - - - - - - 200 - 0 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Tx &5 - - - Alt+5 - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+2 - - - buttonGroup - - - - - - - Switch to this Tx message NOW - - - Now - - - Qt::AlignCenter - - - - - - - - 200 - 0 - - - - - 150 - 0 - - - - - 150 - 16777215 - - - - Generate standard messages for minimal QSO - - - Generate Std Msgs - - - - - - - - 200 - 0 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - - - - - - 200 - 0 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Tx &6 - - - Alt+6 - - - - - - - - 40 - 16777215 - - - - Switch to this Tx message NOW - - - Tx &2 - - - Alt+2 - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+6 - - - true - - - buttonGroup - - - - - - - - 16 - 0 - - - - - 0 - 20 - - - - - 20 - 16777215 - - - - Send this message in next Tx interval - - - - - - Ctrl+5 - - - buttonGroup - - - - - - - - 200 - 0 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - - - - - - 0 - 200 - - - - - 150 - 24 - - - - - 150 - 16777215 - - - - Enter a free text message (maximum 13 characters) -or select a predefined macro from the dropdown list. -Press ENTER to add the current text to the predefined -list. The list can be maintained in Settings (F2). - - - true - - - QComboBox::InsertAtBottom - - - - - - - - - - 2 - - - - 0 - - - 0 - - - 0 - - - 0 - - - 0 - - - - - 6 - - - 2 - - - 2 - - - - - 2 - - - - - - 0 - 30 - - - - - 16777215 - 30 - - - - Calling CQ - - - Qt::AlignCenter - - - - - - - Generate a CQ message - - - CQ - - - - - - - Generate message with RRR - - - RRR - - - - - - - Generate message with report - - - dB - - - - - - - - 0 - 30 - - - - - 16777215 - 30 - - - - Answering CQ - - - Qt::AlignCenter - - - - - - - Generate message for replying to a CQ - - - Grid - - - - - - - Generate message with R+report - - - R+dB - - - - - - - Generate message with 73 - - - 73 - - - - - - - - - - - - 0 - 0 - - - - - 150 - 0 - - - - - - - - - 0 - 0 - - - - - 0 - 26 - - - - Send this standard (generated) message - - - Gen msg - - - true - - - - - - - - - - - - 150 - 0 - - - - Enter a free text message (maximum 13 characters) -or select a predefined macro from the dropdown list. -Press ENTER to add the current text to the predefined -list. The list can be maintained in Settings (F2). - - - true - - - QComboBox::InsertAtBottom - - - - - - - - 0 - 0 - - - - - 0 - 26 - - - - Send this free-text message (max 13 characters) - - - Free msg - - - - - - - - - - - - 3 - - - - - 30 - 22 - 221 - 161 - - - - - - - Band Hopping - - - true - - - - - - Schedule ... - - - - - - - - - - Upload spots - - - - - - - - 16777215 - 20 - - - - - 10 - - - - WSPR Mode - - - Qt::AlignCenter - - - - - - - QPushButton:checked { - background-color: red; - border-style: outset; - border-width: 1px; - border-radius: 5px; - border-color: black; - min-width: 5em; - padding: 3px; -} - - - Tx Next - - - true - - - - - - - Qt::AlignCenter - - - Hz - - - Tx - - - 1400 - - - 1600 - - - 1500 - - - - - - - - - - Qt::Horizontal - - - - 5 - 17 - - - - - - - - Qt::AlignCenter - - - % - - - Tx Pct - - - 100 - - - 20 - - - - - - - - - - - - - - - - 0 - 0 - - - - - 160 - 30 - - - - - 158 - 16777215 - - - - USB dial frequency - - - QLabel { - font-family: MS Shell Dlg 2; - font-size: 16pt; - color : yellow; - background-color : black; -} -QLabel[oob="true"] { - background-color: red; -} - - - - 14.078 - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 100 - 0 - - - - - 100 - 16777215 - - - - Select operating band or frequency in MHz - - - true - - - QComboBox::NoInsert - - - - - - - - 0 - 0 - - - - - 70 - 27 - - - - - 74 - 16777215 - - - - Callsign of station to be worked - - - - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 70 - 27 - - - - - 74 - 16777215 - - - - Locator of station to be worked - - - - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 0 - 23 - - - - - 16777215 - 23 - - - - true - - - - - - Qt::AlignCenter - - - 4 - - - - - - - - 0 - 0 - - - - - 0 - 23 - - - - - 16777215 - 23 - - - - - - - Qt::AlignCenter - - - - - - - - 0 - 0 - - - - - 74 - 16777215 - - - - Search for callsign in database - - - &Lookup - - - - - - - - 0 - 0 - - - - - 74 - 16777215 - - - - Add callsign and locator to database - - - Add - - - - + - + 0 0 - - - 130 - 60 - - - - - 158 - 60 - - QLabel { font-family: MS Shell Dlg 2; @@ -2658,44 +2181,80 @@ QLabel[oob="true"] { 0 - 01:23:45 + <html><head/><body><p align="center"> 2015 Jun 17 </p><p align="center"> 01:23:45 </p></body></html> Qt::AlignCenter + + 5 + - - - - Qt::Horizontal + + + + Pwr - - QSizePolicy::Preferred - - - - 40 - 20 - - - + - - - - Qt::Vertical + + + + false - - QSizePolicy::Fixed + + <html><head/><body><p>If orange or red there has been a rig control failure, click to reset and read the dial frequency.</p></body></html> - - - 20 - 1 - + + QPushButton { + font-family: helvetica; + font-size: 9pt; + font-weight: bold; + background-color: white; + color: black; + border-style: solid; + border-width:1px; + border-radius:10px; + border-color: gray; + max-width:20px; + max-height:20px; + min-width:20px; + min-height:20px; +} +QPushButton[state="error"] { + background-color: red; +} +QPushButton[state="warning"] { + background-color: orange; +} +QPushButton[state="ok"] { + background-color: #00ff00; +} - + + ? + + + + + + + + 0 + 0 + + + + Select operating band or frequency in MHz + + + true + + + QComboBox::NoInsert + + @@ -2708,7 +2267,7 @@ QLabel[oob="true"] { 0 0 - 825 + 934 21 @@ -3212,6 +2771,17 @@ QLabel[oob="true"] { QTextEdit
displaytext.h
+ + LettersSpinBox + QSpinBox +
LettersSpinBox.hpp
+
+ + SignalMeter + QFrame +
signalmeter.h
+ 1 +
logQSOButton @@ -3224,8 +2794,6 @@ QLabel[oob="true"] { tuneButton bandComboBox inGain - dxCallEntry - dxGridEntry txFirstCheckBox TxFreqSpinBox rptSpinBox diff --git a/meterwidget.cpp b/meterwidget.cpp index e36097e96..c22cdaab4 100644 --- a/meterwidget.cpp +++ b/meterwidget.cpp @@ -3,15 +3,20 @@ #include "meterwidget.h" +#include +#include + #include "moc_meterwidget.cpp" -MeterWidget::MeterWidget(QWidget *parent) : - QWidget(parent), - m_signal(0) +MeterWidget::MeterWidget(QWidget * parent) + : QWidget {parent} + , m_top_padding {0} + , m_bottom_padding {0} + , m_signal {0} { - for ( int i = 0; i < 10; i++ ) { - signalQueue.enqueue(0); - } + for ( int i = 0; i < 10; i++ ) { + signalQueue.enqueue(0); + } } void MeterWidget::setValue(int value) @@ -31,23 +36,34 @@ void MeterWidget::setValue(int value) update(); } -void MeterWidget::paintEvent( QPaintEvent * ) +QSize MeterWidget::sizeHint () const { - int pos; - QPainter p; - - p.begin(this); - - // Sanitize - m_signal = m_signal < 0 ? 0 : m_signal; - m_signal = m_signal > 60 ? 60 : m_signal; - - pos = m_signal * 2; - QRect r(0, height() - pos, width(), pos ); - p.fillRect(r, QColor( 255, 150, 0 )); - - // Draw peak hold indicator - p.setPen(Qt::black); - pos = m_sigPeak * 2; - p.drawLine(0, height() - pos, 10, height() - pos); + return {10, 100}; +} + +void MeterWidget::paintEvent (QPaintEvent * event) +{ + QWidget::paintEvent (event); + + // Sanitize + m_signal = m_signal < 0 ? 0 : m_signal; + m_signal = m_signal > 60 ? 60 : m_signal; + + QPainter p {this}; + p.setPen (Qt::NoPen); + + auto const& target = contentsRect (); + QRect r {QPoint {target.left (), static_cast (target.top () + target.height () - m_signal / 60. * target.height ())} + , QPoint {target.right (), target.bottom ()}}; + p.setBrush (QColor {255, 150, 0}); + p.drawRect (r); + + if (m_sigPeak) + { + // Draw peak hold indicator + auto peak = static_cast (target.top () + target.height () - m_sigPeak / 60. * target.height ()); + p.setBrush (Qt::black); + p.translate (target.left (), peak); + p.drawPolygon (QPolygon {{{0, -4}, {0, 4}, {target.width (), 0}}}); + } } diff --git a/meterwidget.h b/meterwidget.h index fbc27b6b9..52fa93352 100644 --- a/meterwidget.h +++ b/meterwidget.h @@ -3,29 +3,31 @@ #define METERWIDGET_H #include -#include #include class MeterWidget : public QWidget { - Q_OBJECT + Q_OBJECT + Q_PROPERTY (int value READ value WRITE setValue) + public: - explicit MeterWidget(QWidget *parent = 0); - -signals: - -public slots: - void setValue(int value); + explicit MeterWidget (QWidget *parent = 0); + + // value property + int value () const {return m_signal;} + Q_SLOT void setValue (int value); + + // QWidget implementation + QSize sizeHint () const override; +protected: + void paintEvent( QPaintEvent * ) override; private: - QQueue signalQueue; - - int m_signal; - int m_sigPeak; - -protected: - void paintEvent( QPaintEvent * ); - + int m_top_padding; + int m_bottom_padding; + QQueue signalQueue; + int m_signal; + int m_sigPeak; }; #endif // METERWIDGET_H diff --git a/signalmeter.cpp b/signalmeter.cpp index e21cb5a90..76d4b098d 100644 --- a/signalmeter.cpp +++ b/signalmeter.cpp @@ -1,55 +1,98 @@ // Simple bargraph dB meter // Implemented by Edson Pereira PY2SDR // -// Limits and geometry are hardcded for now. #include "signalmeter.h" +#include +#include +#include +#include +#include + +#include + #include "moc_signalmeter.cpp" -SignalMeter::SignalMeter(QWidget *parent) : - QWidget(parent) +class Scale final + : public QWidget { - resize(parent->size()); +public: + explicit Scale (QWidget * parent = 0) + : QWidget {parent} + { + setSizePolicy (QSizePolicy::Minimum, QSizePolicy::MinimumExpanding); + } - m_meter = new MeterWidget(this); - m_meter->setGeometry(10, 10, 10, 120); + QSize sizeHint () const override + { + return minimumSizeHint (); + } - m_label = new QLabel(this); - m_label->setGeometry(10, 135, 20, 20); + QSize minimumSizeHint () const override + { + QFontMetrics font_metrics {font (), nullptr}; + return {tick_length + text_indent + font_metrics.width ("00+"), (font_metrics.height () + line_spacing) * range}; + } - QLabel *dbLabel = new QLabel(this); - dbLabel->setText("dB"); - dbLabel->setGeometry(30, 135, 20, 20); -} +protected: + void paintEvent (QPaintEvent * event) override + { + QWidget::paintEvent (event); -SignalMeter::~SignalMeter() + QPainter p {this}; + auto const& target = contentsRect (); + QFontMetrics font_metrics {p.font (), this}; + auto font_offset = font_metrics.ascent () / 2; + p.drawLine (target.left (), target.top () + font_offset, target.left (), target.bottom () - font_offset - font_metrics.descent ()); + for (int i = 0; i <= range; ++i) + { + p.save (); + p.translate (target.left () + , target.top () + font_offset + i * (target.height () - font_metrics.ascent () - font_metrics.descent ()) / range); + p.drawLine (0, 0, tick_length, 0); + auto text = i ? QString::number ((range - i) * scale) : QString {"%1%2"}.arg ((range - i) * scale).arg ('+'); + p.drawText (tick_length + text_indent, font_offset, text); + p.restore (); + } + } + +private: + static int const tick_length {4}; + static int const text_indent {2}; + static int const line_spacing {0}; + static int const range {6}; + static int const scale {10}; +}; + +SignalMeter::SignalMeter (QWidget * parent) + : QFrame {parent} { + auto outer_layout = new QVBoxLayout; + outer_layout->setSpacing (0); -} + auto inner_layout = new QHBoxLayout; + inner_layout->setContentsMargins (9, 0, 9, 0); + inner_layout->setSpacing (0); -void SignalMeter::paintEvent( QPaintEvent * ) -{ - QPainter p; - p.begin(this); - p.drawLine(22, 10, 22, 130); + m_meter = new MeterWidget; + m_meter->setSizePolicy (QSizePolicy::Minimum, QSizePolicy::Minimum); + inner_layout->addWidget (m_meter); - for ( int i = 0; i <= 60; i += 10 ) { - p.drawLine(22, i*2 + 10, 25, i*2 + 10); - } + m_scale = new Scale; + inner_layout->addWidget (m_scale); - for ( int i = 10; i < 60; i += 10 ) { - p.drawText(30, i*2 + 15, QString::number(60 - i)); - } + m_reading = new QLabel(this); + + outer_layout->addLayout (inner_layout); + outer_layout->addWidget (m_reading); + setLayout (outer_layout); } void SignalMeter::setValue(int value) { - m_meter->setValue(value); - m_label->setText(QString::number(value)); -} - -void SignalMeter::resizeEvent(QResizeEvent *s) -{ - resize(s->size()); + QFontMetrics font_metrics {m_scale->font (), nullptr}; + m_meter->setContentsMargins (0, font_metrics.ascent () / 2, 0, font_metrics.ascent () / 2 + font_metrics.descent ()); + m_meter->setValue(value); + m_reading->setText (QString {"%1dB"}.arg (value, 4)); } diff --git a/signalmeter.h b/signalmeter.h index 30badc5df..cd70541a2 100644 --- a/signalmeter.h +++ b/signalmeter.h @@ -2,29 +2,26 @@ #ifndef SIGNALMETER_H #define SIGNALMETER_H -#include -#include -#include +#include -class SignalMeter : public QWidget +class QLabel; +class MeterWidget; + +class SignalMeter final + : public QFrame { - Q_OBJECT - + Q_OBJECT + public: - explicit SignalMeter(QWidget *parent = 0); - ~SignalMeter(); + explicit SignalMeter (QWidget * parent = nullptr); public slots: - void setValue(int value); + void setValue (int value); private: - MeterWidget *m_meter; - - QLabel *m_label; - -protected: - void paintEvent( QPaintEvent * ); - void resizeEvent(QResizeEvent *s); + MeterWidget * m_meter; + QWidget * m_scale; + QLabel * m_reading; }; #endif // SIGNALMETER_H