Reorganized the window, added beacon watch, macro buttons, etc
This commit is contained in:
parent
cb71c3dcf4
commit
f610e946fc
104
mainwindow.cpp
104
mainwindow.cpp
@ -909,6 +909,7 @@ MainWindow::MainWindow(QDir const& temp_directory, bool multiple,
|
||||
connect (&splashTimer, &QTimer::timeout, this, &MainWindow::splash_done);
|
||||
splashTimer.setSingleShot (true);
|
||||
splashTimer.start (20 * 1000);
|
||||
|
||||
/*
|
||||
if(m_config.my_callsign()=="K1JT" or m_config.my_callsign()=="K9AN" or
|
||||
m_config.my_callsign()=="G4WJS" || m_config.my_callsign () == "W9XYZ" or
|
||||
@ -2169,6 +2170,11 @@ void MainWindow::closeEvent(QCloseEvent * e)
|
||||
QMainWindow::closeEvent (e);
|
||||
}
|
||||
|
||||
void MainWindow::on_labDialFreq_clicked() //dialFrequency
|
||||
{
|
||||
ui->bandComboBox->setFocus();
|
||||
}
|
||||
|
||||
void MainWindow::on_stopButton_clicked() //stopButton
|
||||
{
|
||||
monitor (false);
|
||||
@ -2939,10 +2945,45 @@ void MainWindow::readFromStdout() //readFromStdout
|
||||
m_logBook,m_config.color_CQ(),m_config.color_MyCall(),
|
||||
m_config.color_DXCC(), m_config.color_NewCall(),
|
||||
m_config.ppfx(),(ui->cbCQonly->isVisible() and ui->cbCQonly->isChecked()));
|
||||
ui->textEditRXAll->append(decodedtext.messageWords().first().trimmed());
|
||||
|
||||
// TODO: parse decode...
|
||||
//ui->textEditRXAll->append(decodedtext.messageWords().first().trimmed());
|
||||
//ui->tableWidgetRXAll->insertRow(ui->tableWidgetRXAll->rowCount());
|
||||
//ui->tableWidgetRXAll->setItem(ui->tableWidgetRXAll->rowCount()-1, 0, new QTableWidgetItem(QString("%1").arg(decodedtext.frequencyOffset())));
|
||||
//ui->tableWidgetRXAll->setItem(ui->tableWidgetRXAll->rowCount()-1, 1, new QTableWidgetItem(decodedtext.messageWords().first().trimmed()));
|
||||
if(decodedtext.messageWords().length() > 0){
|
||||
int offset = decodedtext.frequencyOffset();
|
||||
|
||||
if(!m_bandActivity.contains(offset)){
|
||||
QList<int> offsets = {offset - 1, offset - 2, offset - 3, offset + 1, offset + 2, offset + 3};
|
||||
foreach(int prevOffset, offsets){
|
||||
if(!m_bandActivity.contains(prevOffset)){ continue; }
|
||||
m_bandActivity[offset] = m_bandActivity[prevOffset];
|
||||
m_bandActivity.remove(prevOffset);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ActivityDetail d;
|
||||
d.freq = offset;
|
||||
d.text = decodedtext.messageWords().first().trimmed();
|
||||
d.timestamp = QDateTime::currentDateTimeUtc().toMSecsSinceEpoch();
|
||||
d.snr = decodedtext.snr();
|
||||
m_bandActivity[offset].append(d);
|
||||
|
||||
while(m_bandActivity[offset].count() > 10){
|
||||
m_bandActivity[offset].removeFirst();
|
||||
}
|
||||
}
|
||||
|
||||
QString cqCall = decodedtext.CQersCall();
|
||||
if(!cqCall.isEmpty()){
|
||||
ui->listWidget->addItem(cqCall);
|
||||
CallDetail d;
|
||||
d.call = cqCall;
|
||||
d.snr = decodedtext.snr();
|
||||
d.freq = decodedtext.frequencyOffset();
|
||||
d.timestamp = QDateTime::currentDateTimeUtc().toMSecsSinceEpoch();
|
||||
m_callActivity[cqCall] = d;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2985,6 +3026,7 @@ void MainWindow::readFromStdout() //readFromStdout
|
||||
}
|
||||
m_QSOText = decodedtext.string ().trimmed ();
|
||||
|
||||
// TODO: parse decode...
|
||||
//ui->textEditRXAll->insertHtml(decodedtext.messageWords().first().trimmed() + "\n");
|
||||
}
|
||||
|
||||
@ -3055,6 +3097,8 @@ void MainWindow::readFromStdout() //readFromStdout
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// See MainWindow::postDecode for displaying the latest decodes
|
||||
}
|
||||
|
||||
//
|
||||
@ -3700,6 +3744,11 @@ void MainWindow::guiUpdate()
|
||||
QString utc = t.date().toString("yyyy MMM dd") + "\n " +
|
||||
t.time().toString() + " ";
|
||||
ui->labUTC->setText(utc);
|
||||
|
||||
auto delta = t.msecsTo(m_nextBeacon)/1000;
|
||||
auto beacon = ui->beaconButton->isChecked() ? delta > 0 ? QString("%1 s").arg(delta) : "queued!" : "disabled";
|
||||
ui->labBeacon->setText(QString("Next Beacon: %1").arg(beacon));
|
||||
|
||||
if(!m_monitoring and !m_diskData) {
|
||||
ui->signal_meter_widget->setValue(0,0);
|
||||
}
|
||||
@ -6066,6 +6115,13 @@ void MainWindow::on_pbT2R_clicked()
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::on_beaconButton_clicked()
|
||||
{
|
||||
if(ui->beaconButton->isChecked()){
|
||||
m_nextBeacon = QDateTime::currentDateTimeUtc().addSecs(300);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void MainWindow::on_readFreq_clicked()
|
||||
{
|
||||
@ -6812,6 +6868,50 @@ void MainWindow::postDecode (bool is_new, QString const& message)
|
||||
, QChar {'?'} == decode.mid (has_seconds ? 24 + 21 : 22 + 21, 1)
|
||||
, m_diskData);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
// TODO: keep track of selection
|
||||
int now = QDateTime::currentDateTimeUtc().toMSecsSinceEpoch();
|
||||
for(int i = ui->tableWidgetRXAll->rowCount(); i >= 0; i--){
|
||||
ui->tableWidgetRXAll->removeRow(i);
|
||||
}
|
||||
QList<int> keys = m_bandActivity.keys();
|
||||
qSort(keys.begin(), keys.end());
|
||||
foreach (int offset, keys) {
|
||||
auto items = m_bandActivity[offset];
|
||||
if(items.length() > 0){
|
||||
QStringList text;
|
||||
int snr = 0;
|
||||
foreach(auto item, items){
|
||||
if(now - item.timestamp > 90000){
|
||||
continue;
|
||||
}
|
||||
text.append(item.text);
|
||||
snr = item.snr;
|
||||
}
|
||||
auto joined = text.join(" … ");
|
||||
if(joined.isEmpty()){
|
||||
continue;
|
||||
}
|
||||
|
||||
ui->tableWidgetRXAll->insertRow(ui->tableWidgetRXAll->rowCount());
|
||||
ui->tableWidgetRXAll->setItem(ui->tableWidgetRXAll->rowCount() - 1, 0, new QTableWidgetItem(QString("%1").arg(offset)));
|
||||
ui->tableWidgetRXAll->setItem(ui->tableWidgetRXAll->rowCount() - 1, 1, new QTableWidgetItem(QString("%1").arg(snr)));
|
||||
ui->tableWidgetRXAll->setItem(ui->tableWidgetRXAll->rowCount() - 1, 2, new QTableWidgetItem(joined));
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: keep track of selection
|
||||
ui->listWidget->clear();
|
||||
ui->listWidget->addItem("allcall");
|
||||
QList<QString> calls = m_callActivity.keys();
|
||||
qSort(calls.begin(), calls.end());
|
||||
foreach(QString call, calls){
|
||||
ui->listWidget->addItem(call);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void MainWindow::postWSPRDecode (bool is_new, QStringList parts)
|
||||
|
23
mainwindow.h
23
mainwindow.h
@ -16,6 +16,7 @@
|
||||
#include <QProgressDialog>
|
||||
#include <QAbstractSocket>
|
||||
#include <QHostAddress>
|
||||
#include <QPair>
|
||||
#include <QPointer>
|
||||
#include <QSet>
|
||||
#include <QVector>
|
||||
@ -37,6 +38,7 @@
|
||||
#include "astro.h"
|
||||
#include "MessageBox.hpp"
|
||||
#include "NetworkAccessManager.hpp"
|
||||
#include "qorderedmap.h"
|
||||
|
||||
#define NUM_JT4_SYMBOLS 206 //(72+31)*2, embedded sync
|
||||
#define NUM_JT65_SYMBOLS 126 //63 data + 63 sync
|
||||
@ -135,6 +137,7 @@ private slots:
|
||||
void on_monitorButton_clicked (bool);
|
||||
void on_actionAbout_triggered();
|
||||
void on_autoButton_clicked (bool);
|
||||
void on_labDialFreq_clicked();
|
||||
void on_stopTxButton_clicked();
|
||||
void on_stopButton_clicked();
|
||||
void on_actionRelease_Notes_triggered ();
|
||||
@ -226,6 +229,7 @@ private slots:
|
||||
void on_tuneButton_clicked (bool);
|
||||
void on_pbR2T_clicked();
|
||||
void on_pbT2R_clicked();
|
||||
void on_beaconButton_clicked();
|
||||
void acceptQSO (QDateTime const&, QString const& call, QString const& grid
|
||||
, Frequency dial_freq, QString const& mode
|
||||
, QString const& rpt_sent, QString const& rpt_received
|
||||
@ -591,6 +595,24 @@ private:
|
||||
qint32 ncall;
|
||||
};
|
||||
|
||||
struct CallDetail
|
||||
{
|
||||
QString call;
|
||||
int freq;
|
||||
int timestamp;
|
||||
int snr;
|
||||
};
|
||||
|
||||
struct ActivityDetail
|
||||
{
|
||||
int freq;
|
||||
QString text;
|
||||
int timestamp;
|
||||
int snr;
|
||||
};
|
||||
|
||||
QMap<int, QList<ActivityDetail>> m_bandActivity; // freq -> [(text, last timestamp), ...]
|
||||
QMap<QString, CallDetail> m_callActivity; // call -> (last freq, last timestamp)
|
||||
QMap<QString,FoxQSO> m_foxQSO;
|
||||
QMap<QString,QString> m_loggedByFox;
|
||||
|
||||
@ -599,6 +621,7 @@ private:
|
||||
QQueue<QString> m_foxRR73Queue;
|
||||
QQueue<qint64> m_foxRateQueue;
|
||||
|
||||
QDateTime m_nextBeacon;
|
||||
QDateTime m_dateTimeQSOOn;
|
||||
QDateTime m_dateTimeLastTX;
|
||||
|
||||
|
1038
mainwindow.ui
1038
mainwindow.ui
File diff suppressed because it is too large
Load Diff
611
qorderedmap.h
Normal file
611
qorderedmap.h
Normal file
@ -0,0 +1,611 @@
|
||||
#ifndef ORDEREDMAP_H
|
||||
#define ORDEREDMAP_H
|
||||
|
||||
#include <QtGlobal>
|
||||
#include <QHash>
|
||||
#include <QLinkedList>
|
||||
#include <QList>
|
||||
#include <QPair>
|
||||
|
||||
template <typename Key> inline bool oMHashEqualToKey(const Key &key1, const Key &key2)
|
||||
{
|
||||
// Key type must provide '==' operator
|
||||
return key1 == key2;
|
||||
}
|
||||
|
||||
template <typename Ptr> inline bool oMHashEqualToKey(Ptr *key1, Ptr *key2)
|
||||
{
|
||||
Q_ASSERT(sizeof(quintptr) == sizeof(Ptr *));
|
||||
return quintptr(key1) == quintptr(key2);
|
||||
}
|
||||
|
||||
template <typename Ptr> inline bool oMHashEqualToKey(const Ptr *key1, const Ptr *key2)
|
||||
{
|
||||
Q_ASSERT(sizeof(quintptr) == sizeof(const Ptr *));
|
||||
return quintptr(key1) == quintptr(key2);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
class OrderedMap
|
||||
{
|
||||
class OMHash;
|
||||
|
||||
typedef typename QLinkedList<Key>::iterator QllIterator;
|
||||
typedef typename QLinkedList<Key>::const_iterator QllConstIterator;
|
||||
typedef QPair<Value, QllIterator> OMHashValue;
|
||||
|
||||
typedef typename OMHash::iterator OMHashIterator;
|
||||
typedef typename OMHash::const_iterator OMHashConstIterator;
|
||||
|
||||
public:
|
||||
|
||||
class iterator;
|
||||
class const_iterator;
|
||||
|
||||
typedef typename OrderedMap<Key, Value>::iterator Iterator;
|
||||
typedef typename OrderedMap<Key, Value>::const_iterator ConstIterator;
|
||||
|
||||
explicit OrderedMap();
|
||||
|
||||
OrderedMap(const OrderedMap<Key, Value>& other);
|
||||
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 2, 0))
|
||||
OrderedMap(OrderedMap<Key, Value>&& other);
|
||||
#endif
|
||||
|
||||
void clear();
|
||||
|
||||
bool contains(const Key &key) const;
|
||||
|
||||
int count() const;
|
||||
|
||||
bool empty() const;
|
||||
|
||||
iterator insert(const Key &key, const Value &value);
|
||||
|
||||
bool isEmpty() const;
|
||||
|
||||
QList<Key> keys() const;
|
||||
|
||||
int remove(const Key &key);
|
||||
|
||||
int size() const;
|
||||
|
||||
Value take(const Key &key);
|
||||
|
||||
Value value(const Key &key) const;
|
||||
|
||||
Value value(const Key &key, const Value &defaultValue) const;
|
||||
|
||||
QList<Value> values() const;
|
||||
|
||||
OrderedMap<Key, Value> & operator=(const OrderedMap<Key, Value>& other);
|
||||
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 2, 0))
|
||||
OrderedMap<Key, Value> & operator=(OrderedMap<Key, Value>&& other);
|
||||
#endif
|
||||
|
||||
bool operator==(const OrderedMap<Key, Value> &other) const;
|
||||
|
||||
bool operator!=(const OrderedMap<Key, Value> &other) const;
|
||||
|
||||
Value& operator[](const Key &key);
|
||||
|
||||
const Value operator[](const Key &key) const;
|
||||
|
||||
iterator begin();
|
||||
|
||||
const_iterator begin() const;
|
||||
|
||||
iterator end();
|
||||
|
||||
const_iterator end() const;
|
||||
|
||||
iterator erase(iterator pos);
|
||||
|
||||
iterator find(const Key& key);
|
||||
|
||||
const_iterator find(const Key& key) const;
|
||||
|
||||
class const_iterator;
|
||||
|
||||
class iterator
|
||||
{
|
||||
QllIterator qllIter;
|
||||
OMHash *data;
|
||||
friend class const_iterator;
|
||||
friend class OrderedMap;
|
||||
|
||||
public:
|
||||
iterator() : data(NULL) {}
|
||||
|
||||
iterator(const QllIterator &qllIter, OMHash *data) :
|
||||
qllIter(qllIter), data(data) {}
|
||||
|
||||
const Key & key() const
|
||||
{
|
||||
return *qllIter;
|
||||
}
|
||||
|
||||
Value & value() const
|
||||
{
|
||||
OMHashIterator hit = data->find(*qllIter);
|
||||
OMHashValue &pair = hit.value();
|
||||
return pair.first;
|
||||
}
|
||||
|
||||
Value & operator*() const
|
||||
{
|
||||
return value();
|
||||
}
|
||||
|
||||
iterator operator+(int i) const
|
||||
{
|
||||
QllIterator q = qllIter;
|
||||
q += i;
|
||||
|
||||
return iterator(q, data);
|
||||
}
|
||||
|
||||
iterator operator-(int i) const
|
||||
{
|
||||
return operator +(- i);
|
||||
}
|
||||
|
||||
iterator& operator+=(int i)
|
||||
{
|
||||
qllIter += i;
|
||||
return *this;
|
||||
}
|
||||
|
||||
iterator& operator-=(int i)
|
||||
{
|
||||
qllIter -= i;
|
||||
return *this;
|
||||
}
|
||||
|
||||
iterator& operator++()
|
||||
{
|
||||
++qllIter;
|
||||
return *this;
|
||||
}
|
||||
|
||||
iterator operator++(int)
|
||||
{
|
||||
iterator it = *this;
|
||||
qllIter++;
|
||||
return it;
|
||||
}
|
||||
|
||||
iterator operator--()
|
||||
{
|
||||
--qllIter;
|
||||
return *this;
|
||||
}
|
||||
|
||||
iterator operator--(int)
|
||||
{
|
||||
iterator it = *this;
|
||||
qllIter--;
|
||||
return it;
|
||||
}
|
||||
|
||||
bool operator ==(const iterator &other) const
|
||||
{
|
||||
return (qllIter == other.qllIter);
|
||||
}
|
||||
|
||||
bool operator !=(const iterator &other) const
|
||||
{
|
||||
return (qllIter != other.qllIter);
|
||||
}
|
||||
};
|
||||
|
||||
class const_iterator
|
||||
{
|
||||
|
||||
QllConstIterator qllConstIter;
|
||||
const OMHash *data;
|
||||
|
||||
public:
|
||||
const_iterator() : data(NULL) {}
|
||||
|
||||
const_iterator(const iterator &i) :
|
||||
qllConstIter(i.qllIter), data(i.data) {}
|
||||
|
||||
const_iterator(const QllConstIterator &qllConstIter, const OMHash* data) :
|
||||
qllConstIter(qllConstIter), data(data) {}
|
||||
|
||||
const Key & key() const
|
||||
{
|
||||
return *qllConstIter;
|
||||
}
|
||||
|
||||
const Value & value() const
|
||||
{
|
||||
OMHashConstIterator hit = data->find(*qllConstIter);
|
||||
const OMHashValue &pair = hit.value();
|
||||
return pair.first;
|
||||
}
|
||||
|
||||
const Value & operator*() const
|
||||
{
|
||||
return value();
|
||||
}
|
||||
|
||||
const_iterator operator+(int i) const
|
||||
{
|
||||
QllConstIterator q = qllConstIter;
|
||||
q += i;
|
||||
|
||||
return const_iterator(q, data);
|
||||
}
|
||||
|
||||
const_iterator operator-(int i) const
|
||||
{
|
||||
return operator +(- i);
|
||||
}
|
||||
|
||||
const_iterator& operator+=(int i)
|
||||
{
|
||||
qllConstIter += i;
|
||||
return *this;
|
||||
}
|
||||
|
||||
const_iterator& operator-=(int i)
|
||||
{
|
||||
qllConstIter -= i;
|
||||
return *this;
|
||||
}
|
||||
|
||||
const_iterator& operator++()
|
||||
{
|
||||
++qllConstIter;
|
||||
return *this;
|
||||
}
|
||||
|
||||
const_iterator operator++(int)
|
||||
{
|
||||
const_iterator it = *this;
|
||||
qllConstIter++;
|
||||
return it;
|
||||
}
|
||||
|
||||
const_iterator operator--()
|
||||
{
|
||||
--qllConstIter;
|
||||
return *this;
|
||||
}
|
||||
|
||||
const_iterator operator--(int)
|
||||
{
|
||||
const_iterator it = *this;
|
||||
qllConstIter--;
|
||||
return it;
|
||||
}
|
||||
|
||||
bool operator ==(const const_iterator &other) const
|
||||
{
|
||||
return (qllConstIter == other.qllConstIter);
|
||||
}
|
||||
|
||||
bool operator !=(const const_iterator &other) const
|
||||
{
|
||||
return (qllConstIter != other.qllConstIter);
|
||||
}
|
||||
};
|
||||
|
||||
private:
|
||||
|
||||
class OMHash : public QHash<Key, OMHashValue >
|
||||
{
|
||||
public:
|
||||
bool operator == (const OMHash &other) const
|
||||
{
|
||||
if (size() != other.size()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (QHash<Key, OMHashValue >::operator ==(other)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
typename QHash<Key, OMHashValue >::const_iterator it1 = this->constBegin();
|
||||
typename QHash<Key, OMHashValue >::const_iterator it2 = other.constBegin();
|
||||
|
||||
while(it1 != this->end()) {
|
||||
OMHashValue v1 = it1.value();
|
||||
OMHashValue v2 = it2.value();
|
||||
|
||||
if ((v1.first != v2.first) || !oMHashEqualToKey<Key>(it1.key(), it2.key())) {
|
||||
return false;
|
||||
}
|
||||
++it1;
|
||||
++it2;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
private:
|
||||
void copy(const OrderedMap<Key, Value> &other);
|
||||
|
||||
OMHash data;
|
||||
QLinkedList<Key> insertOrder;
|
||||
};
|
||||
|
||||
template <typename Key, typename Value>
|
||||
OrderedMap<Key, Value>::OrderedMap() {}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
OrderedMap<Key, Value>::OrderedMap(const OrderedMap<Key, Value>& other)
|
||||
{
|
||||
copy(other);
|
||||
}
|
||||
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 2, 0))
|
||||
template <typename Key, typename Value>
|
||||
OrderedMap<Key, Value>::OrderedMap(OrderedMap<Key, Value>&& other)
|
||||
{
|
||||
data = std::move(other.data);
|
||||
insertOrder = std::move(other.insertOrder);
|
||||
}
|
||||
#endif
|
||||
|
||||
template <typename Key, typename Value>
|
||||
void OrderedMap<Key, Value>::clear()
|
||||
{
|
||||
data.clear();
|
||||
insertOrder.clear();
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
bool OrderedMap<Key, Value>::contains(const Key &key) const
|
||||
{
|
||||
return data.contains(key);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
int OrderedMap<Key, Value>::count() const
|
||||
{
|
||||
return data.count();
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
bool OrderedMap<Key, Value>::empty() const
|
||||
{
|
||||
return data.empty();
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::iterator OrderedMap<Key, Value>::insert(const Key &key, const Value &value)
|
||||
{
|
||||
OMHashIterator it = data.find(key);
|
||||
|
||||
if (it == data.end()) {
|
||||
// New key
|
||||
QllIterator ioIter = insertOrder.insert(insertOrder.end(), key);
|
||||
OMHashValue pair(value, ioIter);
|
||||
data.insert(key, pair);
|
||||
return iterator(ioIter, &data);
|
||||
}
|
||||
|
||||
OMHashValue pair = it.value();
|
||||
// remove old reference
|
||||
insertOrder.erase(pair.second);
|
||||
// Add new reference
|
||||
QllIterator ioIter = insertOrder.insert(insertOrder.end(), key);
|
||||
pair.first = value;
|
||||
pair.second = ioIter;
|
||||
return iterator(ioIter, &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
bool OrderedMap<Key, Value>::isEmpty() const
|
||||
{
|
||||
return data.isEmpty();
|
||||
}
|
||||
|
||||
template<typename Key, typename Value>
|
||||
QList<Key> OrderedMap<Key, Value>::keys() const
|
||||
{
|
||||
return QList<Key>::fromStdList(insertOrder.toStdList());
|
||||
}
|
||||
|
||||
template<typename Key, typename Value>
|
||||
int OrderedMap<Key, Value>::remove(const Key &key)
|
||||
{
|
||||
OMHashIterator it = data.find(key);
|
||||
if (it == data.end()) {
|
||||
return 0;
|
||||
}
|
||||
OMHashValue pair = it.value();
|
||||
insertOrder.erase(pair.second);
|
||||
data.erase(it);
|
||||
return 1;
|
||||
}
|
||||
|
||||
template<typename Key, typename Value>
|
||||
int OrderedMap<Key, Value>::size() const
|
||||
{
|
||||
return data.size();
|
||||
}
|
||||
|
||||
template<typename Key, typename Value>
|
||||
void OrderedMap<Key, Value>::copy(const OrderedMap<Key, Value> &other)
|
||||
{
|
||||
/* Since I'm storing iterators of QLinkedList, I simply cannot make
|
||||
* a trivial copy of the linked list. This is a limitation due to implicit
|
||||
* sharing used in Qt containers, due to which iterator active on one
|
||||
* QLL can change the data of another QLL even after creating a copy.
|
||||
*
|
||||
* Because of this, the old iterators have to be invalidated and new ones
|
||||
* have to be generated.
|
||||
*/
|
||||
insertOrder.clear();
|
||||
// Copy hash
|
||||
data = other.data;
|
||||
|
||||
QllConstIterator cit = other.insertOrder.begin();
|
||||
for (; cit != other.insertOrder.end(); ++cit) {
|
||||
Key key = *cit;
|
||||
QllIterator ioIter = insertOrder.insert(insertOrder.end(), key);
|
||||
OMHashIterator it = data.find(key);
|
||||
(*it).second = ioIter;
|
||||
}
|
||||
}
|
||||
|
||||
template<typename Key, typename Value>
|
||||
Value OrderedMap<Key, Value>::take(const Key &key)
|
||||
{
|
||||
OMHashIterator it = data.find(key);
|
||||
if (it == data.end()) {
|
||||
return Value();
|
||||
}
|
||||
OMHashValue pair = it.value();
|
||||
insertOrder.erase(pair.second);
|
||||
data.erase(it);
|
||||
return pair.first;
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
Value OrderedMap<Key, Value>::value(const Key &key) const
|
||||
{
|
||||
return data.value(key).first;
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
Value OrderedMap<Key, Value>::value(const Key &key, const Value &defaultValue) const
|
||||
{
|
||||
OMHashConstIterator it = data.constFind(key);
|
||||
if (it == data.end()) {
|
||||
return defaultValue;
|
||||
}
|
||||
OMHashValue pair = it.value();
|
||||
return pair.first;
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
QList<Value> OrderedMap<Key, Value>::values() const
|
||||
{
|
||||
QList<Value> values;
|
||||
foreach (const Key &key, insertOrder.toStdList()) {
|
||||
OMHashValue v = data.value(key);
|
||||
values.append(v.first);
|
||||
}
|
||||
return values;
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
OrderedMap<Key, Value> & OrderedMap<Key, Value>::operator=(const OrderedMap<Key, Value>& other)
|
||||
{
|
||||
if (this != &other) {
|
||||
copy(other);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 2, 0))
|
||||
template <typename Key, typename Value>
|
||||
OrderedMap<Key, Value> & OrderedMap<Key, Value>::operator=(OrderedMap<Key, Value>&& other)
|
||||
{
|
||||
if (this != &other) {
|
||||
data = other.data;
|
||||
insertOrder = other.insertOrder;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
#endif
|
||||
|
||||
template <typename Key, typename Value>
|
||||
bool OrderedMap<Key, Value>::operator==(const OrderedMap<Key, Value> &other) const
|
||||
{
|
||||
// 2 Ordered maps are equal if they have the same contents in the same order
|
||||
return ((data == other.data) && (insertOrder == other.insertOrder));
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
bool OrderedMap<Key, Value>::operator!=(const OrderedMap<Key, Value> &other) const
|
||||
{
|
||||
return ((data != other.data) || (insertOrder != other.insertOrder));
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
Value& OrderedMap<Key, Value>::operator[](const Key &key)
|
||||
{
|
||||
OMHashIterator it = data.find(key);
|
||||
if (it == data.end()) {
|
||||
insert(key, Value());
|
||||
it = data.find(key);
|
||||
}
|
||||
OMHashValue &pair = it.value();
|
||||
return pair.first;
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
const Value OrderedMap<Key, Value>::operator[](const Key &key) const
|
||||
{
|
||||
return value(key);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::iterator OrderedMap<Key, Value>::begin()
|
||||
{
|
||||
return iterator(insertOrder.begin(), &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::const_iterator OrderedMap<Key, Value>::begin() const
|
||||
{
|
||||
return const_iterator(insertOrder.begin(), &data);
|
||||
}
|
||||
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::iterator OrderedMap<Key, Value>::end()
|
||||
{
|
||||
return iterator(insertOrder.end(), &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::const_iterator OrderedMap<Key, Value>::end() const
|
||||
{
|
||||
return const_iterator(insertOrder.end(), &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::iterator OrderedMap<Key, Value>::erase(iterator pos)
|
||||
{
|
||||
OMHashIterator hit = data.find(*(pos.qllIter));
|
||||
if (hit == data.end()) {
|
||||
return pos;
|
||||
}
|
||||
data.erase(hit);
|
||||
QllIterator ioIter = insertOrder.erase(pos.qllIter);
|
||||
|
||||
return iterator(ioIter, &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::iterator OrderedMap<Key, Value>::find(const Key& key)
|
||||
{
|
||||
OMHashIterator hit = data.find(key);
|
||||
if (hit == data.end()) {
|
||||
return end();
|
||||
}
|
||||
|
||||
return iterator(hit.value().second, &data);
|
||||
}
|
||||
|
||||
template <typename Key, typename Value>
|
||||
typename OrderedMap<Key, Value>::const_iterator OrderedMap<Key, Value>::find(const Key& key) const
|
||||
{
|
||||
OMHashConstIterator hit = data.find(key);
|
||||
if (hit == data.end()) {
|
||||
return end();
|
||||
}
|
||||
|
||||
return const_iterator(hit.value().second, &data);
|
||||
}
|
||||
|
||||
#endif // ORDEREDMAP_H
|
@ -83,7 +83,8 @@ HEADERS += qt_helpers.hpp \
|
||||
logbook/logbook.h logbook/countrydat.h logbook/countriesworked.h logbook/adif.h \
|
||||
messageaveraging.h echoplot.h echograph.h fastgraph.h fastplot.h Modes.hpp WSPRBandHopping.hpp \
|
||||
WsprTxScheduler.h SampleDownloader.hpp MultiSettings.hpp PhaseEqualizationDialog.hpp \
|
||||
IARURegions.hpp MessageBox.hpp EqualizationToolsDialog.hpp
|
||||
IARURegions.hpp MessageBox.hpp EqualizationToolsDialog.hpp \
|
||||
qorderedmap.h
|
||||
|
||||
|
||||
INCLUDEPATH += qmake_only
|
||||
|
Loading…
Reference in New Issue
Block a user