]> git.sesse.net Git - pitch/blobdiff - pitchdetector.cpp
Move the notes array into its own file, and add a separate version for equal temperam...
[pitch] / pitchdetector.cpp
index 71e5875c7b328a31a38ba45540d967c861af316f..a73fb8632579824a1e603f3a01d73c0d1b8e9d05 100644 (file)
@@ -1,4 +1,5 @@
 #include <stdio.h>
+#include <string.h>
 #include <stdlib.h>
 #include <unistd.h>
 #include <fcntl.h>
@@ -38,7 +39,7 @@ PitchDetector::~PitchDetector()
 std::pair<double, double> PitchDetector::detect_pitch(short *buf)
 {
        unsigned buf_len = fft_length / pad_factor / overlap;
-       memmove(in, in + buf_len, (fft_length - buf_len) * sizeof(double));
+       memmove(in, in + buf_len, (fft_length / pad_factor - buf_len) * sizeof(double));
        
        for (unsigned i = 0; i < buf_len; ++i)
                in[i + (fft_length / pad_factor - buf_len)] = double(buf[i]);
@@ -80,6 +81,13 @@ std::pair<double, double> PitchDetector::find_peak(double *in, unsigned num_samp
                        best_peak = in[i];
                        best_bin = i;
                }
+#if 0
+               if (20.0 * log10(in[i] / fft_length) > 0.0) {
+                       printf("PEAK: %+4.2f dB   %5.2f Hz\n",
+                               20.0 * log10(in[i] / fft_length),
+                               bin_to_freq(i, num_samples));
+               }
+#endif
        }
        
        if (best_bin == 0 || best_bin == num_samples / 2) {
@@ -97,10 +105,11 @@ std::pair<double, double> PitchDetector::find_peak(double *in, unsigned num_samp
                20.0 * log10(in[best_bin/4] / fft_length));
 #endif
 
-       // see if we might have hit an overtone (set a limit of 5dB)
-       for (unsigned i = 4; i >= 1; --i) {
+       // see if we might have hit an overtone (set a limit of 10dB)
+       for (unsigned i = 6; i >= 1; --i) {
                if (best_bin != best_bin / i &&
-                   20.0 * log10(in[best_bin] / in[best_bin / i]) < 5.0f) {
+                   20.0 * log10(in[best_bin] / in[best_bin / i]) < 10.0f &&
+                   best_bin / i >= 5) {
 #if 0
                        printf("Overtone of degree %u!\n", i);
 #endif
@@ -244,7 +253,7 @@ std::pair<double, double> PitchDetector::interpolate_peak(double ym1, double y0,
        double c = y0;
        
        double xmax = (ym1 - y1) / (2.0 * (y1 + ym1 - 2.0 * y0));
-       double ymax = 20.0 * (a * xmax * xmax + b * xmax + c) - 90.0;
+       double ymax = 20.0 * (a * xmax * xmax + b * xmax + c) - 70.0;
 
        return std::make_pair(xmax, ymax);
 }