Audacity 3.2.0
Public Member Functions | Public Attributes | List of all members
EffectDtmf::Instance Struct Reference

Temporary state of the computation. More...

Inheritance diagram for EffectDtmf::Instance:
[legend]
Collaboration diagram for EffectDtmf::Instance:
[legend]

Public Member Functions

 Instance (const PerTrackEffect &effect, double t0)
 
bool ProcessInitialize (EffectSettings &settings, double sampleRate, ChannelNames chanMap) override
 
size_t ProcessBlock (EffectSettings &settings, const float *const *inBlock, float *const *outBlock, size_t blockLen) override
 Called for destructive effect computation. More...
 
unsigned GetAudioInCount () const override
 How many input buffers to allocate at once. More...
 
unsigned GetAudioOutCount () const override
 How many output buffers to allocate at once. More...
 
- Public Member Functions inherited from PerTrackEffect::Instance
 Instance (const PerTrackEffect &processor)
 
 ~Instance () override
 
bool Process (EffectSettings &settings) final
 Uses the other virtual functions of this class. More...
 
bool ProcessInitialize (EffectSettings &settings, double sampleRate, ChannelNames chanMap) override
 
bool ProcessFinalize () noexcept override
 
- Public Member Functions inherited from EffectInstanceEx
virtual bool Init ()
 Call once to set up state for whole list of tracks to be processed. More...
 
virtual bool Process (EffectSettings &settings)=0
 Actually do the effect here. More...
 
 ~EffectInstanceEx () override
 
- Public Member Functions inherited from EffectInstance
virtual ~EffectInstance ()
 
virtual size_t GetBlockSize () const =0
 
virtual size_t SetBlockSize (size_t maxBlockSize)=0
 
virtual unsigned GetAudioInCount () const =0
 How many input buffers to allocate at once. More...
 
virtual unsigned GetAudioOutCount () const =0
 How many output buffers to allocate at once. More...
 
virtual bool RealtimeInitialize (EffectSettings &settings, double sampleRate)
 
virtual bool RealtimeAddProcessor (EffectSettings &settings, EffectOutputs *pOutputs, unsigned numChannels, float sampleRate)
 
virtual bool RealtimeSuspend ()
 
virtual bool RealtimeResume ()
 
virtual std::unique_ptr< MessageMakeMessage () const
 Called on the main thread, in which the result may be cloned. More...
 
virtual bool UsesMessages () const noexcept
 
virtual bool RealtimeProcessStart (MessagePackage &package)
 settings are possibly changed, since last call, by an asynchronous dialog More...
 
virtual size_t RealtimeProcess (size_t group, EffectSettings &settings, const float *const *inBuf, float *const *outBuf, size_t numSamples)
 
virtual bool RealtimeProcessEnd (EffectSettings &settings) noexcept
 settings can be updated to let a dialog change appearance at idle More...
 
virtual bool RealtimeFinalize (EffectSettings &settings) noexcept
 
virtual size_t GetTailSize () const
 
virtual SampleCount GetLatency (const EffectSettings &settings, double sampleRate) const
 
virtual bool NeedsDither () const
 
virtual bool ProcessInitialize (EffectSettings &settings, double sampleRate, ChannelNames chanMap)=0
 
virtual bool ProcessFinalize () noexcept=0
 
virtual size_t ProcessBlock (EffectSettings &settings, const float *const *inBlock, float *const *outBlock, size_t blockLen)=0
 Called for destructive effect computation. More...
 
- Public Member Functions inherited from EffectInstanceWithBlockSize
 ~EffectInstanceWithBlockSize () override
 
size_t GetBlockSize () const override
 
size_t SetBlockSize (size_t maxBlockSize) override
 

Public Attributes

const double mT0
 
double mSampleRate {}
 
sampleCount numSamplesSequence
 
sampleCount numSamplesTone
 
sampleCount numSamplesSilence
 
sampleCount diff
 
sampleCount numRemaining
 
sampleCount curTonePos
 
bool isTone
 
int curSeqPos
 

Additional Inherited Members

- Public Types inherited from EffectInstance
using Message = EffectSettingsAccess::Message
 
using SampleCount = uint64_t
 
- Protected Attributes inherited from PerTrackEffect::Instance
const PerTrackEffectmProcessor
 
- Protected Attributes inherited from EffectInstanceWithBlockSize
size_t mBlockSize { 0 }
 

Detailed Description

Temporary state of the computation.

Definition at line 123 of file DtmfGen.cpp.

Constructor & Destructor Documentation

◆ Instance()

EffectDtmf::Instance::Instance ( const PerTrackEffect effect,
double  t0 
)
inline

Definition at line 127 of file DtmfGen.cpp.

128 : PerTrackEffect::Instance{ effect }
129 , mT0{ t0 }
130 {}
const double mT0
Definition: DtmfGen.cpp:148

Member Function Documentation

◆ GetAudioInCount()

unsigned EffectDtmf::Instance::GetAudioInCount ( ) const
inlineoverridevirtual

How many input buffers to allocate at once.

If the instance processes channels independently, this can return 1 The result is not necessarily well defined before RealtimeInitialize

Implements EffectInstance.

Definition at line 138 of file DtmfGen.cpp.

139 {
140 return 0;
141 }

◆ GetAudioOutCount()

unsigned EffectDtmf::Instance::GetAudioOutCount ( ) const
inlineoverridevirtual

How many output buffers to allocate at once.

The result is not necessarily well defined before RealtimeInitialize

Implements EffectInstance.

Definition at line 143 of file DtmfGen.cpp.

144 {
145 return 1;
146 }

◆ ProcessBlock()

size_t EffectDtmf::Instance::ProcessBlock ( EffectSettings settings,
const float *const *  inBlock,
float *const *  outBlock,
size_t  blockLen 
)
overridevirtual

Called for destructive effect computation.

Implements EffectInstance.

Definition at line 219 of file DtmfGen.cpp.

221{
222 auto &dtmfSettings = GetSettings(settings);
223 float *buffer = outbuf[0];
224 decltype(size) processed = 0;
225
226 // for the whole dtmf sequence, we will be generating either tone or silence
227 // according to a bool value, and this might be done in small chunks of size
228 // 'block', as a single tone might sometimes be larger than the block
229 // tone and silence generally have different duration, thus two generation blocks
230 //
231 // Note: to overcome a 'clicking' noise introduced by the abrupt transition from/to
232 // silence, I added a fade in/out of 1/250th of a second (4ms). This can still be
233 // tweaked but gives excellent results at 44.1kHz: I haven't tried other freqs.
234 // A problem might be if the tone duration is very short (<10ms)... (?)
235 //
236 // One more problem is to deal with the approximations done when calculating the duration
237 // of both tone and silence: in some cases the final sum might not be same as the initial
238 // duration. So, to overcome this, we had a redistribution block up, and now we will spread
239 // the remaining samples in every bin in order to achieve the full duration: test case was
240 // to generate an 11 tone DTMF sequence, in 4 seconds, and with DutyCycle=75%: after generation
241 // you ended up with 3.999s or in other units: 3 seconds and 44097 samples.
242 //
243 while (size)
244 {
245 if (numRemaining == 0)
246 {
247 isTone = !isTone;
248
249 if (isTone)
250 {
251 curSeqPos++;
253 curTonePos = 0;
254 }
255 else
256 {
258 }
259
260 // the statement takes care of extracting one sample from the diff bin and
261 // adding it into the current block until depletion
262 numRemaining += (diff-- > 0 ? 1 : 0);
263 }
264
265 const auto len = limitSampleBufferSize( size, numRemaining );
266
267 if (isTone)
268 {
269 // generate the tone and append
270 assert(curSeqPos < dtmfSettings.dtmfNTones) ;
271 MakeDtmfTone(buffer, len, mSampleRate,
272 dtmfSettings.dtmfSequence[curSeqPos], curTonePos, numSamplesTone,
273 dtmfSettings.dtmfAmplitude);
274 curTonePos += len;
275 }
276 else
277 {
278 memset(buffer, 0, sizeof(float) * len);
279 }
280
281 numRemaining -= len;
282
283 buffer += len;
284 size -= len;
285 processed += len;
286 }
287
288 return processed;
289}
size_t limitSampleBufferSize(size_t bufferSize, sampleCount limit)
Definition: SampleCount.cpp:22
static Settings & settings()
Definition: TrackInfo.cpp:69
static bool MakeDtmfTone(float *buffer, size_t len, float fs, wxChar tone, sampleCount last, sampleCount total, float amplitude)
Definition: DtmfGen.cpp:518
static DtmfSettings & GetSettings(EffectSettings &settings)
Assume settings originated from MakeSettings() and copies thereof.
Definition: Effect.h:166
sampleCount numSamplesTone
Definition: DtmfGen.cpp:152
sampleCount curTonePos
Definition: DtmfGen.cpp:156
sampleCount diff
Definition: DtmfGen.cpp:154
sampleCount numSamplesSilence
Definition: DtmfGen.cpp:153
sampleCount numRemaining
Definition: DtmfGen.cpp:155

References EffectWithSettings< DtmfSettings, StatelessPerTrackEffect >::GetSettings(), limitSampleBufferSize(), EffectDtmf::MakeDtmfTone(), settings(), and size.

Here is the call graph for this function:

◆ ProcessInitialize()

bool EffectDtmf::Instance::ProcessInitialize ( EffectSettings settings,
double  sampleRate,
ChannelNames  chanMap 
)
overridevirtual

Called at start of destructive processing, for each (mono/stereo) track Default implementation does nothing, returns true

Parameters
chanMapnull or array terminated with ChannelNameEOL. Do not retain the pointer
Postcondition
GetAudioInCount() and GetAudioOutCount() are well defined

Implements EffectInstance.

Definition at line 161 of file DtmfGen.cpp.

163{
165
166 auto &dtmfSettings = GetSettings(settings);
167 if (dtmfSettings.dtmfNTones == 0) { // Bail if no DTFM sequence.
168 // TODO: don't use mProcessor for this
170 XO("DTMF sequence empty.\nCheck ALL settings for this effect."),
171 wxICON_ERROR );
172
173 return false;
174 }
175
176 double duration = settings.extra.GetDuration();
177
178 // all dtmf sequence durations in samples from seconds
179 // MJS: Note that mDuration is in seconds but will have been quantised to the units of the TTC.
180 // If this was 'samples' and the project rate was lower than the track rate,
181 // extra samples may get created as mDuration may now be > mT1 - mT0;
182 // However we are making our best efforts at creating what was asked for.
183
184 auto nT0 = (sampleCount)floor(mT0 * mSampleRate + 0.5);
185 auto nT1 = (sampleCount)floor((mT0 + duration) * mSampleRate + 0.5);
186 numSamplesSequence = nT1 - nT0; // needs to be exact number of samples selected
187
188 //make under-estimates if anything, and then redistribute the few remaining samples
189 numSamplesTone = sampleCount( floor(dtmfSettings.dtmfTone * mSampleRate) );
190 numSamplesSilence = sampleCount( floor(dtmfSettings.dtmfSilence * mSampleRate) );
191
192 // recalculate the sum, and spread the difference - due to approximations.
193 // Since diff should be in the order of "some" samples, a division (resulting in zero)
194 // is not sufficient, so we add the additional remaining samples in each tone/silence block,
195 // at least until available.
196 diff = numSamplesSequence - (dtmfSettings.dtmfNTones * numSamplesTone)
197 - (dtmfSettings.dtmfNTones - 1) * numSamplesSilence;
198 while (diff > 2 * dtmfSettings.dtmfNTones - 1) { // more than one per thingToBeGenerated
199 // in this case, both numSamplesTone and numSamplesSilence would change, so it makes sense
200 // to recalculate diff here, otherwise just keep the value we already have
201
202 // should always be the case that dtmfNTones>1, as if 0, we don't even start processing,
203 // and with 1 there is no difference to spread (no silence slot)...
204 wxASSERT(dtmfSettings.dtmfNTones > 1);
205 numSamplesTone += (diff / (dtmfSettings.dtmfNTones));
206 numSamplesSilence += (diff / (dtmfSettings.dtmfNTones - 1));
207 diff = numSamplesSequence - (dtmfSettings.dtmfNTones * numSamplesTone)
208 - (dtmfSettings.dtmfNTones - 1) * numSamplesSilence;
209 }
210 wxASSERT(diff >= 0); // should never be negative
211
212 curSeqPos = -1; // pointer to string in dtmfSequence
213 isTone = false;
214 numRemaining = 0;
215
216 return true;
217}
XO("Cut/Copy/Paste")
static int DoMessageBox(const EffectPlugin &plugin, const TranslatableString &message, long style=DefaultMessageBoxStyle, const TranslatableString &titleStr={})
const PerTrackEffect & mProcessor
Positions or offsets within audio files need a wide type.
Definition: SampleCount.h:19
sampleCount numSamplesSequence
Definition: DtmfGen.cpp:151

References curSeqPos, diff, EffectUIServices::DoMessageBox(), EffectWithSettings< DtmfSettings, StatelessPerTrackEffect >::GetSettings(), isTone, PerTrackEffect::Instance::mProcessor, mSampleRate, mT0, numRemaining, numSamplesSequence, numSamplesSilence, numSamplesTone, anonymous_namespace{ClipSegmentTest.cpp}::sampleRate, settings(), and XO().

Here is the call graph for this function:

Member Data Documentation

◆ curSeqPos

int EffectDtmf::Instance::curSeqPos

Definition at line 158 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ curTonePos

sampleCount EffectDtmf::Instance::curTonePos

Definition at line 156 of file DtmfGen.cpp.

◆ diff

sampleCount EffectDtmf::Instance::diff

Definition at line 154 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ isTone

bool EffectDtmf::Instance::isTone

Definition at line 157 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ mSampleRate

double EffectDtmf::Instance::mSampleRate {}

Definition at line 149 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ mT0

const double EffectDtmf::Instance::mT0

Definition at line 148 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ numRemaining

sampleCount EffectDtmf::Instance::numRemaining

Definition at line 155 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ numSamplesSequence

sampleCount EffectDtmf::Instance::numSamplesSequence

Definition at line 151 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ numSamplesSilence

sampleCount EffectDtmf::Instance::numSamplesSilence

Definition at line 153 of file DtmfGen.cpp.

Referenced by ProcessInitialize().

◆ numSamplesTone

sampleCount EffectDtmf::Instance::numSamplesTone

Definition at line 152 of file DtmfGen.cpp.

Referenced by ProcessInitialize().


The documentation for this struct was generated from the following file: