Initial Commit
This commit is contained in:
@@ -0,0 +1,216 @@
|
||||
#include "adif.h"
|
||||
|
||||
#include <QFile>
|
||||
#include <QTextStream>
|
||||
#include <QDateTime>
|
||||
#include <QDebug>
|
||||
|
||||
/*
|
||||
<CALL:4>W1XT<BAND:3>20m<FREQ:6>14.076<GRIDSQUARE:4>DM33<MODE:4>JT65<RST_RCVD:3>-21<RST_SENT:3>-14<QSO_DATE:8>20110422<TIME_ON:6>041712<TIME_OFF:6>042435<TX_PWR:1>4<COMMENT:34>1st JT65A QSO. Him: mag loop 20W<STATION_CALLSIGN:6>VK3ACF<MY_GRIDSQUARE:6>qf22lb<eor>
|
||||
<CALL:6>IK1SOW<BAND:3>20m<FREQ:6>14.076<GRIDSQUARE:4>JN35<MODE:4>JT65<RST_RCVD:3>-19<RST_SENT:3>-11<QSO_DATE:8>20110422<TIME_ON:6>052501<TIME_OFF:6>053359<TX_PWR:1>3<STATION_CALLSIGN:6>VK3ACF<MY_GRIDSQUARE:6>qf22lb<eor>
|
||||
<CALL:6:S>W4ABC> ...
|
||||
*/
|
||||
|
||||
void ADIF::init(QString const& filename)
|
||||
{
|
||||
_filename = filename;
|
||||
_data.clear();
|
||||
}
|
||||
|
||||
|
||||
QString ADIF::extractField(QString const& record, QString const& fieldName) const
|
||||
{
|
||||
int fieldNameIndex = record.indexOf (fieldName + ':', 0, Qt::CaseInsensitive);
|
||||
if (fieldNameIndex >=0)
|
||||
{
|
||||
int closingBracketIndex = record.indexOf('>',fieldNameIndex);
|
||||
int fieldLengthIndex = record.indexOf(':',fieldNameIndex); // find the size delimiter
|
||||
int dataTypeIndex = -1;
|
||||
if (fieldLengthIndex >= 0)
|
||||
{
|
||||
dataTypeIndex = record.indexOf(':',fieldLengthIndex+1); // check for a second : indicating there is a data type
|
||||
if (dataTypeIndex > closingBracketIndex)
|
||||
dataTypeIndex = -1; // second : was found but it was beyond the closing >
|
||||
}
|
||||
|
||||
if ((closingBracketIndex > fieldNameIndex) && (fieldLengthIndex > fieldNameIndex) && (fieldLengthIndex< closingBracketIndex))
|
||||
{
|
||||
int fieldLengthCharCount = closingBracketIndex - fieldLengthIndex -1;
|
||||
if (dataTypeIndex >= 0)
|
||||
fieldLengthCharCount -= 2; // data type indicator is always a colon followed by a single character
|
||||
QString fieldLengthString = record.mid(fieldLengthIndex+1,fieldLengthCharCount);
|
||||
int fieldLength = fieldLengthString.toInt();
|
||||
if (fieldLength > 0)
|
||||
{
|
||||
QString field = record.mid(closingBracketIndex+1,fieldLength);
|
||||
return field;
|
||||
}
|
||||
}
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
|
||||
|
||||
void ADIF::load()
|
||||
{
|
||||
_data.clear();
|
||||
QFile inputFile(_filename);
|
||||
if (inputFile.open(QIODevice::ReadOnly))
|
||||
{
|
||||
QTextStream in(&inputFile);
|
||||
QString buffer;
|
||||
bool pre_read {false};
|
||||
int end_position {-1};
|
||||
|
||||
// skip optional header record
|
||||
do
|
||||
{
|
||||
buffer += in.readLine () + '\n';
|
||||
if (buffer.startsWith (QChar {'<'})) // denotes no header
|
||||
{
|
||||
pre_read = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
end_position = buffer.indexOf ("<EOH>", 0, Qt::CaseInsensitive);
|
||||
}
|
||||
}
|
||||
while (!in.atEnd () && !pre_read && end_position < 0);
|
||||
if (!pre_read) // found header
|
||||
{
|
||||
buffer.remove (0, end_position + 5);
|
||||
}
|
||||
while (buffer.size () || !in.atEnd ())
|
||||
{
|
||||
do
|
||||
{
|
||||
end_position = buffer.indexOf ("<EOR>", 0, Qt::CaseInsensitive);
|
||||
if (!in.atEnd () && end_position < 0)
|
||||
{
|
||||
buffer += in.readLine () + '\n';
|
||||
}
|
||||
}
|
||||
while (!in.atEnd () && end_position < 0);
|
||||
int record_length {end_position >= 0 ? end_position + 5 : -1};
|
||||
auto record = buffer.left (record_length).trimmed ();
|
||||
auto next_record = buffer.indexOf (QChar {'<'}, record_length);
|
||||
buffer.remove (0, next_record >=0 ? next_record : buffer.size ());
|
||||
record = record.mid (record.indexOf (QChar {'<'}));
|
||||
add (extractField (record, "CALL")
|
||||
, extractField (record, "BAND")
|
||||
, extractField (record, "MODE")
|
||||
, extractField (record, "QSO_DATE"));
|
||||
}
|
||||
inputFile.close ();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void ADIF::add(QString const& call, QString const& band, QString const& mode, QString const& date)
|
||||
{
|
||||
QSO q;
|
||||
q.call = call;
|
||||
q.band = band;
|
||||
q.mode = mode;
|
||||
q.date = date;
|
||||
if (q.call.size ())
|
||||
{
|
||||
_data.insert(q.call,q);
|
||||
// qDebug() << "Added as worked:" << call << band << mode << date;
|
||||
}
|
||||
}
|
||||
|
||||
// return true if in the log same band and mode (where JT65 == JT9)
|
||||
bool ADIF::match(QString const& call, QString const& band, QString const& mode) const
|
||||
{
|
||||
QList<QSO> qsos = _data.values(call);
|
||||
if (qsos.size()>0)
|
||||
{
|
||||
QSO q;
|
||||
foreach(q,qsos)
|
||||
{
|
||||
if ( (band.compare(q.band,Qt::CaseInsensitive) == 0)
|
||||
|| (band=="")
|
||||
|| (q.band==""))
|
||||
{
|
||||
if (
|
||||
(
|
||||
((mode.compare("JT65",Qt::CaseInsensitive)==0) ||
|
||||
(mode.compare("JT9",Qt::CaseInsensitive)==0) ||
|
||||
(mode.compare("FT8",Qt::CaseInsensitive)==0))
|
||||
&&
|
||||
((q.mode.compare("JT65",Qt::CaseInsensitive)==0) ||
|
||||
(q.mode.compare("JT9",Qt::CaseInsensitive)==0) ||
|
||||
(q.mode.compare("FT8",Qt::CaseInsensitive)==0))
|
||||
)
|
||||
|| (mode.compare(q.mode,Qt::CaseInsensitive)==0)
|
||||
|| (mode=="")
|
||||
|| (q.mode=="")
|
||||
)
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
QList<QString> ADIF::getCallList() const
|
||||
{
|
||||
QList<QString> p;
|
||||
QMultiHash<QString,QSO>::const_iterator i = _data.constBegin();
|
||||
while (i != _data.constEnd())
|
||||
{
|
||||
p << i.key();
|
||||
++i;
|
||||
}
|
||||
return p;
|
||||
}
|
||||
|
||||
int ADIF::getCount() const
|
||||
{
|
||||
return _data.size();
|
||||
}
|
||||
|
||||
|
||||
// open ADIF file and append the QSO details. Return true on success
|
||||
bool ADIF::addQSOToFile(QString const& hisCall, QString const& hisGrid, QString const& mode, QString const& rptSent, QString const& rptRcvd, QDateTime const& dateTimeOn, QDateTime const& dateTimeOff, QString const& band,
|
||||
QString const& comments, QString const& name, QString const& strDialFreq, QString const& m_myCall, QString const& m_myGrid, QString const& m_txPower)
|
||||
{
|
||||
QFile f2(_filename);
|
||||
if (!f2.open(QIODevice::Text | QIODevice::Append))
|
||||
return false;
|
||||
else
|
||||
{
|
||||
QTextStream out(&f2);
|
||||
if (f2.size()==0)
|
||||
out << "WSJT-X ADIF Export<eoh>" << endl; // new file
|
||||
|
||||
QString t;
|
||||
t="<call:" + QString::number(hisCall.length()) + ">" + hisCall;
|
||||
t+=" <gridsquare:" + QString::number(hisGrid.length()) + ">" + hisGrid;
|
||||
t+=" <mode:" + QString::number(mode.length()) + ">" + mode;
|
||||
t+=" <rst_sent:" + QString::number(rptSent.length()) + ">" + rptSent;
|
||||
t+=" <rst_rcvd:" + QString::number(rptRcvd.length()) + ">" + rptRcvd;
|
||||
t+=" <qso_date:8>" + dateTimeOn.date ().toString ("yyyyMMdd");
|
||||
t+=" <time_on:6>" + dateTimeOn.time ().toString ("hhmmss");
|
||||
t+=" <qso_date_off:8>" + dateTimeOff.date ().toString ("yyyyMMdd");
|
||||
t+=" <time_off:6>" + dateTimeOff.time ().toString ("hhmmss");
|
||||
t+=" <band:" + QString::number(band.length()) + ">" + band;
|
||||
t+=" <freq:" + QString::number(strDialFreq.length()) + ">" + strDialFreq;
|
||||
t+=" <station_callsign:" + QString::number(m_myCall.length()) + ">" +
|
||||
m_myCall;
|
||||
t+=" <my_gridsquare:" + QString::number(m_myGrid.length()) + ">" +
|
||||
m_myGrid;
|
||||
if(m_txPower!="") t+= " <tx_pwr:" + QString::number(m_txPower.length()) +
|
||||
">" + m_txPower;
|
||||
if(comments!="") t+=" <comment:" + QString::number(comments.length()) +
|
||||
">" + comments;
|
||||
if(name!="") t+=" <name:" + QString::number(name.length()) +
|
||||
">" + name;
|
||||
t+=" <eor>";
|
||||
out << t << endl;
|
||||
f2.close();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Reads an ADIF log file into memory
|
||||
* Searches log for call, band and mode
|
||||
* VK3ACF July 2013
|
||||
*/
|
||||
|
||||
|
||||
#ifndef __ADIF_H
|
||||
#define __ADIF_H
|
||||
|
||||
#if defined (QT5)
|
||||
#include <QList>
|
||||
#include <QString>
|
||||
#include <QMultiHash>
|
||||
#else
|
||||
#include <QtGui>
|
||||
#endif
|
||||
|
||||
class QDateTime;
|
||||
|
||||
class ADIF
|
||||
{
|
||||
public:
|
||||
void init(QString const& filename);
|
||||
void load();
|
||||
void add(QString const& call, QString const& band, QString const& mode, QString const& date);
|
||||
bool match(QString const& call, QString const& band, QString const& mode) const;
|
||||
QList<QString> getCallList() const;
|
||||
int getCount() const;
|
||||
|
||||
// open ADIF file and append the QSO details. Return true on success
|
||||
bool addQSOToFile(QString const& hisCall, QString const& hisGrid, QString const& mode, QString const& rptSent, QString const& rptRcvd, QDateTime const& dateTimeOn, QDateTime const& dateTimeOff, QString const& band,
|
||||
QString const& comments, QString const& name, QString const& strDialFreq, QString const& m_myCall, QString const& m_myGrid, QString const& m_txPower);
|
||||
|
||||
private:
|
||||
struct QSO
|
||||
{
|
||||
QString call,band,mode,date;
|
||||
};
|
||||
|
||||
QMultiHash<QString, QSO> _data;
|
||||
QString _filename;
|
||||
|
||||
QString extractField(QString const& line, QString const& fieldName) const;
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
#include "countriesworked.h"
|
||||
|
||||
void CountriesWorked::init(const QStringList countryNames)
|
||||
{
|
||||
_data.clear();
|
||||
foreach(QString name,countryNames)
|
||||
_data.insert(name,false);
|
||||
}
|
||||
|
||||
void CountriesWorked::setAsWorked(const QString countryName)
|
||||
{
|
||||
if (_data.contains(countryName))
|
||||
_data.insert(countryName,true);
|
||||
}
|
||||
|
||||
bool CountriesWorked::getHasWorked(const QString countryName) const
|
||||
{
|
||||
if (_data.contains(countryName))
|
||||
return _data.value(countryName);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
int CountriesWorked::getWorkedCount() const
|
||||
{
|
||||
int count = 0;
|
||||
foreach (bool value,_data)
|
||||
if (value)
|
||||
count += 1;
|
||||
return count;
|
||||
}
|
||||
|
||||
int CountriesWorked::getSize() const
|
||||
{
|
||||
return _data.count();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* maintains a list of country names that have been worked
|
||||
* VK3ACF July 2013
|
||||
*/
|
||||
|
||||
#ifndef __COUNTRIESWORKDED_H
|
||||
#define __COUNTRIESWORKDED_H
|
||||
|
||||
#include <QList>
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
#include <QHash>
|
||||
|
||||
|
||||
class CountriesWorked
|
||||
{
|
||||
public:
|
||||
void init(const QStringList countryNames);
|
||||
void setAsWorked(const QString countryName);
|
||||
bool getHasWorked(const QString countryName) const;
|
||||
int getWorkedCount() const;
|
||||
int getSize() const;
|
||||
|
||||
private:
|
||||
QHash<QString, bool> _data;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -0,0 +1,153 @@
|
||||
/*
|
||||
#Sov Mil Order of Malta: 15: 28: EU: 41.90: -12.43: -1.0: 1A:
|
||||
#1A;
|
||||
#Spratly Islands: 26: 50: AS: 9.88: -114.23: -8.0: 1S:
|
||||
#1S,9M0,BV9S;
|
||||
#Monaco: 14: 27: EU: 43.73: -7.40: -1.0: 3A:
|
||||
#3A;
|
||||
#Heard Island: 39: 68: AF: -53.08: -73.50: -5.0: VK0H:
|
||||
#=VK0IR;
|
||||
#Macquarie Island: 30: 60: OC: -54.60: -158.88: -10.0: VK0M:
|
||||
#=VK0KEV;
|
||||
#Cocos-Keeling: 29: 54: OC: -12.15: -96.82: -6.5: VK9C:
|
||||
#AX9C,AX9Y,VH9C,VH9Y,VI9C,VI9Y,VJ9C,VJ9Y,VK9C,VK9Y,VL9C,VL9Y,VM9C,VM9Y,
|
||||
#VN9C,VN9Y,VZ9C,VZ9Y,=VK9AA;
|
||||
*/
|
||||
|
||||
|
||||
#include "countrydat.h"
|
||||
#include <QFile>
|
||||
#include <QTextStream>
|
||||
|
||||
|
||||
void CountryDat::init(const QString filename)
|
||||
{
|
||||
_filename = filename;
|
||||
_data.clear();
|
||||
}
|
||||
|
||||
QString CountryDat::_extractName(const QString line) const
|
||||
{
|
||||
int s1 = line.indexOf(':');
|
||||
if (s1>=0)
|
||||
{
|
||||
QString name = line.mid(0,s1);
|
||||
return name;
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
void CountryDat::_removeBrackets(QString &line, const QString a, const QString b) const
|
||||
{
|
||||
int s1 = line.indexOf(a);
|
||||
while (s1 >= 0)
|
||||
{
|
||||
int s2 = line.indexOf(b);
|
||||
line = line.mid(0,s1) + line.mid(s2+1,-1);
|
||||
s1 = line.indexOf(a);
|
||||
}
|
||||
}
|
||||
|
||||
QStringList CountryDat::_extractPrefix(QString &line, bool &more) const
|
||||
{
|
||||
line = line.remove(" \n");
|
||||
line = line.replace(" ","");
|
||||
|
||||
_removeBrackets(line,"(",")");
|
||||
_removeBrackets(line,"[","]");
|
||||
_removeBrackets(line,"<",">");
|
||||
_removeBrackets(line,"~","~");
|
||||
|
||||
int s1 = line.indexOf(';');
|
||||
more = true;
|
||||
if (s1 >= 0)
|
||||
{
|
||||
line = line.mid(0,s1);
|
||||
more = false;
|
||||
}
|
||||
|
||||
QStringList r = line.split(',');
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
|
||||
void CountryDat::load()
|
||||
{
|
||||
_data.clear();
|
||||
_countryNames.clear(); //used by countriesWorked
|
||||
|
||||
QFile inputFile(_filename);
|
||||
if (inputFile.open(QIODevice::ReadOnly))
|
||||
{
|
||||
QTextStream in(&inputFile);
|
||||
while ( !in.atEnd() )
|
||||
{
|
||||
QString line1 = in.readLine();
|
||||
if ( !in.atEnd() )
|
||||
{
|
||||
QString line2 = in.readLine();
|
||||
|
||||
QString name = _extractName(line1);
|
||||
if (name.length()>0)
|
||||
{
|
||||
_countryNames << name;
|
||||
bool more = true;
|
||||
QStringList prefixs;
|
||||
while (more)
|
||||
{
|
||||
QStringList p = _extractPrefix(line2,more);
|
||||
prefixs += p;
|
||||
if (more)
|
||||
line2 = in.readLine();
|
||||
}
|
||||
|
||||
QString p;
|
||||
foreach(p,prefixs)
|
||||
{
|
||||
if (p.length() > 0)
|
||||
_data.insert(p,name);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
inputFile.close();
|
||||
}
|
||||
}
|
||||
|
||||
// return country name else ""
|
||||
QString CountryDat::find(QString call) const
|
||||
{
|
||||
call = call.toUpper ();
|
||||
|
||||
// check for exact match first
|
||||
if (_data.contains ("=" + call))
|
||||
{
|
||||
return fixup (_data.value ("=" + call), call);
|
||||
}
|
||||
|
||||
auto prefix = call;
|
||||
while (prefix.size () >= 1)
|
||||
{
|
||||
if (_data.contains (prefix))
|
||||
{
|
||||
return fixup (_data.value (prefix), call);
|
||||
}
|
||||
prefix = prefix.left (prefix.size () - 1);
|
||||
}
|
||||
return QString {};
|
||||
}
|
||||
|
||||
QString CountryDat::fixup (QString country, QString const& call) const
|
||||
{
|
||||
//
|
||||
// deal with special rules that cty.dat does not cope with
|
||||
//
|
||||
|
||||
// KG4 2x1 and 2x3 calls that map to Gitmo are mainland US not Gitmo
|
||||
if (call.startsWith ("KG4") && call.size () != 5)
|
||||
{
|
||||
country.replace ("Guantanamo Bay", "United States");
|
||||
}
|
||||
return country;
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Reads cty.dat file
|
||||
* Establishes a map between prefixes and their country names
|
||||
* VK3ACF July 2013
|
||||
*/
|
||||
|
||||
|
||||
#ifndef __COUNTRYDAT_H
|
||||
#define __COUNTRYDAT_H
|
||||
|
||||
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
#include <QHash>
|
||||
|
||||
|
||||
class CountryDat
|
||||
{
|
||||
public:
|
||||
void init(const QString filename);
|
||||
void load();
|
||||
QString find(QString prefix) const; // return country name or ""
|
||||
QStringList getCountryNames() const { return _countryNames; };
|
||||
|
||||
private:
|
||||
QString _extractName(const QString line) const;
|
||||
void _removeBrackets(QString &line, const QString a, const QString b) const;
|
||||
QStringList _extractPrefix(QString &line, bool &more) const;
|
||||
QString fixup (QString country, QString const& call) const;
|
||||
|
||||
QString _filename;
|
||||
QStringList _countryNames;
|
||||
QHash<QString, QString> _data;
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,100 @@
|
||||
#include "logbook.h"
|
||||
#include <QDebug>
|
||||
#include <QFontMetrics>
|
||||
#include <QStandardPaths>
|
||||
#include <QDir>
|
||||
|
||||
namespace
|
||||
{
|
||||
auto logFileName = "wsjtx_log.adi";
|
||||
auto countryFileName = "cty.dat";
|
||||
}
|
||||
|
||||
void LogBook::init()
|
||||
{
|
||||
QDir dataPath {QStandardPaths::writableLocation (QStandardPaths::DataLocation)};
|
||||
QString countryDataFilename;
|
||||
if (dataPath.exists (countryFileName))
|
||||
{
|
||||
// User override
|
||||
countryDataFilename = dataPath.absoluteFilePath (countryFileName);
|
||||
}
|
||||
else
|
||||
{
|
||||
countryDataFilename = QString {":/"} + countryFileName;
|
||||
}
|
||||
|
||||
_countries.init(countryDataFilename);
|
||||
_countries.load();
|
||||
|
||||
_worked.init(_countries.getCountryNames());
|
||||
|
||||
_log.init(dataPath.absoluteFilePath (logFileName));
|
||||
_log.load();
|
||||
|
||||
_setAlreadyWorkedFromLog();
|
||||
|
||||
/*
|
||||
int QSOcount = _log.getCount();
|
||||
int count = _worked.getWorkedCount();
|
||||
qDebug() << QSOcount << "QSOs and" << count << "countries worked in file" << logFilename;
|
||||
*/
|
||||
|
||||
// QString call = "ok1ct";
|
||||
// QString countryName;
|
||||
// bool callWorkedBefore,countryWorkedBefore;
|
||||
// match(/*in*/call, /*out*/ countryName,callWorkedBefore,countryWorkedBefore);
|
||||
// qDebug() << countryName;
|
||||
|
||||
}
|
||||
|
||||
|
||||
void LogBook::_setAlreadyWorkedFromLog()
|
||||
{
|
||||
QList<QString> calls = _log.getCallList();
|
||||
QString c;
|
||||
foreach(c,calls)
|
||||
{
|
||||
QString countryName = _countries.find(c);
|
||||
if (countryName.length() > 0)
|
||||
{
|
||||
_worked.setAsWorked(countryName);
|
||||
//qDebug() << countryName << " worked " << c;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void LogBook::match(/*in*/const QString call,
|
||||
/*out*/ QString &countryName,
|
||||
bool &callWorkedBefore,
|
||||
bool &countryWorkedBefore) const
|
||||
{
|
||||
if (call.length() > 0)
|
||||
{
|
||||
QString currentMode = "JT9"; // JT65 == JT9 in ADIF::match()
|
||||
QString currentBand = ""; // match any band
|
||||
callWorkedBefore = _log.match(call,currentBand,currentMode);
|
||||
countryName = _countries.find(call);
|
||||
|
||||
if (countryName.length() > 0) // country was found
|
||||
countryWorkedBefore = _worked.getHasWorked(countryName);
|
||||
else
|
||||
{
|
||||
countryName = "where?"; //error: prefix not found
|
||||
countryWorkedBefore = false;
|
||||
}
|
||||
}
|
||||
//qDebug() << "Logbook:" << call << ":" << countryName << "Cty B4:" << countryWorkedBefore << "call B4:" << callWorkedBefore;
|
||||
}
|
||||
|
||||
void LogBook::addAsWorked(const QString call, const QString band, const QString mode, const QString date)
|
||||
{
|
||||
//qDebug() << "adding " << call << " as worked";
|
||||
_log.add(call,band,mode,date);
|
||||
QString countryName = _countries.find(call);
|
||||
if (countryName.length() > 0)
|
||||
_worked.setAsWorked(countryName);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* From an ADIF file and cty.dat, get a call's DXCC entity and its worked before status
|
||||
* VK3ACF July 2013
|
||||
*/
|
||||
|
||||
#ifndef LOGBOOK_H
|
||||
#define LOGBOOK_H
|
||||
|
||||
|
||||
#include <QString>
|
||||
#include <QFont>
|
||||
|
||||
#include "countrydat.h"
|
||||
#include "countriesworked.h"
|
||||
#include "adif.h"
|
||||
|
||||
class QDir;
|
||||
|
||||
class LogBook
|
||||
{
|
||||
public:
|
||||
void init();
|
||||
void match(/*in*/ const QString call,
|
||||
/*out*/ QString &countryName,
|
||||
bool &callWorkedBefore,
|
||||
bool &countryWorkedBefore) const;
|
||||
void addAsWorked(const QString call, const QString band, const QString mode, const QString date);
|
||||
|
||||
private:
|
||||
CountryDat _countries;
|
||||
CountriesWorked _worked;
|
||||
ADIF _log;
|
||||
|
||||
void _setAlreadyWorkedFromLog();
|
||||
|
||||
};
|
||||
|
||||
#endif // LOGBOOK_H
|
||||
|
||||
Reference in New Issue
Block a user