changeset 12:cb88b9954eec track

Start an alternative idea
author Chris Cannam
date Thu, 28 Jun 2012 12:17:18 +0100
parents 0c95dc49163a
children 9fa97de8692a 213d80320d4b
files CepstrumPitchTracker.cpp CepstrumPitchTracker.h
diffstat 2 files changed, 111 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/CepstrumPitchTracker.cpp	Tue Jun 26 16:06:00 2012 +0100
+++ b/CepstrumPitchTracker.cpp	Thu Jun 28 12:17:18 2012 +0100
@@ -30,6 +30,79 @@
 #include <complex>
 
 using std::string;
+using std::vector;
+
+CepstrumPitchTracker::Hypothesis::Hypothesis(Estimate s)
+{
+    m_state = Provisional;
+    m_pending.push_back(s);
+    m_age = 0;
+}
+
+bool
+CepstrumPitchTracker::Hypothesis::isWithinTolerance(Estimate s)
+{
+    if (m_pending.empty()) {
+        return true;
+    }
+    Estimate last = m_pending[m_pending.size()-1];
+    double r = s.freq / last.freq;
+    int cents = lrint(1200.0 * (log(r) / log(2.0)));
+    return (cents > -200 && cents < 200);
+}
+
+bool 
+CepstrumPitchTracker::Hypothesis::isSatisfied()
+{
+    return (m_pending.size() > 2);
+}
+
+bool
+CepstrumPitchTracker::Hypothesis::test(Estimate s)
+{
+    if (m_state == Rejected || m_state == Expired) {
+        return false;
+    }
+
+    if (++m_age > 3) {
+        if (m_state == Satisfied) {
+            m_state = Expired;
+        } else {
+            m_state = Rejected;
+        }
+        return false;
+    }
+
+    if (isWithinTolerance(s)) {
+        m_pending.push_back(s);
+        if (m_state == Provisional) {
+            if (isSatisfied()) {
+                m_state == Satisfied;
+            }
+        }
+        m_age = 0;
+        return true;
+    }
+    
+    return false;
+}
+
+CepstrumPitchTracker::Hypothesis::State
+CepstrumPitchTracker::Hypothesis::getState()
+{
+    return m_state;
+}
+
+CepstrumPitchTracker::Hypothesis::Estimates
+CepstrumPitchTracker::Hypothesis::getAcceptedEstimates()
+{
+    if (m_state == Satisfied || m_state == Expired) {
+        return m_pending;
+    } else {
+        return Estimates();
+    }
+}
+
 
 CepstrumPitchTracker::CepstrumPitchTracker(float inputSampleRate) :
     Plugin(inputSampleRate),
@@ -43,6 +116,7 @@
     m_binFrom(0),
     m_binTo(0),
     m_bins(0),
+    m_accepted(0),
     m_history(0),
     m_prevpeak(0),
     m_prevprop(0)
--- a/CepstrumPitchTracker.h	Tue Jun 26 16:06:00 2012 +0100
+++ b/CepstrumPitchTracker.h	Thu Jun 28 12:17:18 2012 +0100
@@ -75,6 +75,43 @@
     int m_binTo;
     int m_bins; // count of "interesting" bins, those returned in m_cepOutput
 
+    class Hypothesis {
+
+    public:
+        struct Estimate {
+            double freq;
+            Vamp::RealTime time;
+        };
+        typedef std::vector<Estimate> Estimates;
+        
+        Hypothesis(Estimate s);
+        ~Hypothesis();
+
+        enum State {
+            Provisional,
+            Satisfied,
+            Rejected,
+            Expired
+        };
+
+        bool test(Estimate);
+        State getState();
+
+        Estimates getAcceptedEstimates();
+
+    private:
+        bool isWithinTolerance(Estimate);
+        bool isSatisfied();
+
+        State m_state;
+        Estimates m_pending;
+        int m_age;
+    };
+
+    typedef std::vector<Hypothesis> Hypotheses;
+    Hypotheses m_possible;
+    Hypothesis *m_accepted;
+
     double **m_history;
     
     int m_prevpeak;