From 2e6b173fb1d615e403fa1ee293919f692e8dd9fb Mon Sep 17 00:00:00 2001 From: "Charles J. Cliffe" Date: Mon, 7 Sep 2015 20:46:03 -0400 Subject: [PATCH] attempt to fix waterfall stutter working parts --- CMakeLists.txt | 2 + src/process/FFTDataDistributor.cpp | 81 +++++++++++++++++++++++++++++ src/process/FFTDataDistributor.h | 22 ++++++++ src/process/FFTVisualDataThread.cpp | 2 +- src/process/FFTVisualDataThread.h | 1 + src/sdr/SDRPostThread.cpp | 31 ++++------- src/sdr/SDRPostThread.h | 4 -- 7 files changed, 117 insertions(+), 26 deletions(-) create mode 100644 src/process/FFTDataDistributor.cpp create mode 100644 src/process/FFTDataDistributor.h diff --git a/CMakeLists.txt b/CMakeLists.txt index ff832df..f10bbd5 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -264,6 +264,7 @@ SET (cubicsdr_sources src/process/ScopeVisualProcessor.cpp src/process/SpectrumVisualProcessor.cpp src/process/FFTVisualDataThread.cpp + src/process/FFTDataDistributor.cpp src/process/SpectrumVisualDataThread.cpp src/ui/GLPanel.cpp external/rtaudio/RtAudio.cpp @@ -319,6 +320,7 @@ SET (cubicsdr_headers src/process/ScopeVisualProcessor.h src/process/SpectrumVisualProcessor.h src/process/FFTVisualDataThread.h + src/process/FFTDataDistributor.h src/process/SpectrumVisualDataThread.h src/ui/GLPanel.h src/ui/UITestCanvas.cpp diff --git a/src/process/FFTDataDistributor.cpp b/src/process/FFTDataDistributor.cpp new file mode 100644 index 0000000..818c955 --- /dev/null +++ b/src/process/FFTDataDistributor.cpp @@ -0,0 +1,81 @@ +#include "FFTDataDistributor.h" + +FFTDataDistributor::FFTDataDistributor() : linesPerSecond(DEFAULT_WATERFALL_LPS), lineRateAccum(0.0), fftSize(DEFAULT_FFT_SIZE) { +} + +void FFTDataDistributor::setFFTSize(int fftSize) { + this->fftSize = fftSize; +} + +void FFTDataDistributor::setLinesPerSecond(int lines) { + this->linesPerSecond = lines; +} + +int FFTDataDistributor::getLinesPerSecond() { + return this->linesPerSecond; +} + +void FFTDataDistributor::process() { + while (!input->empty()) { + if (!isAnyOutputEmpty()) { + return; + } + DemodulatorThreadIQData *inp; + input->pop(inp); + + if (inp) { + if (inputBuffer.sampleRate != inp->sampleRate || inputBuffer.frequency != inp->frequency) { + inputBuffer.sampleRate = inp->sampleRate; + inputBuffer.frequency = inp->frequency; + inputBuffer.data.assign(inp->data.begin(), inp->data.end()); + } else { + inputBuffer.data.insert(inputBuffer.data.end(), inp->data.begin(), inp->data.end()); + } + inp->decRefCount(); + } else { + continue; + } + + // number of seconds contained in input + double inputTime = (double)inputBuffer.data.size() / (double)inputBuffer.sampleRate; + // number of lines in input + double inputLines = (double)inputBuffer.data.size()/(double)fftSize; + + // ratio required to achieve the desired rate + double lineRateStep = ((double)linesPerSecond * inputTime)/(double)inputLines; + + if (inputBuffer.data.size() >= fftSize) { + int numProcessed = 0; + +// if (lineRateAccum + (lineRateStep * floor((double)inputBuffer.data.size()/(double)fftSize)) < 1.0) { +// // move along, nothing to see here.. +// lineRateAccum += (lineRateStep * inputBuffer.data.size()/fftSize); +// numProcessed = inputBuffer.data.size()/fftSize; +// } else { + for (int i = 0, iMax = inputBuffer.data.size(); i < iMax; i += fftSize) { + if ((i + fftSize) > iMax) { + break; + } + lineRateAccum += lineRateStep; + + if (lineRateAccum >= 1.0) { + DemodulatorThreadIQData *outp = outputBuffers.getBuffer(); + outp->frequency = inputBuffer.frequency; + outp->sampleRate = inputBuffer.sampleRate; + outp->data.assign(inputBuffer.data.begin()+i,inputBuffer.data.begin()+i+fftSize); + distribute(outp); + + while (lineRateAccum >= 1.0) { + lineRateAccum -= 1.0; + } + } + + numProcessed += fftSize; + } +// } + if (numProcessed) { + inputBuffer.data.erase(inputBuffer.data.begin(), inputBuffer.data.begin() + numProcessed); + } + } + } +} diff --git a/src/process/FFTDataDistributor.h b/src/process/FFTDataDistributor.h new file mode 100644 index 0000000..561a0e7 --- /dev/null +++ b/src/process/FFTDataDistributor.h @@ -0,0 +1,22 @@ +#pragma once + +#include "VisualProcessor.h" +#include "DemodDefs.h" +#include + +class FFTDataDistributor : public VisualProcessor { +public: + FFTDataDistributor(); + void setFFTSize(int fftSize); + void setLinesPerSecond(int lines); + int getLinesPerSecond(); + +protected: + void process(); + + DemodulatorThreadIQData inputBuffer, tempBuffer; + ReBuffer outputBuffers; + int fftSize; + int linesPerSecond; + double lineRateAccum; +}; diff --git a/src/process/FFTVisualDataThread.cpp b/src/process/FFTVisualDataThread.cpp index dd5ce72..fe27525 100644 --- a/src/process/FFTVisualDataThread.cpp +++ b/src/process/FFTVisualDataThread.cpp @@ -37,7 +37,7 @@ void FFTVisualDataThread::run() { while(!terminated) { - std::this_thread::sleep_for(std::chrono::milliseconds(12)); + std::this_thread::sleep_for(std::chrono::milliseconds(1)); int fftSize = wproc.getDesiredInputSize(); diff --git a/src/process/FFTVisualDataThread.h b/src/process/FFTVisualDataThread.h index a08cd4d..31eb971 100644 --- a/src/process/FFTVisualDataThread.h +++ b/src/process/FFTVisualDataThread.h @@ -2,6 +2,7 @@ #include "IOThread.h" #include "SpectrumVisualProcessor.h" +#include "FFTDataDistributor.h" class FFTVisualDataThread : public IOThread { public: diff --git a/src/sdr/SDRPostThread.cpp b/src/sdr/SDRPostThread.cpp index e19cc51..7e76654 100644 --- a/src/sdr/SDRPostThread.cpp +++ b/src/sdr/SDRPostThread.cpp @@ -6,7 +6,7 @@ #include SDRPostThread::SDRPostThread() : IOThread(), - iqDataInQueue(NULL), iqDataOutQueue(NULL), iqVisualQueue(NULL), dcFilter(NULL), num_vis_samples(16384*2) { + iqDataInQueue(NULL), iqDataOutQueue(NULL), iqVisualQueue(NULL), dcFilter(NULL){ swapIQ.store(false); @@ -50,14 +50,6 @@ void SDRPostThread::removeDemodulator(DemodulatorInstance *demod) { busy_demod.unlock(); } -void SDRPostThread::setNumVisSamples(int num_vis_samples_in) { - num_vis_samples = num_vis_samples_in; -} - -int SDRPostThread::getNumVisSamples() { - return num_vis_samples; -} - void SDRPostThread::setSwapIQ(bool swapIQ) { this->swapIQ.store(swapIQ); } @@ -93,7 +85,6 @@ void SDRPostThread::run() { iqDataInQueue->pop(data_in); // std::lock_guard < std::mutex > lock(data_in->m_mutex); - int num_vis_samples = this->num_vis_samples; if (data_in && data_in->data.size()) { int dataSize = data_in->data.size()/2; @@ -118,21 +109,19 @@ void SDRPostThread::run() { iirfilt_crcf_execute_block(dcFilter, &fpData[0], dataSize, &dataOut[0]); - if (iqVisualQueue != NULL && iqVisualQueue->empty()) { + if (iqVisualQueue != NULL && !iqVisualQueue->full()) { DemodulatorThreadIQData *visualDataOut = visualDataBuffers.getBuffer(); visualDataOut->setRefCount(1); - if (num_vis_samples > dataOut.size()) { - num_vis_samples = dataOut.size(); - } + int num_vis_samples = dataOut.size(); - if (visualDataOut->data.size() < num_vis_samples) { - if (visualDataOut->data.capacity() < num_vis_samples) { - visualDataOut->data.reserve(num_vis_samples); - } - visualDataOut->data.resize(num_vis_samples); - } - +// if (visualDataOut->data.size() < num_vis_samples) { +// if (visualDataOut->data.capacity() < num_vis_samples) { +// visualDataOut->data.reserve(num_vis_samples); +// } +// visualDataOut->data.resize(num_vis_samples); +// } +// visualDataOut->frequency = data_in->frequency; visualDataOut->sampleRate = data_in->sampleRate; visualDataOut->data.assign(dataOut.begin(), dataOut.begin() + num_vis_samples); diff --git a/src/sdr/SDRPostThread.h b/src/sdr/SDRPostThread.h index e08ab58..0162e7e 100644 --- a/src/sdr/SDRPostThread.h +++ b/src/sdr/SDRPostThread.h @@ -11,9 +11,6 @@ public: void bindDemodulator(DemodulatorInstance *demod); void removeDemodulator(DemodulatorInstance *demod); - void setNumVisSamples(int num_vis_samples_in); - int getNumVisSamples(); - void setSwapIQ(bool swapIQ); bool getSwapIQ(); @@ -28,7 +25,6 @@ protected: std::mutex busy_demod; std::vector demodulators; iirfilt_crcf dcFilter; - int num_vis_samples; std::atomic_bool swapIQ; ReBuffer visualDataBuffers;