26#include <wx/textfile.h>
105 auto samplesleft = len - WindowSizeInt;
106 auto lastsubthresholdsample = start;
117 for(
auto i = start; samplesleft >= 10;
118 i += (WindowSizeInt - 1) , samplesleft -= (WindowSizeInt - 1)) {
129 lastsubthresholdsample = i;
139 if(samplesleft > 10) {
144 size_t remaining = 2*WindowSizeInt+1;
148 Floats buffer{ remaining };
150 lastsubthresholdsample, remaining);
156 int atrend =
sgn(buffer[1]-buffer[0]);
157 int ztrend =
sgn(buffer[WindowSizeInt+1]-buffer[WindowSizeInt]);
166 erg =
TestEnergy(t, lastsubthresholdsample, WindowSizeInt);
176 wxASSERT(WindowSizeInt < SignalWindowSizeInt);
178 for(i = 0; i + WindowSizeInt < SignalWindowSizeInt; i++) {
181 int testThreshold = 0;
191 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
198 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
205 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
212 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
219 if(tests >= testThreshold)
226 return i + lastsubthresholdsample;
253 auto samplesleft = len - WindowSizeInt;
254 auto lastsubthresholdsample =
end;
264 for(
auto i =
end - WindowSizeInt; samplesleft >= 10;
265 i -= (WindowSizeInt - 1) , samplesleft -= (WindowSizeInt - 1)) {
280 lastsubthresholdsample = i+WindowSizeInt;
290 if(samplesleft > 10) {
294 size_t remaining = 2*WindowSizeInt+1;
298 Floats buffer{ remaining };
300 lastsubthresholdsample - remaining, remaining);
304 int atrend =
sgn(buffer[remaining - 2]-buffer[remaining - 1]);
306 int ztrend =
sgn(buffer[remaining - WindowSizeInt - 2] -
307 buffer[remaining - WindowSizeInt
321 erg =
TestEnergy(t, lastsubthresholdsample, WindowSizeInt);
329 for(i = remaining - 1; i > WindowSizeInt; i--) {
331 int testThreshold = 0;
341 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
347 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
353 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
359 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
364 if(tests >= testThreshold)
371 return lastsubthresholdsample - remaining + i;
396 unsigned int WindowSizeInt = (
unsigned int)(rate *
mWindowSize);
400 auto lastsubthresholdsample = start;
409 for(
auto i = start; samplesleft >= 10;
410 i += (WindowSizeInt - 1) , samplesleft -= (WindowSizeInt - 1)) {
422 lastsubthresholdsample = i;
432 if(samplesleft > 10) {
437 size_t remaining = 2*WindowSizeInt+1;
441 Floats buffer{ remaining };
443 lastsubthresholdsample, remaining);
447 int atrend =
sgn(buffer[1]-buffer[0]);
448 int ztrend =
sgn(buffer[WindowSizeInt+1]-buffer[WindowSizeInt]);
457 erg =
TestEnergy(t, lastsubthresholdsample, WindowSizeInt);
465 for(i = 0; i < SilentWindowSizeInt - WindowSizeInt; i++) {
467 int testThreshold = 0;
477 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
483 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
489 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
495 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
500 if(tests < testThreshold)
507 return i + lastsubthresholdsample;
532 unsigned int WindowSizeInt = (
unsigned int)(rate *
mWindowSize);
535 auto samplesleft = len - WindowSizeInt;
536 auto lastsubthresholdsample =
end;
545 for(
auto i =
end - WindowSizeInt; samplesleft >= 10;
546 i -= (WindowSizeInt - 1), samplesleft -= (WindowSizeInt -1 )) {
559 lastsubthresholdsample = i+WindowSizeInt;
570 if(samplesleft > 10) {
574 const size_t remaining = 2*WindowSizeInt+1;
578 Floats buffer{ remaining };
580 lastsubthresholdsample - remaining, remaining);
584 int atrend =
sgn(buffer[remaining - 2] - buffer[remaining - 1]);
586 sgn(buffer[remaining - WindowSizeInt - 2] -
587 buffer[remaining - WindowSizeInt - 2]);
594 erg =
TestEnergy(t, lastsubthresholdsample, WindowSizeInt);
602 for(i = remaining - 1; i > WindowSizeInt; i--) {
605 int testThreshold = 0;
615 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
621 TestSignChangesUpdate(sc,WindowSizeInt,buffer[i],buffer[i+1],buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
627 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
633 TestDirectionChangesUpdate(dc,WindowSizeInt,atrend,buffer[i],buffer[i+1],ztrend,buffer[i+WindowSizeInt],buffer[i+WindowSizeInt+1]);
640 if(tests < testThreshold)
647 return lastsubthresholdsample - remaining + i;
720 return (tests >= testThreshold);
749 double sumerg, sumerg2;
750 double sumsc, sumsc2;
751 double sumdc, sumdc2;
756 unsigned int WindowSizeInt = (
unsigned int)(rate *
mWindowSize);
783 auto samplesleft = len - WindowSizeInt;
786 for(
auto i = start; samplesleft >= 10;
787 i += (WindowSizeInt - 1), samplesleft -= (WindowSizeInt -1) ) {
796 sumerg +=(double)erg;
797 sumerg2 += pow((
double)erg,2);
801 sumsc2 += pow((
double)sc,2);
806 sumdc2 += pow((
double)dc,2);
818 auto text =
XO(
"Calibration Results\n");
821 XO(
"Energy -- mean: %1.4f sd: (%1.4f)\n")
824 XO(
"Sign Changes -- mean: %1.4f sd: (%1.4f)\n")
827 XO(
"Direction Changes -- mean: %1.4f sd: (%1.4f)\n")
832 XO(
"Calibration Complete"),
833 wxOK | wxICON_INFORMATION,
843 bool dcLow,
bool dcHigh)
860 auto originalLen = len;
863 Floats buffer{ blockSize };
873 for(
decltype(block) i = 0; i< block; i++)
875 sum += buffer[i]*buffer[i];
890 prevErg = prevErg + (double)(fabs(
add) - fabs(drop))/len;
901 auto originalLen = len;
904 unsigned long signchanges = 1;
907 Floats buffer{ blockSize };
915 if (len == originalLen)
918 currentsign =
sgn(buffer[0]);
923 for(
decltype(block) i = 0; i< block; i++)
925 if(
sgn(buffer[i]) != currentsign)
927 currentsign =
sgn(buffer[i]);
935 return (
double)signchanges / originalLen.
as_double();
945 if(
sgn(a1)!=
sgn(a2)) currentsignchanges -= 1.0/len;
946 if(
sgn(z1)!=
sgn(z2)) currentsignchanges += 1.0/len;
957 auto originalLen = len;
960 unsigned long directionchanges = 1;
961 float lastval=float(0);
964 Floats buffer{ blockSize };
972 if (len == originalLen) {
980 for(
decltype(block) i = 0; i< block; i++){
982 if(
sgn(buffer[i]-lastval) != lastdirection) {
984 lastdirection =
sgn(buffer[i] - lastval);
992 return (
double)directionchanges/originalLen.
as_double();
1001 int & atrend,
const float & a1,
const float & a2,
1002 int & ztrend,
const float & z1,
const float & z2)
1005 if(
sgn(a2 - a1)!= atrend ) {
1007 currentdirectionchanges -= 1.0/len;
1008 atrend =
sgn(a2-a1);
1010 if(
sgn(z2 - z1)!= ztrend){
1012 currentdirectionchanges += 1.0/len;
1013 ztrend =
sgn(z2-z1);
int AudacityMessageBox(const TranslatableString &message, const TranslatableString &caption, long style, wxWindow *parent, int x, int y)
size_t limitSampleBufferSize(size_t bufferSize, sampleCount limit)
Wrap wxMessageDialog so that caption IS translatable.
double TestDirectionChanges(const WaveChannel &t, sampleCount start, sampleCount len)
double mThresholdAdjustment
void TestDirectionChangesUpdate(double ¤tdirectionchanges, int length, int &atrend, const float &a1, const float &a2, int &ztrend, const float &z1, const float &z2)
sampleCount OffForward(const WaveChannel &t, sampleCount start, sampleCount len)
sampleCount OnBackward(const WaveChannel &t, sampleCount start, sampleCount len)
double mThresholdDirectionChangesUpper
void AdjustThreshold(double t)
sampleCount OnForward(const WaveChannel &t, sampleCount start, sampleCount len)
double mThresholdDirectionChangesLower
bool AboveThreshold(const WaveChannel &t, sampleCount start, sampleCount len)
bool mUseDirectionChangesLow
sampleCount OffBackward(const WaveChannel &t, sampleCount start, sampleCount len)
void TestEnergyUpdate(double &prevErg, int length, const float &drop, const float &add)
double mThresholdSignChangesLower
bool mUseDirectionChangesHigh
double TestEnergy(const WaveChannel &t, sampleCount start, sampleCount len)
double TestSignChanges(const WaveChannel &t, sampleCount start, sampleCount len)
void CalibrateNoise(const WaveChannel &t, sampleCount start, sampleCount len)
void SetKeyType(bool erg, bool scLow, bool scHigh, bool dcLow, bool dcHigh)
void TestSignChangesUpdate(double ¤tsignchanges, int length, const float &a1, const float &a2, const float &z1, const float &z2)
double mThresholdSignChangesUpper
double mDirectionChangesSD
double mDirectionChangesMean
double GetRate() const override
bool GetFloats(float *buffer, sampleCount start, size_t len, fillFormat fill=FillFormat::fillZero, bool mayThrow=true, sampleCount *pNumWithinClips=nullptr) const
"narrow" overload fetches from the unique channel
size_t GetBestBlockSize(sampleCount t) const
A hint for sizing of well aligned fetches.
size_t GetMaxBlockSize() const
Positions or offsets within audio files need a wide type.
const char * end(const char *str) noexcept
__finl float_x4 __vecc sqrt(const float_x4 &a)
void add(const T *src1, const T *src2, T *dst, int32_t n)