BFM Demod: Delete baseband on stop()

This commit is contained in:
srcejon 2024-05-08 15:00:20 +01:00
parent a31e83d43c
commit 605cf51d7f
5 changed files with 210 additions and 137 deletions

View File

@ -54,16 +54,10 @@ BFMDemod::BFMDemod(DeviceAPI *deviceAPI) :
ChannelAPI(m_channelIdURI, ChannelAPI::StreamSingleSink), ChannelAPI(m_channelIdURI, ChannelAPI::StreamSingleSink),
m_deviceAPI(deviceAPI), m_deviceAPI(deviceAPI),
m_spectrumVis(SDR_RX_SCALEF), m_spectrumVis(SDR_RX_SCALEF),
m_running(false),
m_basebandSampleRate(0) m_basebandSampleRate(0)
{ {
setObjectName(m_channelId); setObjectName(m_channelId);
m_thread = new QThread(this);
m_basebandSink = new BFMDemodBaseband();
m_basebandSink->setSpectrumSink(&m_spectrumVis);
m_basebandSink->setChannel(this);
m_basebandSink->moveToThread(m_thread);
applySettings(m_settings, true); applySettings(m_settings, true);
m_deviceAPI->addChannelSink(this); m_deviceAPI->addChannelSink(this);
@ -82,6 +76,7 @@ BFMDemod::BFMDemod(DeviceAPI *deviceAPI) :
this, this,
&BFMDemod::handleIndexInDeviceSetChanged &BFMDemod::handleIndexInDeviceSetChanged
); );
start();
} }
BFMDemod::~BFMDemod() BFMDemod::~BFMDemod()
@ -96,8 +91,7 @@ BFMDemod::~BFMDemod()
m_deviceAPI->removeChannelSinkAPI(this); m_deviceAPI->removeChannelSinkAPI(this);
m_deviceAPI->removeChannelSink(this); m_deviceAPI->removeChannelSink(this);
delete m_basebandSink; stop();
delete m_thread;
} }
void BFMDemod::setDeviceAPI(DeviceAPI *deviceAPI) void BFMDemod::setDeviceAPI(DeviceAPI *deviceAPI)
@ -125,25 +119,44 @@ void BFMDemod::feed(const SampleVector::const_iterator& begin, const SampleVecto
void BFMDemod::start() void BFMDemod::start()
{ {
if (m_running) {
return;
}
qDebug() << "BFMDemod::start"; qDebug() << "BFMDemod::start";
m_thread = new QThread(this);
m_basebandSink = new BFMDemodBaseband();
m_basebandSink->setSpectrumSink(&m_spectrumVis);
m_basebandSink->setChannel(this);
m_basebandSink->moveToThread(m_thread);
QObject::connect(m_thread, &QThread::finished, m_basebandSink, &QObject::deleteLater);
QObject::connect(m_thread, &QThread::finished, m_thread, &QThread::deleteLater);
if (m_basebandSampleRate != 0) { if (m_basebandSampleRate != 0) {
m_basebandSink->setBasebandSampleRate(m_basebandSampleRate); m_basebandSink->setBasebandSampleRate(m_basebandSampleRate);
} }
m_basebandSink->reset(); m_basebandSink->reset();
m_basebandSink->startWork();
m_thread->start(); m_thread->start();
SpectrumSettings spectrumSettings = m_spectrumVis.getSettings(); SpectrumSettings spectrumSettings = m_spectrumVis.getSettings();
spectrumSettings.m_ssb = true; spectrumSettings.m_ssb = true;
SpectrumVis::MsgConfigureSpectrumVis *msg = SpectrumVis::MsgConfigureSpectrumVis::create(spectrumSettings, false); SpectrumVis::MsgConfigureSpectrumVis *msg = SpectrumVis::MsgConfigureSpectrumVis::create(spectrumSettings, false);
m_spectrumVis.getInputMessageQueue()->push(msg); m_spectrumVis.getInputMessageQueue()->push(msg);
m_running = true;
} }
void BFMDemod::stop() void BFMDemod::stop()
{ {
if (!m_running) {
return;
}
qDebug() << "BFMDemod::stop"; qDebug() << "BFMDemod::stop";
m_thread->exit(); m_running = false;
m_thread->quit();
m_thread->wait(); m_thread->wait();
} }
@ -163,9 +176,12 @@ bool BFMDemod::handleMessage(const Message& cmd)
DSPSignalNotification& notif = (DSPSignalNotification&) cmd; DSPSignalNotification& notif = (DSPSignalNotification&) cmd;
m_basebandSampleRate = notif.getSampleRate(); m_basebandSampleRate = notif.getSampleRate();
// Forward to the sink // Forward to the sink
DSPSignalNotification* rep = new DSPSignalNotification(notif); // make a copy if (m_running)
qDebug() << "BFMDemod::handleMessage: DSPSignalNotification"; {
m_basebandSink->getInputMessageQueue()->push(rep); DSPSignalNotification* rep = new DSPSignalNotification(notif); // make a copy
qDebug() << "BFMDemod::handleMessage: DSPSignalNotification";
m_basebandSink->getInputMessageQueue()->push(rep);
}
if (getMessageQueueToGUI()) { if (getMessageQueueToGUI()) {
getMessageQueueToGUI()->push(new DSPSignalNotification(notif)); getMessageQueueToGUI()->push(new DSPSignalNotification(notif));
@ -257,8 +273,11 @@ void BFMDemod::applySettings(const BFMDemodSettings& settings, bool force)
reverseAPIKeys.append("streamIndex"); reverseAPIKeys.append("streamIndex");
} }
BFMDemodBaseband::MsgConfigureBFMDemodBaseband *msg = BFMDemodBaseband::MsgConfigureBFMDemodBaseband::create(settings, force); if (m_running)
m_basebandSink->getInputMessageQueue()->push(msg); {
BFMDemodBaseband::MsgConfigureBFMDemodBaseband *msg = BFMDemodBaseband::MsgConfigureBFMDemodBaseband::create(settings, force);
m_basebandSink->getInputMessageQueue()->push(msg);
}
if (settings.m_useReverseAPI) if (settings.m_useReverseAPI)
{ {
@ -511,6 +530,10 @@ void BFMDemod::webapiFormatChannelSettings(SWGSDRangel::SWGChannelSettings& resp
void BFMDemod::webapiFormatChannelReport(SWGSDRangel::SWGChannelReport& response) void BFMDemod::webapiFormatChannelReport(SWGSDRangel::SWGChannelReport& response)
{ {
if (!m_running) {
return;
}
double magsqAvg, magsqPeak; double magsqAvg, magsqPeak;
int nbMagsqSamples; int nbMagsqSamples;
getMagSqLevels(magsqAvg, magsqPeak, nbMagsqSamples); getMagSqLevels(magsqAvg, magsqPeak, nbMagsqSamples);
@ -535,28 +558,31 @@ void BFMDemod::webapiFormatChannelReport(SWGSDRangel::SWGChannelReport& response
void BFMDemod::webapiFormatRDSReport(SWGSDRangel::SWGRDSReport *report) void BFMDemod::webapiFormatRDSReport(SWGSDRangel::SWGRDSReport *report)
{ {
report->setDemodStatus(round(getDemodQua())); if (getRDSParser())
report->setDecodStatus(round(getDecoderQua()));
report->setRdsDemodAccumDb(CalcDb::dbPower(std::fabs(getDemodAcc())));
report->setRdsDemodFrequency(getDemodFclk());
report->setPid(new QString(str(boost::format("%04X") % getRDSParser().m_pi_program_identification).c_str()));
report->setPiType(new QString(getRDSParser().pty_table[getRDSParser().m_pi_program_type].c_str()));
report->setPiCoverage(new QString(getRDSParser().coverage_area_codes[getRDSParser().m_pi_area_coverage_index].c_str()));
report->setProgServiceName(new QString(getRDSParser().m_g0_program_service_name));
report->setMusicSpeech(new QString((getRDSParser().m_g0_music_speech ? "Music" : "Speech")));
report->setMonoStereo(new QString((getRDSParser().m_g0_mono_stereo ? "Mono" : "Stereo")));
report->setRadioText(new QString(getRDSParser().m_g2_radiotext));
std::string time = str(boost::format("%4i-%02i-%02i %02i:%02i (%+.1fh)")\
% (1900 + getRDSParser().m_g4_year) % getRDSParser().m_g4_month % getRDSParser().m_g4_day % getRDSParser().m_g4_hours % getRDSParser().m_g4_minutes % getRDSParser().m_g4_local_time_offset);
report->setTime(new QString(time.c_str()));
report->setAltFrequencies(new QList<SWGSDRangel::SWGRDSReport_altFrequencies*>);
for (std::set<double>::iterator it = getRDSParser().m_g0_alt_freq.begin(); it != getRDSParser().m_g0_alt_freq.end(); ++it)
{ {
if (*it > 76.0) report->setDemodStatus(round(getDemodQua()));
report->setDecodStatus(round(getDecoderQua()));
report->setRdsDemodAccumDb(CalcDb::dbPower(std::fabs(getDemodAcc())));
report->setRdsDemodFrequency(getDemodFclk());
report->setPid(new QString(str(boost::format("%04X") % getRDSParser()->m_pi_program_identification).c_str()));
report->setPiType(new QString(getRDSParser()->pty_table[getRDSParser()->m_pi_program_type].c_str()));
report->setPiCoverage(new QString(getRDSParser()->coverage_area_codes[getRDSParser()->m_pi_area_coverage_index].c_str()));
report->setProgServiceName(new QString(getRDSParser()->m_g0_program_service_name));
report->setMusicSpeech(new QString((getRDSParser()->m_g0_music_speech ? "Music" : "Speech")));
report->setMonoStereo(new QString((getRDSParser()->m_g0_mono_stereo ? "Mono" : "Stereo")));
report->setRadioText(new QString(getRDSParser()->m_g2_radiotext));
std::string time = str(boost::format("%4i-%02i-%02i %02i:%02i (%+.1fh)")\
% (1900 + getRDSParser()->m_g4_year) % getRDSParser()->m_g4_month % getRDSParser()->m_g4_day % getRDSParser()->m_g4_hours % getRDSParser()->m_g4_minutes % getRDSParser()->m_g4_local_time_offset);
report->setTime(new QString(time.c_str()));
report->setAltFrequencies(new QList<SWGSDRangel::SWGRDSReport_altFrequencies*>);
for (std::set<double>::iterator it = getRDSParser()->m_g0_alt_freq.begin(); it != getRDSParser()->m_g0_alt_freq.end(); ++it)
{ {
report->getAltFrequencies()->append(new SWGSDRangel::SWGRDSReport_altFrequencies); if (*it > 76.0)
report->getAltFrequencies()->back()->setFrequency(*it); {
report->getAltFrequencies()->append(new SWGSDRangel::SWGRDSReport_altFrequencies);
report->getAltFrequencies()->back()->setFrequency(*it);
}
} }
} }
} }
@ -712,7 +738,7 @@ void BFMDemod::networkManagerFinished(QNetworkReply *reply)
void BFMDemod::handleIndexInDeviceSetChanged(int index) void BFMDemod::handleIndexInDeviceSetChanged(int index)
{ {
if (index < 0) { if (!m_running || (index < 0)) {
return; return;
} }

View File

@ -105,21 +105,27 @@ public:
return m_settings.m_inputFrequencyOffset; return m_settings.m_inputFrequencyOffset;
} }
double getMagSq() const { return m_basebandSink->getMagSq(); } double getMagSq() const { return m_running ? m_basebandSink->getMagSq() : 0.0; }
bool getPilotLock() const { return m_basebandSink->getPilotLock(); } bool getPilotLock() const { return m_running ? m_basebandSink->getPilotLock() : false; }
Real getPilotLevel() const { return m_basebandSink->getPilotLevel(); } Real getPilotLevel() const { return m_running ? m_basebandSink->getPilotLevel() : 0.0f; }
Real getDecoderQua() const { return m_basebandSink->getDecoderQua(); } Real getDecoderQua() const { return m_running ? m_basebandSink->getDecoderQua() : 0.0f; }
bool getDecoderSynced() const { return m_basebandSink->getDecoderSynced(); } bool getDecoderSynced() const { return m_running ? m_basebandSink->getDecoderSynced() : false; }
Real getDemodAcc() const { return m_basebandSink->getDemodAcc(); } Real getDemodAcc() const { return m_running ? m_basebandSink->getDemodAcc() : 0.0f; }
Real getDemodQua() const { return m_basebandSink->getDemodQua(); } Real getDemodQua() const { return m_running ? m_basebandSink->getDemodQua() : 0.0f; }
Real getDemodFclk() const { return m_basebandSink->getDemodFclk(); } Real getDemodFclk() const { return m_running ? m_basebandSink->getDemodFclk() : 0.0f; }
int getAudioSampleRate() const { return m_basebandSink->getAudioSampleRate(); } int getAudioSampleRate() const { return m_running ? m_basebandSink->getAudioSampleRate() : 0; }
void getMagSqLevels(double& avg, double& peak, int& nbSamples) { m_basebandSink->getMagSqLevels(avg, peak, nbSamples); } void getMagSqLevels(double& avg, double& peak, int& nbSamples) {
if (m_running) {
m_basebandSink->getMagSqLevels(avg, peak, nbSamples);
} else {
avg = 0.0; peak = 0.0; nbSamples = 1;
}
}
RDSParser& getRDSParser() { return m_basebandSink->getRDSParser(); } RDSParser *getRDSParser() { return m_running ? &m_basebandSink->getRDSParser() : nullptr; }
virtual int webapiSettingsGet( virtual int webapiSettingsGet(
SWGSDRangel::SWGChannelSettings& response, SWGSDRangel::SWGChannelSettings& response,
@ -157,6 +163,7 @@ private:
DeviceAPI *m_deviceAPI; DeviceAPI *m_deviceAPI;
QThread *m_thread; QThread *m_thread;
BFMDemodBaseband* m_basebandSink; BFMDemodBaseband* m_basebandSink;
bool m_running;
BFMDemodSettings m_settings; BFMDemodSettings m_settings;
SpectrumVis m_spectrumVis; SpectrumVis m_spectrumVis;
int m_basebandSampleRate; //!< stored from device message used when starting baseband sink int m_basebandSampleRate; //!< stored from device message used when starting baseband sink

View File

@ -30,20 +30,15 @@
MESSAGE_CLASS_DEFINITION(BFMDemodBaseband::MsgConfigureBFMDemodBaseband, Message) MESSAGE_CLASS_DEFINITION(BFMDemodBaseband::MsgConfigureBFMDemodBaseband, Message)
BFMDemodBaseband::BFMDemodBaseband() : BFMDemodBaseband::BFMDemodBaseband() :
m_running(false),
m_messageQueueToGUI(nullptr), m_messageQueueToGUI(nullptr),
m_spectrumVis(nullptr) m_spectrumVis(nullptr)
{ {
m_sampleFifo.setSize(SampleSinkFifo::getSizePolicy(48000)); m_sampleFifo.setSize(SampleSinkFifo::getSizePolicy(48000));
m_channelizer = new DownChannelizer(&m_sink); m_channelizer = new DownChannelizer(&m_sink);
qDebug("BFMDemodBaseband::BFMDemodBaseband"); qDebug("BFMDemodBaseband::BFMDemodBaseband");
QObject::connect(
&m_sampleFifo,
&SampleSinkFifo::dataReady,
this,
&BFMDemodBaseband::handleData,
Qt::QueuedConnection
);
DSPEngine::instance()->getAudioDeviceManager()->addAudioSink(m_sink.getAudioFifo(), getInputMessageQueue()); DSPEngine::instance()->getAudioDeviceManager()->addAudioSink(m_sink.getAudioFifo(), getInputMessageQueue());
m_sink.applyAudioSampleRate(DSPEngine::instance()->getAudioDeviceManager()->getOutputSampleRate()); m_sink.applyAudioSampleRate(DSPEngine::instance()->getAudioDeviceManager()->getOutputSampleRate());
@ -65,6 +60,33 @@ void BFMDemodBaseband::reset()
m_channelSampleRate = 0; m_channelSampleRate = 0;
} }
void BFMDemodBaseband::startWork()
{
QMutexLocker mutexLocker(&m_mutex);
QObject::connect(
&m_sampleFifo,
&SampleSinkFifo::dataReady,
this,
&BFMDemodBaseband::handleData,
Qt::QueuedConnection
);
connect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages()));
m_running = true;
}
void BFMDemodBaseband::stopWork()
{
QMutexLocker mutexLocker(&m_mutex);
disconnect(&m_inputMessageQueue, SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages()));
QObject::disconnect(
&m_sampleFifo,
&SampleSinkFifo::dataReady,
this,
&BFMDemodBaseband::handleData
);
m_running = false;
}
void BFMDemodBaseband::feed(const SampleVector::const_iterator& begin, const SampleVector::const_iterator& end) void BFMDemodBaseband::feed(const SampleVector::const_iterator& begin, const SampleVector::const_iterator& end)
{ {
m_sampleFifo.write(begin, end); m_sampleFifo.write(begin, end);

View File

@ -62,12 +62,15 @@ public:
BFMDemodBaseband(); BFMDemodBaseband();
~BFMDemodBaseband(); ~BFMDemodBaseband();
void reset(); void reset();
void startWork();
void stopWork();
void feed(const SampleVector::const_iterator& begin, const SampleVector::const_iterator& end); void feed(const SampleVector::const_iterator& begin, const SampleVector::const_iterator& end);
MessageQueue *getInputMessageQueue() { return &m_inputMessageQueue; } //!< Get the queue for asynchronous inbound communication MessageQueue *getInputMessageQueue() { return &m_inputMessageQueue; } //!< Get the queue for asynchronous inbound communication
int getChannelSampleRate() const; int getChannelSampleRate() const;
void setBasebandSampleRate(int sampleRate); void setBasebandSampleRate(int sampleRate);
void setSpectrumSink(SpectrumVis* spectrumSink) { m_spectrumVis = spectrumSink; m_sink.setSpectrumSink((BasebandSampleSink*) spectrumSink); } void setSpectrumSink(SpectrumVis* spectrumSink) { m_spectrumVis = spectrumSink; m_sink.setSpectrumSink((BasebandSampleSink*) spectrumSink); }
void setChannel(ChannelAPI *channel); void setChannel(ChannelAPI *channel);
bool isRunning() const { return m_running; }
void setMessageQueueToGUI(MessageQueue *messageQueue) { m_messageQueueToGUI = messageQueue; } void setMessageQueueToGUI(MessageQueue *messageQueue) { m_messageQueueToGUI = messageQueue; }
int getAudioSampleRate() const { return m_sink.getAudioSampleRate(); } int getAudioSampleRate() const { return m_sink.getAudioSampleRate(); }
@ -92,6 +95,7 @@ private:
BFMDemodSink m_sink; BFMDemodSink m_sink;
MessageQueue m_inputMessageQueue; //!< Queue for asynchronous inbound communication MessageQueue m_inputMessageQueue; //!< Queue for asynchronous inbound communication
BFMDemodSettings m_settings; BFMDemodSettings m_settings;
bool m_running;
QRecursiveMutex m_mutex; QRecursiveMutex m_mutex;
MessageQueue *m_messageQueueToGUI; MessageQueue *m_messageQueueToGUI;
SpectrumVis *m_spectrumVis; SpectrumVis *m_spectrumVis;

View File

@ -227,7 +227,9 @@ void BFMDemodGUI::on_clearData_clicked(bool checked)
(void) checked; (void) checked;
if (ui->rds->isChecked()) if (ui->rds->isChecked())
{ {
m_bfmDemod->getRDSParser().clearAllFields(); if (m_bfmDemod->getRDSParser()) {
m_bfmDemod->getRDSParser()->clearAllFields();
}
ui->g00ProgServiceName->clear(); ui->g00ProgServiceName->clear();
ui->go2Text->clear(); ui->go2Text->clear();
@ -246,14 +248,18 @@ void BFMDemodGUI::on_clearData_clicked(bool checked)
void BFMDemodGUI::on_g14ProgServiceNames_currentIndexChanged(int _index) void BFMDemodGUI::on_g14ProgServiceNames_currentIndexChanged(int _index)
{ {
if (!m_bfmDemod->getRDSParser()) {
return;
}
uint32_t index = _index & 0x7FFFFFF; uint32_t index = _index & 0x7FFFFFF;
if (index < m_g14ComboIndex.size()) if (index < m_g14ComboIndex.size())
{ {
unsigned int piKey = m_g14ComboIndex[index]; unsigned int piKey = m_g14ComboIndex[index];
RDSParser::freqs_map_t::const_iterator mIt = m_bfmDemod->getRDSParser().m_g14_mapped_freqs.find(piKey); RDSParser::freqs_map_t::const_iterator mIt = m_bfmDemod->getRDSParser()->m_g14_mapped_freqs.find(piKey);
if (mIt != m_bfmDemod->getRDSParser().m_g14_mapped_freqs.end()) if (mIt != m_bfmDemod->getRDSParser()->m_g14_mapped_freqs.end())
{ {
ui->g14MappedFrequencies->clear(); ui->g14MappedFrequencies->clear();
RDSParser::freqs_set_t::iterator sIt = (mIt->second).begin(); RDSParser::freqs_set_t::iterator sIt = (mIt->second).begin();
@ -269,9 +275,9 @@ void BFMDemodGUI::on_g14ProgServiceNames_currentIndexChanged(int _index)
ui->g14MappedFrequencies->setEnabled(ui->g14MappedFrequencies->count() > 0); ui->g14MappedFrequencies->setEnabled(ui->g14MappedFrequencies->count() > 0);
} }
mIt = m_bfmDemod->getRDSParser().m_g14_alt_freqs.find(piKey); mIt = m_bfmDemod->getRDSParser()->m_g14_alt_freqs.find(piKey);
if (mIt != m_bfmDemod->getRDSParser().m_g14_alt_freqs.end()) if (mIt != m_bfmDemod->getRDSParser()->m_g14_alt_freqs.end())
{ {
ui->g14AltFrequencies->clear(); ui->g14AltFrequencies->clear();
RDSParser::freqs_set_t::iterator sIt = (mIt->second).begin(); RDSParser::freqs_set_t::iterator sIt = (mIt->second).begin();
@ -597,33 +603,41 @@ void BFMDemodGUI::tick()
void BFMDemodGUI::rdsUpdateFixedFields() void BFMDemodGUI::rdsUpdateFixedFields()
{ {
ui->g00Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[0].c_str()); if (!m_bfmDemod->getRDSParser()) {
ui->g01Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[1].c_str()); return;
ui->g02Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[2].c_str()); }
ui->g03Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[3].c_str());
ui->g04Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[4].c_str());
//ui->g05Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[5].c_str());
//ui->g06Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[6].c_str());
//ui->g07Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[7].c_str());
ui->g08Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[8].c_str());
ui->g09Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[9].c_str());
ui->g14Label->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[14].c_str());
ui->g00CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[0].c_str()); ui->g00Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[0].c_str());
ui->g01CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[1].c_str()); ui->g01Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[1].c_str());
ui->g02CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[2].c_str()); ui->g02Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[2].c_str());
ui->g03CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[3].c_str()); ui->g03Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[3].c_str());
ui->g04CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[4].c_str()); ui->g04Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[4].c_str());
ui->g05CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[5].c_str()); //ui->g05Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[5].c_str());
ui->g06CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[6].c_str()); //ui->g06Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[6].c_str());
ui->g07CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[7].c_str()); //ui->g07Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[7].c_str());
ui->g08CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[8].c_str()); ui->g08Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[8].c_str());
ui->g09CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[9].c_str()); ui->g09Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[9].c_str());
ui->g14CountLabel->setText(m_bfmDemod->getRDSParser().rds_group_acronym_tags[14].c_str()); ui->g14Label->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[14].c_str());
ui->g00CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[0].c_str());
ui->g01CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[1].c_str());
ui->g02CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[2].c_str());
ui->g03CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[3].c_str());
ui->g04CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[4].c_str());
ui->g05CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[5].c_str());
ui->g06CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[6].c_str());
ui->g07CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[7].c_str());
ui->g08CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[8].c_str());
ui->g09CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[9].c_str());
ui->g14CountLabel->setText(m_bfmDemod->getRDSParser()->rds_group_acronym_tags[14].c_str());
} }
void BFMDemodGUI::rdsUpdate(bool force) void BFMDemodGUI::rdsUpdate(bool force)
{ {
if (!m_bfmDemod->getRDSParser()) {
return;
}
// Quality metrics // Quality metrics
ui->demodQText->setText(QString("%1 %").arg(m_bfmDemod->getDemodQua(), 0, 'f', 0)); ui->demodQText->setText(QString("%1 %").arg(m_bfmDemod->getDemodQua(), 0, 'f', 0));
ui->decoderQText->setText(QString("%1 %").arg(m_bfmDemod->getDecoderQua(), 0, 'f', 0)); ui->decoderQText->setText(QString("%1 %").arg(m_bfmDemod->getDecoderQua(), 0, 'f', 0));
@ -638,21 +652,21 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// PI group // PI group
if (m_bfmDemod->getRDSParser().m_pi_updated || force) if (m_bfmDemod->getRDSParser()->m_pi_updated || force)
{ {
ui->piLabel->setStyleSheet("QLabel { background-color : green; }"); ui->piLabel->setStyleSheet("QLabel { background-color : green; }");
ui->piCountText->setNum((int) m_bfmDemod->getRDSParser().m_pi_count); ui->piCountText->setNum((int) m_bfmDemod->getRDSParser()->m_pi_count);
QString pistring(str(boost::format("%04X") % m_bfmDemod->getRDSParser().m_pi_program_identification).c_str()); QString pistring(str(boost::format("%04X") % m_bfmDemod->getRDSParser()->m_pi_program_identification).c_str());
ui->piText->setText(pistring); ui->piText->setText(pistring);
if (m_bfmDemod->getRDSParser().m_pi_traffic_program) { if (m_bfmDemod->getRDSParser()->m_pi_traffic_program) {
ui->piTPIndicator->setStyleSheet("QLabel { background-color : green; }"); ui->piTPIndicator->setStyleSheet("QLabel { background-color : green; }");
} else { } else {
ui->piTPIndicator->setStyleSheet("QLabel { background:rgb(79,79,79); }"); ui->piTPIndicator->setStyleSheet("QLabel { background:rgb(79,79,79); }");
} }
ui->piType->setText(QString(m_bfmDemod->getRDSParser().pty_table[m_bfmDemod->getRDSParser().m_pi_program_type].c_str())); ui->piType->setText(QString(m_bfmDemod->getRDSParser()->pty_table[m_bfmDemod->getRDSParser()->m_pi_program_type].c_str()));
ui->piCoverage->setText(QString(m_bfmDemod->getRDSParser().coverage_area_codes[m_bfmDemod->getRDSParser().m_pi_area_coverage_index].c_str())); ui->piCoverage->setText(QString(m_bfmDemod->getRDSParser()->coverage_area_codes[m_bfmDemod->getRDSParser()->m_pi_area_coverage_index].c_str()));
} }
else else
{ {
@ -660,29 +674,29 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G0 group // G0 group
if (m_bfmDemod->getRDSParser().m_g0_updated || force) if (m_bfmDemod->getRDSParser()->m_g0_updated || force)
{ {
ui->g00Label->setStyleSheet("QLabel { background-color : green; }"); ui->g00Label->setStyleSheet("QLabel { background-color : green; }");
ui->g00CountText->setNum((int) m_bfmDemod->getRDSParser().m_g0_count); ui->g00CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g0_count);
if (m_bfmDemod->getRDSParser().m_g0_psn_bitmap == 0b1111) { if (m_bfmDemod->getRDSParser()->m_g0_psn_bitmap == 0b1111) {
ui->g00ProgServiceName->setText(QString(m_bfmDemod->getRDSParser().m_g0_program_service_name)); ui->g00ProgServiceName->setText(QString(m_bfmDemod->getRDSParser()->m_g0_program_service_name));
} }
if (m_bfmDemod->getRDSParser().m_g0_traffic_announcement) { if (m_bfmDemod->getRDSParser()->m_g0_traffic_announcement) {
ui->g00TrafficAnnouncement->setStyleSheet("QLabel { background-color : green; }"); ui->g00TrafficAnnouncement->setStyleSheet("QLabel { background-color : green; }");
} else { } else {
ui->g00TrafficAnnouncement->setStyleSheet("QLabel { background:rgb(79,79,79); }"); ui->g00TrafficAnnouncement->setStyleSheet("QLabel { background:rgb(79,79,79); }");
} }
ui->g00MusicSpeech->setText(QString((m_bfmDemod->getRDSParser().m_g0_music_speech ? "Music" : "Speech"))); ui->g00MusicSpeech->setText(QString((m_bfmDemod->getRDSParser()->m_g0_music_speech ? "Music" : "Speech")));
ui->g00MonoStereo->setText(QString((m_bfmDemod->getRDSParser().m_g0_mono_stereo ? "Mono" : "Stereo"))); ui->g00MonoStereo->setText(QString((m_bfmDemod->getRDSParser()->m_g0_mono_stereo ? "Mono" : "Stereo")));
if (m_bfmDemod->getRDSParser().m_g0_af_updated) if (m_bfmDemod->getRDSParser()->m_g0_af_updated)
{ {
ui->g00AltFrequenciesBox->clear(); ui->g00AltFrequenciesBox->clear();
for (std::set<double>::iterator it = m_bfmDemod->getRDSParser().m_g0_alt_freq.begin(); it != m_bfmDemod->getRDSParser().m_g0_alt_freq.end(); ++it) for (std::set<double>::iterator it = m_bfmDemod->getRDSParser()->m_g0_alt_freq.begin(); it != m_bfmDemod->getRDSParser()->m_g0_alt_freq.end(); ++it)
{ {
if (*it > 76.0) if (*it > 76.0)
{ {
@ -701,20 +715,20 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G1 group // G1 group
if (m_bfmDemod->getRDSParser().m_g1_updated || force) if (m_bfmDemod->getRDSParser()->m_g1_updated || force)
{ {
ui->g01Label->setStyleSheet("QLabel { background-color : green; }"); ui->g01Label->setStyleSheet("QLabel { background-color : green; }");
ui->g01CountText->setNum((int) m_bfmDemod->getRDSParser().m_g1_count); ui->g01CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g1_count);
if ((m_bfmDemod->getRDSParser().m_g1_country_page_index >= 0) && (m_bfmDemod->getRDSParser().m_g1_country_index >= 0)) { if ((m_bfmDemod->getRDSParser()->m_g1_country_page_index >= 0) && (m_bfmDemod->getRDSParser()->m_g1_country_index >= 0)) {
ui->g01CountryCode->setText(QString((m_bfmDemod->getRDSParser().pi_country_codes[m_bfmDemod->getRDSParser().m_g1_country_page_index][m_bfmDemod->getRDSParser().m_g1_country_index]).c_str())); ui->g01CountryCode->setText(QString((m_bfmDemod->getRDSParser()->pi_country_codes[m_bfmDemod->getRDSParser()->m_g1_country_page_index][m_bfmDemod->getRDSParser()->m_g1_country_index]).c_str()));
} }
if (m_bfmDemod->getRDSParser().m_g1_language_index >= 0) { if (m_bfmDemod->getRDSParser()->m_g1_language_index >= 0) {
ui->g01Language->setText(QString(m_bfmDemod->getRDSParser().language_codes[m_bfmDemod->getRDSParser().m_g1_language_index].c_str())); ui->g01Language->setText(QString(m_bfmDemod->getRDSParser()->language_codes[m_bfmDemod->getRDSParser()->m_g1_language_index].c_str()));
} }
ui->g01DHM->setText(QString(str(boost::format("%id:%i:%i") % m_bfmDemod->getRDSParser().m_g1_pin_day % m_bfmDemod->getRDSParser().m_g1_pin_hour % m_bfmDemod->getRDSParser().m_g1_pin_minute).c_str())); ui->g01DHM->setText(QString(str(boost::format("%id:%i:%i") % m_bfmDemod->getRDSParser()->m_g1_pin_day % m_bfmDemod->getRDSParser()->m_g1_pin_hour % m_bfmDemod->getRDSParser()->m_g1_pin_minute).c_str()));
} }
else else
{ {
@ -722,11 +736,11 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G2 group // G2 group
if (m_bfmDemod->getRDSParser().m_g2_updated || force) if (m_bfmDemod->getRDSParser()->m_g2_updated || force)
{ {
ui->g02Label->setStyleSheet("QLabel { background-color : green; }"); ui->g02Label->setStyleSheet("QLabel { background-color : green; }");
ui->g02CountText->setNum((int) m_bfmDemod->getRDSParser().m_g2_count); ui->g02CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g2_count);
bool radiotext_AB_flag = m_bfmDemod->getRDSParser().m_radiotext_AB_flag; bool radiotext_AB_flag = m_bfmDemod->getRDSParser()->m_radiotext_AB_flag;
if (!m_radiotext_AB_flag && radiotext_AB_flag) // B -> A transiition is start of new text if (!m_radiotext_AB_flag && radiotext_AB_flag) // B -> A transiition is start of new text
{ {
@ -734,7 +748,7 @@ void BFMDemodGUI::rdsUpdate(bool force)
ui->go2PrevText->setText(oldText); ui->go2PrevText->setText(oldText);
} }
ui->go2Text->setText(QString(m_bfmDemod->getRDSParser().m_g2_radiotext)); ui->go2Text->setText(QString(m_bfmDemod->getRDSParser()->m_g2_radiotext));
m_radiotext_AB_flag = radiotext_AB_flag; m_radiotext_AB_flag = radiotext_AB_flag;
} }
else else
@ -743,11 +757,11 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G3 group // G3 group
if (m_bfmDemod->getRDSParser().m_g3_updated || force) if (m_bfmDemod->getRDSParser()->m_g3_updated || force)
{ {
ui->g03Label->setStyleSheet("QLabel { background-color : green; }"); ui->g03Label->setStyleSheet("QLabel { background-color : green; }");
ui->g03CountText->setNum((int) m_bfmDemod->getRDSParser().m_g3_count); ui->g03CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g3_count);
std::string g3str = str(boost::format("%02X%c %04X %04X") % m_bfmDemod->getRDSParser().m_g3_appGroup % (m_bfmDemod->getRDSParser().m_g3_groupB ? 'B' : 'A') % m_bfmDemod->getRDSParser().m_g3_message % m_bfmDemod->getRDSParser().m_g3_aid); std::string g3str = str(boost::format("%02X%c %04X %04X") % m_bfmDemod->getRDSParser()->m_g3_appGroup % (m_bfmDemod->getRDSParser()->m_g3_groupB ? 'B' : 'A') % m_bfmDemod->getRDSParser()->m_g3_message % m_bfmDemod->getRDSParser()->m_g3_aid);
ui->g03Data->setText(QString(g3str.c_str())); ui->g03Data->setText(QString(g3str.c_str()));
} }
else else
@ -756,12 +770,12 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G4 group // G4 group
if (m_bfmDemod->getRDSParser().m_g4_updated || force) if (m_bfmDemod->getRDSParser()->m_g4_updated || force)
{ {
ui->g04Label->setStyleSheet("QLabel { background-color : green; }"); ui->g04Label->setStyleSheet("QLabel { background-color : green; }");
ui->g04CountText->setNum((int) m_bfmDemod->getRDSParser().m_g4_count); ui->g04CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g4_count);
std::string time = str(boost::format("%4i-%02i-%02i %02i:%02i (%+.1fh)")\ std::string time = str(boost::format("%4i-%02i-%02i %02i:%02i (%+.1fh)")\
% (1900 + m_bfmDemod->getRDSParser().m_g4_year) % m_bfmDemod->getRDSParser().m_g4_month % m_bfmDemod->getRDSParser().m_g4_day % m_bfmDemod->getRDSParser().m_g4_hours % m_bfmDemod->getRDSParser().m_g4_minutes % m_bfmDemod->getRDSParser().m_g4_local_time_offset); % (1900 + m_bfmDemod->getRDSParser()->m_g4_year) % m_bfmDemod->getRDSParser()->m_g4_month % m_bfmDemod->getRDSParser()->m_g4_day % m_bfmDemod->getRDSParser()->m_g4_hours % m_bfmDemod->getRDSParser()->m_g4_minutes % m_bfmDemod->getRDSParser()->m_g4_local_time_offset);
ui->g04Time->setText(QString(time.c_str())); ui->g04Time->setText(QString(time.c_str()));
} }
else else
@ -770,42 +784,42 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G5 group // G5 group
if (m_bfmDemod->getRDSParser().m_g5_updated || force) if (m_bfmDemod->getRDSParser()->m_g5_updated || force)
{ {
ui->g05CountText->setNum((int) m_bfmDemod->getRDSParser().m_g5_count); ui->g05CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g5_count);
} }
// G6 group // G6 group
if (m_bfmDemod->getRDSParser().m_g6_updated || force) if (m_bfmDemod->getRDSParser()->m_g6_updated || force)
{ {
ui->g06CountText->setNum((int) m_bfmDemod->getRDSParser().m_g6_count); ui->g06CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g6_count);
} }
// G7 group // G7 group
if (m_bfmDemod->getRDSParser().m_g7_updated || force) if (m_bfmDemod->getRDSParser()->m_g7_updated || force)
{ {
ui->g07CountText->setNum((int) m_bfmDemod->getRDSParser().m_g7_count); ui->g07CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g7_count);
} }
// G8 group // G8 group
if (m_bfmDemod->getRDSParser().m_g8_updated || force) if (m_bfmDemod->getRDSParser()->m_g8_updated || force)
{ {
ui->g08Label->setStyleSheet("QLabel { background-color : green; }"); ui->g08Label->setStyleSheet("QLabel { background-color : green; }");
ui->g08CountText->setNum((int) m_bfmDemod->getRDSParser().m_g8_count); ui->g08CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g8_count);
std::ostringstream os; std::ostringstream os;
os << (m_bfmDemod->getRDSParser().m_g8_sign ? "-" : "+") << m_bfmDemod->getRDSParser().m_g8_extent + 1; os << (m_bfmDemod->getRDSParser()->m_g8_sign ? "-" : "+") << m_bfmDemod->getRDSParser()->m_g8_extent + 1;
ui->g08Extent->setText(QString(os.str().c_str())); ui->g08Extent->setText(QString(os.str().c_str()));
int event_line = RDSTMC::get_tmc_event_code_index(m_bfmDemod->getRDSParser().m_g8_event, 1); int event_line = RDSTMC::get_tmc_event_code_index(m_bfmDemod->getRDSParser()->m_g8_event, 1);
ui->g08TMCEvent->setText(QString(RDSTMC::get_tmc_events(event_line, 1).c_str())); ui->g08TMCEvent->setText(QString(RDSTMC::get_tmc_events(event_line, 1).c_str()));
QString pistring(str(boost::format("%04X") % m_bfmDemod->getRDSParser().m_g8_location).c_str()); QString pistring(str(boost::format("%04X") % m_bfmDemod->getRDSParser()->m_g8_location).c_str());
ui->g08Location->setText(pistring); ui->g08Location->setText(pistring);
if (m_bfmDemod->getRDSParser().m_g8_label_index >= 0) { if (m_bfmDemod->getRDSParser()->m_g8_label_index >= 0) {
ui->g08Description->setText(QString(m_bfmDemod->getRDSParser().label_descriptions[m_bfmDemod->getRDSParser().m_g8_label_index].c_str())); ui->g08Description->setText(QString(m_bfmDemod->getRDSParser()->label_descriptions[m_bfmDemod->getRDSParser()->m_g8_label_index].c_str()));
} }
ui->g08Content->setNum(m_bfmDemod->getRDSParser().m_g8_content); ui->g08Content->setNum(m_bfmDemod->getRDSParser()->m_g8_content);
} }
else else
{ {
@ -813,11 +827,11 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G9 group // G9 group
if (m_bfmDemod->getRDSParser().m_g9_updated || force) if (m_bfmDemod->getRDSParser()->m_g9_updated || force)
{ {
ui->g09Label->setStyleSheet("QLabel { background-color : green; }"); ui->g09Label->setStyleSheet("QLabel { background-color : green; }");
ui->g09CountText->setNum((int) m_bfmDemod->getRDSParser().m_g9_count); ui->g09CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g9_count);
std::string g9str = str(boost::format("%02X %04X %04X %02X %04X") % m_bfmDemod->getRDSParser().m_g9_varA % m_bfmDemod->getRDSParser().m_g9_cA % m_bfmDemod->getRDSParser().m_g9_dA % m_bfmDemod->getRDSParser().m_g9_varB % m_bfmDemod->getRDSParser().m_g9_dB); std::string g9str = str(boost::format("%02X %04X %04X %02X %04X") % m_bfmDemod->getRDSParser()->m_g9_varA % m_bfmDemod->getRDSParser()->m_g9_cA % m_bfmDemod->getRDSParser()->m_g9_dA % m_bfmDemod->getRDSParser()->m_g9_varB % m_bfmDemod->getRDSParser()->m_g9_dB);
ui->g09Data->setText(QString(g9str.c_str())); ui->g09Data->setText(QString(g9str.c_str()));
} }
else else
@ -826,18 +840,18 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
// G14 group // G14 group
if (m_bfmDemod->getRDSParser().m_g14_updated || force) if (m_bfmDemod->getRDSParser()->m_g14_updated || force)
{ {
ui->g14CountText->setNum((int) m_bfmDemod->getRDSParser().m_g14_count); ui->g14CountText->setNum((int) m_bfmDemod->getRDSParser()->m_g14_count);
if (m_bfmDemod->getRDSParser().m_g14_data_available) if (m_bfmDemod->getRDSParser()->m_g14_data_available)
{ {
ui->g14Label->setStyleSheet("QLabel { background-color : green; }"); ui->g14Label->setStyleSheet("QLabel { background-color : green; }");
m_g14ComboIndex.clear(); m_g14ComboIndex.clear();
ui->g14ProgServiceNames->clear(); ui->g14ProgServiceNames->clear();
RDSParser::psns_map_t::iterator it = m_bfmDemod->getRDSParser().m_g14_program_service_names.begin(); RDSParser::psns_map_t::iterator it = m_bfmDemod->getRDSParser()->m_g14_program_service_names.begin();
const RDSParser::psns_map_t::iterator itEnd = m_bfmDemod->getRDSParser().m_g14_program_service_names.end(); const RDSParser::psns_map_t::iterator itEnd = m_bfmDemod->getRDSParser()->m_g14_program_service_names.end();
int i = 0; int i = 0;
for (; it != itEnd; ++it, i++) for (; it != itEnd; ++it, i++)
@ -853,7 +867,7 @@ void BFMDemodGUI::rdsUpdate(bool force)
} }
} }
m_bfmDemod->getRDSParser().clearUpdateFlags(); m_bfmDemod->getRDSParser()->clearUpdateFlags();
} }
void BFMDemodGUI::changeFrequency(qint64 f) void BFMDemodGUI::changeFrequency(qint64 f)