Configurable custom HB and STATUS messages

This commit is contained in:
Jordan Sherer 2020-03-28 15:10:41 -04:00
parent 8528a47dad
commit 4b6d343850
8 changed files with 354 additions and 233 deletions

View File

@ -578,6 +578,7 @@ private:
unsigned transceiver_command_number_;
QString dynamic_grid_;
QString dynamic_info_;
QString dynamic_status_;
// configuration fields that we publish
bool auto_switch_bands_;
@ -591,7 +592,9 @@ private:
QStringList secondary_highlight_words_;
QString eot_;
QString my_info_;
QString my_status_;
QString cq_;
QString hb_;
QString reply_;
int callsign_aging_;
int activity_aging_;
@ -1070,6 +1073,21 @@ QString Configuration::my_info() const
return info.trimmed();
}
QString Configuration::my_status() const
{
auto status = m_->my_status_;
if(m_->use_dynamic_info_ && !m_->dynamic_status_.isEmpty()){
status = m_->dynamic_status_;
}
return status.trimmed();
}
QString Configuration::hb_message() const
{
return m_->hb_.trimmed();
}
QString Configuration::cq_message() const
{
return m_->cq_.trimmed().replace("CQCQCQ", "CQ CQ CQ"); // deprecate legacy
@ -1100,6 +1118,12 @@ void Configuration::set_dynamic_station_info(QString const& info)
m_->dynamic_info_ = info.trimmed ();
}
void Configuration::set_dynamic_station_status(QString const& status)
{
m_->dynamic_status_ = status.trimmed ();
}
namespace
{
#if defined (Q_OS_MAC)
@ -1261,14 +1285,18 @@ Configuration::impl::impl (Configuration * self, QDir const& temp_directory,
ui_->info_message_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
ui_->reply_message_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
ui_->cq_message_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
ui_->hb_message_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
ui_->status_message_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
ui_->groups_line_edit->setValidator (new QRegExpValidator {message_alphabet, this});
setUppercase(ui_->callsign_line_edit);
setUppercase(ui_->grid_line_edit);
setUppercase(ui_->add_macro_line_edit);
setUppercase(ui_->info_message_line_edit);
setUppercase(ui_->status_message_line_edit);
setUppercase(ui_->reply_message_line_edit);
setUppercase(ui_->cq_message_line_edit);
setUppercase(ui_->hb_message_line_edit);
setUppercase(ui_->groups_line_edit);
setUppercase(ui_->auto_whitelist_line_edit);
@ -1476,7 +1504,9 @@ void Configuration::impl::initialize_models ()
ui_->secondaryHighlightLineEdit->setText(secondary_highlight_words_.join(", "));
ui_->eot_line_edit->setText(eot_.trimmed().left(2));
ui_->info_message_line_edit->setText (my_info_.toUpper());
ui_->status_message_line_edit->setText (my_status_.toUpper());
ui_->cq_message_line_edit->setText(cq_.toUpper().replace("CQCQCQ", "CQ CQ CQ"));
ui_->hb_message_line_edit->setText(hb_.toUpper());
ui_->reply_message_line_edit->setText (reply_.toUpper());
ui_->use_dynamic_grid->setChecked(use_dynamic_info_);
@ -1753,6 +1783,8 @@ void Configuration::impl::read_settings ()
activity_aging_ = settings_->value ("ActivityAging", 2).toInt ();
eot_ = settings_->value("EOTCharacter", QString{"\u2662"}).toString().trimmed().left(2);
my_info_ = settings_->value("MyInfo", QString {}).toString();
my_status_ = settings_->value("MyStatus", QString {"IDLE <MYIDLE> VERSION <MYVERSION>"}).toString();
hb_ = settings_->value("HBMessage", QString {"HB <MYGRID4>"}).toString();
cq_ = settings_->value("CQMessage", QString {"CQ CQ CQ <MYGRID4>"}).toString();
reply_ = settings_->value("Reply", QString {"HW CPY?"}).toString();
next_color_cq_ = color_cq_ = settings_->value("colorCQ","#66ff66").toString();
@ -2070,7 +2102,9 @@ void Configuration::impl::write_settings ()
settings_->setValue ("SecondaryHighlightWords", secondary_highlight_words_);
settings_->setValue ("EOTCharacter", eot_);
settings_->setValue ("MyInfo", my_info_);
settings_->setValue ("MyStatus", my_status_);
settings_->setValue ("CQMessage", cq_);
settings_->setValue ("HBMessage", hb_);
settings_->setValue ("Reply", reply_);
settings_->setValue ("CallsignAging", callsign_aging_);
settings_->setValue ("ActivityAging", activity_aging_);
@ -2435,6 +2469,12 @@ bool Configuration::impl::validate ()
}
}
auto hb = ui_->hb_message_line_edit->text().toUpper().trimmed();
if(!hb.isEmpty() && !(hb.startsWith("HB") || hb.contains(callsign))){
MessageBox::critical_message (this, QString("The HB message format is invalid. It must either start with \"HB\" or contain your callsign."));
return false;
}
auto cq = ui_->cq_message_line_edit->text().toUpper().trimmed();
if(!cq.isEmpty() && !(cq.startsWith("CQ") || cq.contains(callsign))){
MessageBox::critical_message (this, QString("The CQ message format is invalid. It must either start with \"CQ\" or contain your callsign."));
@ -2749,9 +2789,11 @@ void Configuration::impl::accept ()
primary_highlight_words_ = splitWords(ui_->primaryHighlightLineEdit->text().toUpper().trimmed());
secondary_highlight_words_ = splitWords(ui_->secondaryHighlightLineEdit->text().toUpper().trimmed());
cq_ = ui_->cq_message_line_edit->text().toUpper();
hb_ = ui_->hb_message_line_edit->text().toUpper();
reply_ = ui_->reply_message_line_edit->text().toUpper();
eot_ = ui_->eot_line_edit->text().trimmed().left(2);
my_info_ = ui_->info_message_line_edit->text().toUpper();
my_status_ = ui_->status_message_line_edit->text().toUpper();
callsign_aging_ = ui_->callsign_aging_spin_box->value();
activity_aging_ = ui_->activity_aging_spin_box->value();
spot_to_reporting_networks_ = ui_->psk_reporter_check_box->isChecked ();

View File

@ -116,6 +116,8 @@ public:
int callsign_aging() const;
QString eot() const;
QString my_info () const;
QString my_status () const;
QString hb_message () const;
QString cq_message () const;
QString reply_message () const;
QFont table_font() const;
@ -255,9 +257,11 @@ public:
// Set the dynamic grid which is only used if configuration setting is enabled.
void set_dynamic_location (QString const&);
// Set the dynamic station qth message which is only used if configuration setting is enabled.
// Set the dynamic station info message which is only used if configuration setting is enabled.
void set_dynamic_station_info(QString const& info);
// Set the dynamic station status message which is only used if configuration setting is enabled.
void set_dynamic_station_status(QString const& status);
// This method queries if a CAT and PTT connection is operational.
bool is_transceiver_online () const;

View File

@ -190,14 +190,14 @@
<string>Station Messages</string>
</property>
<layout class="QGridLayout" name="gridLayout_4">
<item row="1" column="1">
<widget class="QLineEdit" name="reply_message_line_edit">
<item row="4" column="1">
<widget class="QLineEdit" name="status_message_line_edit">
<property name="text">
<string>HW CPY?</string>
<string>IDLE &lt;MYIDLE&gt; VERSION &lt;MYVERSION&gt;</string>
</property>
</widget>
</item>
<item row="1" column="0">
<item row="2" column="0">
<widget class="QLabel" name="label_17">
<property name="text">
<string>Reply Message:</string>
@ -205,27 +205,34 @@
</widget>
</item>
<item row="0" column="0">
<widget class="QLabel" name="label_19">
<widget class="QLabel" name="label_28">
<property name="text">
<string>CQ Message:</string>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLineEdit" name="cq_message_line_edit">
<property name="text">
<string>CQCQCQ &lt;MYGRID4&gt;</string>
<string>HB Message:</string>
</property>
</widget>
</item>
<item row="2" column="1">
<widget class="QLineEdit" name="info_message_line_edit">
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Station location message that is transmitted in response to &amp;quot;@&amp;quot; directed queries.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
<widget class="QLineEdit" name="reply_message_line_edit">
<property name="text">
<string>HW CPY?</string>
</property>
</widget>
</item>
<item row="2" column="0">
<item row="0" column="1">
<widget class="QLineEdit" name="hb_message_line_edit">
<property name="text">
<string>HB &lt;MYGRID4&gt;</string>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QLineEdit" name="cq_message_line_edit">
<property name="text">
<string>CQ CQ CQ &lt;MYGRID4&gt;</string>
</property>
</widget>
</item>
<item row="3" column="0">
<widget class="QLabel" name="label_14">
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Station location message&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
@ -235,6 +242,27 @@
</property>
</widget>
</item>
<item row="4" column="0">
<widget class="QLabel" name="label_27">
<property name="text">
<string>Station Status (Weather, Idle Time, Version, etc):</string>
</property>
</widget>
</item>
<item row="3" column="1">
<widget class="QLineEdit" name="info_message_line_edit">
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Station location message that is transmitted in response to &amp;quot;@&amp;quot; directed queries.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
</widget>
</item>
<item row="1" column="0">
<widget class="QLabel" name="label_19">
<property name="text">
<string>CQ Message:</string>
</property>
</widget>
</item>
</layout>
</widget>
</item>
@ -281,7 +309,7 @@
<rect>
<x>0</x>
<y>0</y>
<width>615</width>
<width>724</width>
<height>537</height>
</rect>
</property>
@ -1534,7 +1562,7 @@ a few, particularly some Kenwood rigs, require it).</string>
<rect>
<x>0</x>
<y>0</y>
<width>494</width>
<width>718</width>
<height>490</height>
</rect>
</property>
@ -1938,8 +1966,8 @@ this setting allows you to select which audio input will be used
<rect>
<x>0</x>
<y>0</y>
<width>266</width>
<height>345</height>
<width>760</width>
<height>510</height>
</rect>
</property>
<layout class="QVBoxLayout" name="verticalLayout_29">
@ -2325,7 +2353,7 @@ both here.</string>
<rect>
<x>0</x>
<y>0</y>
<width>508</width>
<width>746</width>
<height>567</height>
</rect>
</property>
@ -2522,7 +2550,7 @@ comments field.</string>
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Check to allow changes to grid, qtc, etc from external programs&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Accept Dynamic Station Information</string>
<string>Accept Dynamic Station Information (Grid, Info, Status, etc)</string>
</property>
</widget>
</item>
@ -2850,8 +2878,8 @@ for assessing propagation and system performance.</string>
<rect>
<x>0</x>
<y>0</y>
<width>487</width>
<height>341</height>
<width>760</width>
<height>510</height>
</rect>
</property>
<layout class="QVBoxLayout" name="verticalLayout_31">
@ -3187,8 +3215,8 @@ QListView::item:hover {
<rect>
<x>0</x>
<y>0</y>
<width>163</width>
<height>99</height>
<width>760</width>
<height>510</height>
</rect>
</property>
<layout class="QVBoxLayout" name="verticalLayout_35">
@ -3330,8 +3358,8 @@ QListView::item:hover {
<rect>
<x>0</x>
<y>0</y>
<width>274</width>
<height>690</height>
<width>724</width>
<height>418</height>
</rect>
</property>
<layout class="QVBoxLayout" name="verticalLayout_14">
@ -4401,9 +4429,11 @@ soundcard changes</string>
<tabstop>grid_line_edit</tabstop>
<tabstop>groups_line_edit</tabstop>
<tabstop>avoid_allcall_check_box</tabstop>
<tabstop>hb_message_line_edit</tabstop>
<tabstop>cq_message_line_edit</tabstop>
<tabstop>reply_message_line_edit</tabstop>
<tabstop>info_message_line_edit</tabstop>
<tabstop>status_message_line_edit</tabstop>
<tabstop>scrollArea_2</tabstop>
<tabstop>miles_check_box</tabstop>
<tabstop>monitor_off_check_box</tabstop>
@ -4521,6 +4551,22 @@ soundcard changes</string>
<tabstop>sbBandwidth</tabstop>
<tabstop>cbx4ToneSpacing</tabstop>
<tabstop>sbNtrials</tabstop>
<tabstop>write_logs_check_box</tabstop>
<tabstop>scrollArea_11</tabstop>
<tabstop>heartbeat_anywhere_check_box</tabstop>
<tabstop>heartbeat_qso_pause_check_box</tabstop>
<tabstop>hb_blacklist_line_edit</tabstop>
<tabstop>autoreply_on_check_box</tabstop>
<tabstop>cqMessagesButton</tabstop>
<tabstop>relay_disabled_check_box</tabstop>
<tabstop>auto_whitelist_line_edit</tabstop>
<tabstop>auto_blacklist_line_edit</tabstop>
<tabstop>tx_watchdog_spin_box</tabstop>
<tabstop>autoreply_confirmation_check_box</tabstop>
<tabstop>notification_sound_output_combo_box</tabstop>
<tabstop>scrollArea_12</tabstop>
<tabstop>notifications_check_box</tabstop>
<tabstop>notifications_table_widget</tabstop>
</tabstops>
<resources/>
<connections>

View File

@ -1,6 +1,6 @@
# Version number components
set (WSJTX_VERSION_MAJOR 2)
set (WSJTX_VERSION_MINOR 1)
set (WSJTX_VERSION_PATCH 2)
set (WSJTX_VERSION_MINOR 2)
set (WSJTX_VERSION_PATCH 0)
set (WSJTX_RC 0) # release candidate number, comment out or zero for development versions
set (WSJTX_VERSION_IS_RELEASE 0) # set to 1 for final release build

View File

@ -8127,10 +8127,15 @@ void MainWindow::sendHeartbeat(){
QString mygrid = m_config.my_grid().left(4);
QStringList parts;
parts.append(QString("%1:").arg(mycall));
parts.append("HB");
parts.append(mygrid);
auto hb = m_config.hb_message();
if(hb.isEmpty()){
parts.append("HB");
parts.append(mygrid);
} else {
parts.append(hb);
}
QString message = parts.join(" ").trimmed();
@ -8286,6 +8291,17 @@ void MainWindow::on_infoMacroButton_clicked(){
if(m_config.transmit_directed()) toggleTx(true);
}
void MainWindow::on_statusMacroButton_clicked(){
QString status = m_config.my_status();
if(status.isEmpty()){
return;
}
addMessageText(QString("STATUS %1").arg(replaceMacros(status, buildMacroValues(), true)));
if(m_config.transmit_directed()) toggleTx(true);
}
void MainWindow::setShowColumn(QString tableKey, QString columnKey, bool value){
m_showColumnsCache[tableKey + columnKey] = QVariant(value);
displayBandActivity();
@ -8843,14 +8859,22 @@ void MainWindow::buildEditMenu(QMenu *menu, QTextEdit *edit){
}
QMap<QString, QString> MainWindow::buildMacroValues(){
auto lastActive = DriftingDateTime::currentDateTimeUtc().addSecs(-m_idleMinutes*60);
QString myIdle = since(lastActive).toUpper().replace("NOW", "0M");
QString myVersion = version().replace("-devel", "").replace("-rc", "");
QMap<QString, QString> values = {
{"<MYCALL>", m_config.my_callsign()},
{"<MYGRID4>", m_config.my_grid().left(4)},
{"<MYGRID12>", m_config.my_grid().left(12)},
{"<MYINFO>", m_config.my_info()},
{"<MYHB>", m_config.hb_message()},
{"<MYCQ>", m_config.cq_message()},
{"<MYREPLY>", m_config.reply_message()},
{"<MYSTATUS>", generateStatus()},
{"<MYSTATUS>", m_config.my_status()},
{"<MYVERSION>", myVersion},
{"<MYIDLE>", myIdle},
};
auto selectedCall = callsignSelected();
@ -8867,7 +8891,9 @@ QMap<QString, QString> MainWindow::buildMacroValues(){
// these macros can have recursive macros
values["<MYINFO>"] = replaceMacros(values["<MYINFO>"], values, false);
values["<MYSTATUS>"] = replaceMacros(values["<MYSTATUS>"], values, false);
values["<MYCQ>"] = replaceMacros(values["<MYCQ>"], values, false);
values["<MYHB>"] = replaceMacros(values["<MYHB>"], values, false);
values["<MYREPLY>"] = replaceMacros(values["<MYREPLY>"], values, false);
return values;
@ -9875,7 +9901,11 @@ void MainWindow::updateModeButtonText(){
}
if(autoreply){
modeText += QString("+AUTO");
if(m_config.autoreply_confirmation()){
modeText += QString("+AUTO+CONF");
} else {
modeText += QString("+AUTO");
}
}
if(heartbeat){
@ -9894,12 +9924,14 @@ void MainWindow::updateButtonDisplay(){
auto selectedCallsign = callsignSelected(true);
bool emptyCallsign = selectedCallsign.isEmpty();
bool emptyInfo = m_config.my_info().isEmpty();
bool emptyStatus = m_config.my_status().isEmpty();
ui->hbMacroButton->setDisabled(isTransmitting);
ui->cqMacroButton->setDisabled(isTransmitting);
ui->replyMacroButton->setDisabled(isTransmitting || emptyCallsign);
ui->snrMacroButton->setDisabled(isTransmitting || emptyCallsign);
ui->infoMacroButton->setDisabled(isTransmitting || emptyInfo);
ui->statusMacroButton->setDisabled(isTransmitting || emptyStatus);
ui->macrosMacroButton->setDisabled(isTransmitting);
ui->queryButton->setDisabled(isTransmitting || emptyCallsign);
ui->deselectButton->setDisabled(isTransmitting || emptyCallsign);
@ -10711,44 +10743,6 @@ void MainWindow::processBufferedActivity() {
}
}
QString MainWindow::generateStatus() {
auto lastActive = DriftingDateTime::currentDateTimeUtc().addSecs(-m_idleMinutes*60);
QString lastActiveString = since(lastActive).toUpper().replace("NOW", "0M");
QStringList status;
status.append(generateStatusFlags());
if(!lastActiveString.isEmpty()){
status.append(lastActiveString.trimmed());
}
status.append("V" + version().replace("-devel", "").replace("-rc", ""));
return status.join(" ").trimmed();
}
QStringList MainWindow::generateStatusFlags() {
QStringList flags;
if(ui->hbMacroButton->isChecked() && m_hbInterval > 0){
flags.append("HB");
}
if(ui->actionModeAutoreply->isChecked()){
flags.append("AUTO");
}
if(ui->actionModeAutoreply->isChecked() && !m_config.relay_off()){
flags.append("RELAY");
}
if(m_config.spot_to_reporting_networks()){
flags.append("SPOT");
}
return flags;
}
void MainWindow::processCommandActivity() {
#if 0
if (!m_txFrameQueue.isEmpty()) {
@ -10999,7 +10993,12 @@ void MainWindow::processCommandActivity() {
// QUERIED ACTIVE
else if (d.cmd == " STATUS?" && !isAllCall) {
reply = QString("%1 STATUS %2").arg(d.from).arg(generateStatus());
QString status = m_config.my_status();
if (status.isEmpty()) {
continue;
}
reply = QString("%1 STATUS %2").arg(d.from).arg(replaceMacros(status, buildMacroValues(), true));
}
// QUERIED GRID
@ -12583,6 +12582,21 @@ void MainWindow::networkMessage(Message const &message)
return;
}
if(type == "STATION.GET_STATUS"){
sendNetworkMessage("STATION.STATUS", m_config.my_status(), {
{"_ID", id},
});
return;
}
if(type == "STATION.SET_STATUS"){
m_config.set_dynamic_station_status(message.value());
sendNetworkMessage("STATION.STATUS", m_config.my_status(), {
{"_ID", id},
});
return;
}
// RX.GET_CALL_ACTIVITY
// RX.GET_CALL_SELECTED
// RX.GET_BAND_ACTIVITY

View File

@ -322,6 +322,7 @@ private slots:
void on_replyMacroButton_clicked();
void on_snrMacroButton_clicked();
void on_infoMacroButton_clicked();
void on_statusMacroButton_clicked();
void setShowColumn(QString tableKey, QString columnKey, bool value);
bool showColumn(QString tableKey, QString columnKey, bool default_=true);
void buildShowColumnsMenu(QMenu *menu, QString tableKey);
@ -992,8 +993,6 @@ private:
void processIdleActivity();
void processCompoundActivity();
void processBufferedActivity();
QString generateStatus();
QStringList generateStatusFlags();
void processCommandActivity();
QString inboxPath();
void refreshInboxCounts();

View File

@ -1437,6 +1437,54 @@ QTextEdit[transmitting=&quot;true&quot;] {
<property name="bottomMargin">
<number>0</number>
</property>
<item row="1" column="13">
<widget class="QPushButton" name="queryButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send a directed message to another station&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Directed</string>
</property>
</widget>
</item>
<item row="1" column="4">
<widget class="QPushButton" name="snrMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send an signal report&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>SNR</string>
</property>
</widget>
</item>
<item row="1" column="7">
<spacer name="horizontalSpacer_11">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="0">
<widget class="QPushButton" name="hbMacroButton">
<property name="minimumSize">
@ -1465,11 +1513,8 @@ QTextEdit[transmitting=&quot;true&quot;] {
</property>
</widget>
</item>
<item row="1" column="16">
<widget class="QPushButton" name="startTxButton">
<property name="enabled">
<bool>false</bool>
</property>
<item row="1" column="8">
<widget class="QPushButton" name="macrosMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
@ -1477,26 +1522,26 @@ QTextEdit[transmitting=&quot;true&quot;] {
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Start transmitting&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="autoFillBackground">
<bool>false</bool>
</property>
<property name="styleSheet">
<string notr="true">QPushButton:checked {
background-color: #22FF22;
color:#222;
}
QPushButton[transmitting=&quot;true&quot;]{
background:#FF2222;
color:#222;
}</string>
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send a saved message&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Send</string>
<string>Saved</string>
</property>
<property name="checkable">
<bool>true</bool>
</widget>
</item>
<item row="1" column="5">
<widget class="QPushButton" name="infoMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send your station information&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>INFO</string>
</property>
</widget>
</item>
@ -1531,120 +1576,11 @@ color:#222;
</property>
</widget>
</item>
<item row="1" column="5">
<widget class="QPushButton" name="infoMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send your station information&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>INFO</string>
</property>
</widget>
</item>
<item row="1" column="6">
<spacer name="horizontalSpacer_11">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="8">
<spacer name="horizontalSpacerSavedDirected">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="15">
<spacer name="horizontalSpacer_5">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="4">
<widget class="QPushButton" name="snrMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send an signal report&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>SNR</string>
</property>
</widget>
</item>
<item row="1" column="3">
<widget class="QPushButton" name="replyMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Reply to a CQ&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>REPLY</string>
</property>
</widget>
</item>
<item row="1" column="17">
<widget class="QPushButton" name="stopTxButton">
<property name="minimumSize">
<size>
<width>75</width>
<height>30</height>
</size>
<widget class="QPushButton" name="startTxButton">
<property name="enabled">
<bool>false</bool>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Stop transmitting&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Halt</string>
</property>
</widget>
</item>
<item row="1" column="7">
<widget class="QPushButton" name="macrosMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
@ -1652,30 +1588,30 @@ color:#222;
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send a saved message&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Start transmitting&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="autoFillBackground">
<bool>false</bool>
</property>
<property name="styleSheet">
<string notr="true">QPushButton:checked {
background-color: #22FF22;
color:#222;
}
QPushButton[transmitting=&quot;true&quot;]{
background:#FF2222;
color:#222;
}</string>
</property>
<property name="text">
<string>Saved</string>
<string>Send</string>
</property>
<property name="checkable">
<bool>true</bool>
</property>
</widget>
</item>
<item row="1" column="12">
<widget class="QPushButton" name="queryButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Send a directed message to another station&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Directed</string>
</property>
</widget>
</item>
<item row="1" column="13">
<item row="1" column="14">
<widget class="QPushButton" name="deselectButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Minimum" vsizetype="Fixed">
@ -1697,6 +1633,83 @@ color:#222;
</property>
</widget>
</item>
<item row="1" column="16">
<spacer name="horizontalSpacer_5">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="9">
<spacer name="horizontalSpacerSavedDirected">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeType">
<enum>QSizePolicy::Preferred</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>10</height>
</size>
</property>
</spacer>
</item>
<item row="1" column="3">
<widget class="QPushButton" name="replyMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Reply to a CQ&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>REPLY</string>
</property>
</widget>
</item>
<item row="1" column="18">
<widget class="QPushButton" name="stopTxButton">
<property name="minimumSize">
<size>
<width>75</width>
<height>30</height>
</size>
</property>
<property name="toolTip">
<string>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Stop transmitting&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="text">
<string>Halt</string>
</property>
</widget>
</item>
<item row="1" column="6">
<widget class="QPushButton" name="statusMacroButton">
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="text">
<string>STATUS</string>
</property>
</widget>
</item>
</layout>
</widget>
<widget class="QFrame" name="frame_5">

View File

@ -262,7 +262,10 @@ QMap<QString, quint32> basecalls = {
{ "@RADAR", nbasecall + 42 }, // RADAR GROUP
{ "@SKYWARN", nbasecall + 43 }, // SKYWARN GROUP
{ "@CQ", nbasecall + 44 }, // CQ GROUP
{ "@QSO", nbasecall + 45 }, // QSO GROUP
{ "@HB", nbasecall + 45 }, // HB GROUP
{ "@QSO", nbasecall + 46 }, // QSO GROUP
{ "@QSOPARTY", nbasecall + 47 }, // QSO PARTY GROUP
{ "@CONTEST", nbasecall + 48 }, // CONTEST GROUP
};
QMap<quint32, QString> cqs = {
@ -342,7 +345,7 @@ int dbmTomwatts(int dbm){
QString Varicode::extendedChars(){
static QString c;
if(c.size() == 0){
for(int i = 0; i < JSC::prefixSize; i++){
for(quint32 i = 0; i < JSC::prefixSize; i++){
if(JSC::prefix[i].size != 1){ continue; }
c.append(QLatin1String(JSC::prefix[i].str, 1));
}