Audacity 3.2.0
Classes | Public Member Functions | Protected Member Functions | Static Protected Member Functions | Private Member Functions | Private Attributes | List of all members
SpectralDataManager::Worker Class Reference

#include <SpectralDataManager.h>

Inheritance diagram for SpectralDataManager::Worker:
[legend]
Collaboration diagram for SpectralDataManager::Worker:
[legend]

Classes

struct  MyWindow
 

Public Member Functions

 Worker (WaveChannel *pChannel, const Setting &setting)
 
 ~Worker ()
 
bool Process (const WaveChannel &channel, const std::shared_ptr< SpectralData > &sDataPtr)
 
int ProcessSnapping (const WaveChannel &channel, long long int startSC, int hopSize, size_t winSize, double threshold, int targetFreqBin)
 
std::vector< int > ProcessOvertones (const WaveChannel &channel, long long int startSC, int hopSize, size_t winSize, double threshold, int targetFreqBin)
 
- Public Member Functions inherited from TrackSpectrumTransformer
 TrackSpectrumTransformer (WaveChannel *pOutputTrack, bool needsOutput, eWindowFunctions inWindowType, eWindowFunctions outWindowType, size_t windowSize, unsigned stepsPerWindow, bool leadingPadding, bool trailingPadding)
 
 ~TrackSpectrumTransformer () override
 
bool Process (const WindowProcessor &processor, const WaveChannel &channel, size_t queueLength, sampleCount start, sampleCount len)
 Invokes Start(), ProcessSamples(), and Finish() More...
 
- Public Member Functions inherited from SpectrumTransformer
 SpectrumTransformer (bool needsOutput, eWindowFunctions inWindowType, eWindowFunctions outWindowType, size_t windowSize, unsigned stepsPerWindow, bool leadingPadding, bool trailingPadding)
 
virtual ~SpectrumTransformer ()
 
bool NeedsOutput () const
 
bool Start (size_t queueLength)
 Call once before a sequence of calls to ProcessSamples; Invokes DoStart. More...
 
bool ProcessSamples (const WindowProcessor &processor, const float *buffer, size_t len)
 Call multiple times. More...
 
bool Finish (const WindowProcessor &processor)
 
virtual std::unique_ptr< WindowNewWindow (size_t windowSize)
 Allocates a window to place in the queue. More...
 
virtual bool DoStart ()
 Called before any calls to ProcessWindow. More...
 
virtual void DoOutput (const float *outBuffer, size_t mStepSize)=0
 Called within ProcessSamples if output was requested. More...
 
virtual bool DoFinish ()
 Called after the last call to ProcessWindow(). More...
 
size_t TotalQueueSize () const
 Useful functions to implement WindowProcesser: More...
 
size_t CurrentQueueSize () const
 How many windows in the queue have been filled? More...
 
bool QueueIsFull () const
 
WindowNth (int n)
 Access the queue, so you can inspect and modify any window in it. More...
 
WindowNewest ()
 
WindowLatest ()
 

Protected Member Functions

MyWindowNthWindow (int nn)
 
std::unique_ptr< WindowNewWindow (size_t windowSize) override
 Allocates a window to place in the queue. More...
 
bool DoStart () override
 Called before any calls to ProcessWindow. More...
 
bool DoFinish () override
 Called after the last call to ProcessWindow(). More...
 
- Protected Member Functions inherited from TrackSpectrumTransformer
bool DoStart () override
 Called before any calls to ProcessWindow. More...
 
void DoOutput (const float *outBuffer, size_t mStepSize) override
 Called within ProcessSamples if output was requested. More...
 
bool DoFinish () override
 Called after the last call to ProcessWindow(). More...
 

Static Protected Member Functions

static bool Processor (SpectrumTransformer &transformer)
 
static bool OvertonesProcessor (SpectrumTransformer &transformer)
 
static bool SnappingProcessor (SpectrumTransformer &transformer)
 

Private Member Functions

bool ApplyEffectToSelection ()
 

Private Attributes

std::shared_ptr< SpectralDatampSpectralData
 
int mWindowCount { 0 }
 
double mSnapSamplingRate
 
double mSnapThreshold
 
double mOvertonesThreshold
 
std::vector< int > mOvertonesTargetFreqBin
 
int mSnapTargetFreqBin
 
int mSnapReturnFreqBin { -1 }
 
long long mStartHopNum { 0 }
 

Additional Inherited Members

- Public Types inherited from SpectrumTransformer
using FloatVector = std::vector< float >
 
using WindowProcessor = std::function< bool(SpectrumTransformer &) >
 Type of function that transforms windows in the queue. More...
 
- Static Public Member Functions inherited from TrackSpectrumTransformer
static bool PostProcess (WaveTrack &outputTrack, sampleCount len)
 Final flush and trimming of tail samples. More...
 
- Protected Attributes inherited from SpectrumTransformer
const size_t mWindowSize
 
const size_t mSpectrumSize
 
const unsigned mStepsPerWindow
 
const size_t mStepSize
 
const bool mLeadingPadding
 
const bool mTrailingPadding
 

Detailed Description

Definition at line 40 of file SpectralDataManager.h.

Constructor & Destructor Documentation

◆ Worker()

SpectralDataManager::Worker::Worker ( WaveChannel pChannel,
const Setting setting 
)

Definition at line 151 of file SpectralDataManager.cpp.

153 : TrackSpectrumTransformer{ pChannel,
154 setting.mNeedOutput, setting.mInWindowType, setting.mOutWindowType,
155 setting.mWindowSize, setting.mStepsPerWindow,
156 setting.mLeadingPadding, setting.mTrailingPadding
157 }
158// Work members
159{
160}
Subclass of SpectrumTransformer that rewrites a track.

◆ ~Worker()

SpectralDataManager::Worker::~Worker ( )
default

Member Function Documentation

◆ ApplyEffectToSelection()

bool SpectralDataManager::Worker::ApplyEffectToSelection ( )
private

Definition at line 324 of file SpectralDataManager.cpp.

324 {
325 auto &record = NthWindow(0);
326
327 for(auto &spectralDataMap: mpSpectralData->dataHistory){
328 // For all added frequency
329 for(const int &freqBin: spectralDataMap[mStartHopNum]){
330 record.mRealFFTs[freqBin] = 0;
331 record.mImagFFTs[freqBin] = 0;
332 }
333 }
334
335 mWindowCount++;
336 mStartHopNum ++;
337 return true;
338}
std::shared_ptr< SpectralData > mpSpectralData

◆ DoFinish()

bool SpectralDataManager::Worker::DoFinish ( )
overrideprotectedvirtual

Called after the last call to ProcessWindow().

Returns
false to abort processing. Default implementation just returns true.

Reimplemented from SpectrumTransformer.

Definition at line 167 of file SpectralDataManager.cpp.

167 {
169}
bool DoFinish() override
Called after the last call to ProcessWindow().

References TrackSpectrumTransformer::DoFinish().

Here is the call graph for this function:

◆ DoStart()

bool SpectralDataManager::Worker::DoStart ( )
overrideprotectedvirtual

Called before any calls to ProcessWindow.

More queue initializations can be done here.

Returns
false to abort processing. Default implementation just returns true.

Reimplemented from SpectrumTransformer.

Definition at line 164 of file SpectralDataManager.cpp.

164 {
166}
bool DoStart() override
Called before any calls to ProcessWindow.

References TrackSpectrumTransformer::DoStart().

Here is the call graph for this function:

◆ NewWindow()

auto SpectralDataManager::Worker::NewWindow ( size_t  windowSize)
overrideprotectedvirtual

Allocates a window to place in the queue.

Only when initializing – windows are recycled thereafter. You can derive from Window to add fields, and then override this factory function.

Reimplemented from SpectrumTransformer.

Definition at line 340 of file SpectralDataManager.cpp.

342{
343 return std::make_unique<MyWindow>(windowSize);
344}

◆ NthWindow()

MyWindow & SpectralDataManager::Worker::NthWindow ( int  nn)
inlineprotected

Definition at line 71 of file SpectralDataManager.h.

71 {
72 return static_cast<MyWindow&>(Nth(nn));
73 }
Window & Nth(int n)
Access the queue, so you can inspect and modify any window in it.

References SpectrumTransformer::Nth().

Here is the call graph for this function:

◆ OvertonesProcessor()

bool SpectralDataManager::Worker::OvertonesProcessor ( SpectrumTransformer transformer)
staticprotected

Definition at line 256 of file SpectralDataManager.cpp.

256 {
257 auto &worker = static_cast<Worker &>(transformer);
258 // Compute power spectrum in the newest window
259 {
260 MyWindow &record = worker.NthWindow(0);
261 float *pSpectrum = &record.mSpectrums[0];
262 const double dc = record.mRealFFTs[0];
263 *pSpectrum++ = dc * dc;
264 float *pReal = &record.mRealFFTs[1], *pImag = &record.mImagFFTs[1];
265 for (size_t nn = worker.mSpectrumSize - 2; nn--;) {
266 const double re = *pReal++, im = *pImag++;
267 *pSpectrum++ = re * re + im * im;
268 }
269 const double nyquist = record.mImagFFTs[0];
270 *pSpectrum = nyquist * nyquist;
271
272 const double &spectrumSize = worker.mSpectrumSize;
273 const int &targetBin = worker.mSnapTargetFreqBin;
274
275 float targetValue = record.mSpectrums[targetBin];
276
277 double fundamental = targetBin;
278 int overtone = 2, binNum = 0;
279 pSpectrum = &record.mSpectrums[0];
280 while ( fundamental >= 1 &&
281 ( binNum = lrint( fundamental * overtone ) ) < spectrumSize) {
282 // Examine a few bins each way up and down
283 constexpr int tolerance = 3;
284 auto begin = pSpectrum + std::max( 0, binNum - (tolerance + 1) );
285 auto end = pSpectrum +
286 std::min<size_t>( spectrumSize, binNum + (tolerance + 1) + 1 );
287 auto peak = std::max_element( begin, end );
288
289 // Abandon if the peak is too far up or down
290 if ( peak == begin || peak == end - 1 )
291 break;
292
293 int newBin = peak - pSpectrum;
294 worker.mOvertonesTargetFreqBin.push_back(newBin);
295 // Correct the estimate of the fundamental
296 fundamental = double(newBin) / overtone++;
297 }
298 }
299 return true;
300}
Worker(WaveChannel *pChannel, const Setting &setting)
#define lrint(dbl)
Definition: float_cast.h:169
auto end(const Ptr< Type, BaseDeleter > &p)
Enables range-for.
Definition: PackedArray.h:159
auto begin(const Ptr< Type, BaseDeleter > &p)
Enables range-for.
Definition: PackedArray.h:150

References PackedArray::begin(), PackedArray::end(), lrint, and SpectralDataManager::Worker::MyWindow::mSpectrums.

Here is the call graph for this function:

◆ Process()

bool SpectralDataManager::Worker::Process ( const WaveChannel channel,
const std::shared_ptr< SpectralData > &  sDataPtr 
)

Definition at line 171 of file SpectralDataManager.cpp.

173{
174 mpSpectralData = pSpectralData;
175 const auto hopSize = mpSpectralData->GetHopSize();
176 const auto startSample = mpSpectralData->GetStartSample();
177 // Correct the first hop num, because SpectrumTransformer will send
178 // a few initial windows that overlay the range only partially
179 mStartHopNum = startSample / hopSize - (mStepsPerWindow - 1);
180 mWindowCount = 0;
182 mpSpectralData->GetCorrectedStartSample(), mpSpectralData->GetLength());
183}
static bool Processor(SpectrumTransformer &transformer)
const unsigned mStepsPerWindow
bool Process(const WindowProcessor &processor, const WaveChannel &channel, size_t queueLength, sampleCount start, sampleCount len)
Invokes Start(), ProcessSamples(), and Finish()

References TrackSpectrumTransformer::Process().

Here is the call graph for this function:

◆ Processor()

bool SpectralDataManager::Worker::Processor ( SpectrumTransformer transformer)
staticprotected

Definition at line 302 of file SpectralDataManager.cpp.

303{
304 auto &worker = static_cast<Worker &>(transformer);
305 // Compute power spectrum in the newest window
306 {
307 MyWindow &record = worker.NthWindow(0);
308 float *pSpectrum = &record.mSpectrums[0];
309 const double dc = record.mRealFFTs[0];
310 *pSpectrum++ = dc * dc;
311 float *pReal = &record.mRealFFTs[1], *pImag = &record.mImagFFTs[1];
312 for (size_t nn = worker.mSpectrumSize - 2; nn--;) {
313 const double re = *pReal++, im = *pImag++;
314 *pSpectrum++ = re * re + im * im;
315 }
316 const double nyquist = record.mImagFFTs[0];
317 *pSpectrum = nyquist * nyquist;
318 }
319
320 worker.ApplyEffectToSelection();
321 return true;
322}

References SpectralDataManager::Worker::MyWindow::mSpectrums.

◆ ProcessOvertones()

std::vector< int > SpectralDataManager::Worker::ProcessOvertones ( const WaveChannel channel,
long long int  startSC,
int  hopSize,
size_t  winSize,
double  threshold,
int  targetFreqBin 
)

Definition at line 202 of file SpectralDataManager.cpp.

205{
206 mOvertonesThreshold = threshold;
207 mSnapTargetFreqBin = targetFreqBin;
208 mSnapSamplingRate = channel.GetTrack().GetRate();
209
210 startSC = std::max(static_cast<long long>(0), startSC - 2 * hopSize);
211 // The calculated multiple frequency peaks will be stored in mOvertonesTargetFreqBin
213 OvertonesProcessor, channel, 1, startSC, winSize);
214 return move( mOvertonesTargetFreqBin );
215 }
std::vector< int > mOvertonesTargetFreqBin
static bool OvertonesProcessor(SpectrumTransformer &transformer)
WaveTrack & GetTrack()
Definition: WaveTrack.h:1220
double GetRate() const override
Definition: WaveTrack.cpp:1128

References WaveTrack::GetRate(), WaveChannel::GetTrack(), and TrackSpectrumTransformer::Process().

Here is the call graph for this function:

◆ ProcessSnapping()

int SpectralDataManager::Worker::ProcessSnapping ( const WaveChannel channel,
long long int  startSC,
int  hopSize,
size_t  winSize,
double  threshold,
int  targetFreqBin 
)

Definition at line 185 of file SpectralDataManager.cpp.

188{
189 mSnapThreshold = threshold;
190 mSnapTargetFreqBin = targetFreqBin;
191 mSnapSamplingRate = channel.GetTrack().GetRate();
192
193 startSC = std::max(static_cast<long long>(0), startSC - 2 * hopSize);
194 // The calculated frequency peak will be stored in mReturnFreq
196 1, startSC, winSize))
197 return 0;
198
199 return mSnapReturnFreqBin;
200}
static bool SnappingProcessor(SpectrumTransformer &transformer)

References WaveTrack::GetRate(), WaveChannel::GetTrack(), and TrackSpectrumTransformer::Process().

Here is the call graph for this function:

◆ SnappingProcessor()

bool SpectralDataManager::Worker::SnappingProcessor ( SpectrumTransformer transformer)
staticprotected

Definition at line 217 of file SpectralDataManager.cpp.

217 {
218 auto &worker = static_cast<Worker &>(transformer);
219 // Compute power spectrum in the newest window
220 {
221 MyWindow &record = worker.NthWindow(0);
222 float *pSpectrum = &record.mSpectrums[0];
223 const double dc = record.mRealFFTs[0];
224 *pSpectrum++ = dc * dc;
225 float *pReal = &record.mRealFFTs[1], *pImag = &record.mImagFFTs[1];
226 for (size_t nn = worker.mSpectrumSize - 2; nn--;) {
227 const double re = *pReal++, im = *pImag++;
228 *pSpectrum++ = re * re + im * im;
229 }
230 const double nyquist = record.mImagFFTs[0];
231 *pSpectrum = nyquist * nyquist;
232
233 const double &sr = worker.mSnapSamplingRate;
234 const double nyquistRate = sr / 2;
235 const double &threshold = worker.mSnapThreshold;
236 const double &spectrumSize = worker.mSpectrumSize;
237 const int &targetBin = worker.mSnapTargetFreqBin;
238
239 int binBound = spectrumSize * threshold;
240 float maxValue = std::numeric_limits<float>::min();
241
242 // Skip the first and last bin
243 for(int i = -binBound; i < binBound; i++){
244 int idx = std::clamp(targetBin + i, 0, static_cast<int>(spectrumSize - 1));
245 if(record.mSpectrums[idx] > maxValue){
246 maxValue = record.mSpectrums[idx];
247 // Update the return frequency
248 worker.mSnapReturnFreqBin = idx;
249 }
250 }
251 }
252
253 return true;
254}
int min(int a, int b)

References min(), and SpectralDataManager::Worker::MyWindow::mSpectrums.

Here is the call graph for this function:

Member Data Documentation

◆ mOvertonesTargetFreqBin

std::vector<int> SpectralDataManager::Worker::mOvertonesTargetFreqBin
private

Definition at line 88 of file SpectralDataManager.h.

◆ mOvertonesThreshold

double SpectralDataManager::Worker::mOvertonesThreshold
private

Definition at line 87 of file SpectralDataManager.h.

◆ mpSpectralData

std::shared_ptr<SpectralData> SpectralDataManager::Worker::mpSpectralData
private

Definition at line 83 of file SpectralDataManager.h.

◆ mSnapReturnFreqBin

int SpectralDataManager::Worker::mSnapReturnFreqBin { -1 }
private

Definition at line 90 of file SpectralDataManager.h.

◆ mSnapSamplingRate

double SpectralDataManager::Worker::mSnapSamplingRate
private

Definition at line 85 of file SpectralDataManager.h.

◆ mSnapTargetFreqBin

int SpectralDataManager::Worker::mSnapTargetFreqBin
private

Definition at line 89 of file SpectralDataManager.h.

◆ mSnapThreshold

double SpectralDataManager::Worker::mSnapThreshold
private

Definition at line 86 of file SpectralDataManager.h.

◆ mStartHopNum

long long SpectralDataManager::Worker::mStartHopNum { 0 }
private

Definition at line 91 of file SpectralDataManager.h.

◆ mWindowCount

int SpectralDataManager::Worker::mWindowCount { 0 }
private

Definition at line 84 of file SpectralDataManager.h.


The documentation for this class was generated from the following files: