shithub: leaf

Download patch

ref: fdb31244751d90b1a6f869215769ac049da15936
parent: 7c1652ac641228e85209accc16e509f74e249396
author: Matthew Wang <mjw7@princeton.edu>
date: Thu Jul 16 09:05:15 EDT 2020

working bacf pitch detection

--- a/TestPlugin/Source/MyTest.cpp
+++ b/TestPlugin/Source/MyTest.cpp
@@ -35,6 +35,8 @@
 
 tPitchDetector detector;
 
+tPeriodDetection pd;
+
 float gain;
 float freq;
 float dtime;
@@ -44,6 +46,9 @@
 float y = 0.0f;
 float a, b, c, d;
 
+float bufIn[4096];
+float bufOut[4096];
+
 #define MSIZE 500000
 char memory[MSIZE];
 
@@ -55,7 +60,11 @@
     tMBTriangle_init(&btri);
     tMBPulse_init(&bpulse);
     
-    tPitchDetector_init(&detector, 1000.0f, 5000.0f, 0.0f);
+    
+    // lowestFreq, highestFreq, hysteresis (width of hysteresis region around 0.0 for zero crossing detection)
+    tPitchDetector_init(&detector, mtof(48), mtof(84), 0.01f);
+    
+    tPeriodDetection_init(&pd, bufIn, bufOut, 4096, 1024);
 }
 
 inline double getSawFall(double angle) {
@@ -81,10 +90,13 @@
 //    return tMBPulse_tick(&bpulse);
     
     tPitchDetector_tick(&detector, input);
-
+    
     tMBTriangle_setFreq(&btri, tPitchDetector_getFrequency(&detector));
     
-    return input + tMBTriangle_tick(&btri) * 0.25;
+//    float freq = 1.0f/tPeriodDetection_tick(&pd, input) * leaf.sampleRate;
+//    tMBTriangle_setFreq(&btri, freq);
+
+    return tMBTriangle_tick(&btri);// * 0.25;
 }
 
 int firstFrame = 1;
--- a/leaf/Src/leaf-analysis.c
+++ b/leaf/Src/leaf-analysis.c
@@ -1049,7 +1049,7 @@
     _tZeroCrossings* z = *zc = (_tZeroCrossings*) mpool_alloc(sizeof(_tZeroCrossings), m);
     z->mempool = m;
     
-    z->_hysteresis = hysteresis;
+    z->_hysteresis = -hysteresis;
     int bits = CHAR_BIT * sizeof(unsigned int);
     z->_window_size = fmax(2, (windowSize + bits - 1) / bits) * bits;
     
@@ -1091,12 +1091,12 @@
     if (z->_num_edges >= z->_size)
         reset(zc);
     
-    if ((z->_frame == z->_window_size/2) && z->_num_edges == 0)
+    if ((z->_frame == z->_window_size/2) && (z->_num_edges == 0))
         reset(zc);
     
     update_state(zc, s);
     
-    if (++z->_frame >= z->_window_size && !z->_state)
+    if ((++z->_frame >= z->_window_size) && !z->_state)
     {
         // Remove half the size from _frame, so we can continue seamlessly
         z->_frame -= z->_window_size / 2;
@@ -1122,7 +1122,8 @@
 {
     _tZeroCrossings* z = *zc;
     
-    return z->_info[(z->_num_edges - 1) - index];
+    int i = (z->_num_edges - 1) - index;
+    return z->_info[(z->_pos + i) & z->_mask];
 }
 
 int     tZeroCrossings_getNumEdges(tZeroCrossings* const zc)
@@ -1178,16 +1179,15 @@
 {
     _tZeroCrossings* z = *zc;
     
-    int capacity = z->_window_size / 2;
     if (z->_ready)
     {
-        shift(zc, capacity);
+        shift(zc, z->_window_size / 2);
         z->_ready = 0;
         z->_peak = z->_peak_update;
         z->_peak_update = 0.0f;
     }
     
-    if (z->_num_edges >= capacity)
+    if (z->_num_edges >= z->_size)
         reset(zc);
     
     if (s > 0.0f)
@@ -1201,6 +1201,8 @@
             crossing->_after_crossing = s;
             crossing->_peak = s;
             crossing->_leading_edge = (int) z->_frame;
+            crossing->_trailing_edge = INT_MIN;
+            crossing->_width = 0.0f;
             ++z->_num_edges;
             z->_state = 1;
         }