# HG changeset patch # User Chris Cannam # Date 1385639199 0 # Node ID a25abb7a21c0136d2982eefdeaae46f3ec507875 # Parent 99fb93c720532553410672aca56edfc2448778e4 Further tidying, compensate for latency in Vamp plugin diff -r 99fb93c72053 -r a25abb7a21c0 cpp-qm-dsp/ConstantQ.cpp --- a/cpp-qm-dsp/ConstantQ.cpp Thu Nov 28 11:26:53 2013 +0000 +++ b/cpp-qm-dsp/ConstantQ.cpp Thu Nov 28 11:46:39 2013 +0000 @@ -114,7 +114,10 @@ m_bigBlockSize = m_p.fftSize * pow(2, m_octaves) / 2; // Now add in the extra padding and compensate for hops that must - // be dropped in order to align the atom centres across octaves + // be dropped in order to align the atom centres across + // octaves. Again this is a bit trickier because we are doing it + // at input rather than output and so must work in per-octave + // sample rates rather than output blocks int emptyHops = m_p.firstCentre / m_p.atomSpacing; diff -r 99fb93c72053 -r a25abb7a21c0 cpp-qm-dsp/ConstantQ.h --- a/cpp-qm-dsp/ConstantQ.h Thu Nov 28 11:26:53 2013 +0000 +++ b/cpp-qm-dsp/ConstantQ.h Thu Nov 28 11:46:39 2013 +0000 @@ -25,6 +25,7 @@ int getOctaves() const { return m_octaves; } int getTotalBins() const { return m_octaves * m_binsPerOctave; } int getColumnHop() const { return m_p.fftHop / m_p.atomsPerFrame; } + int getLatency() const { return m_totalLatency; } // a multiple of column hop std::vector > process(const std::vector &); std::vector > getRemainingBlocks(); diff -r 99fb93c72053 -r a25abb7a21c0 cpp-qm-dsp/test.cpp --- a/cpp-qm-dsp/test.cpp Thu Nov 28 11:26:53 2013 +0000 +++ b/cpp-qm-dsp/test.cpp Thu Nov 28 11:46:39 2013 +0000 @@ -16,9 +16,9 @@ vector in; for (int i = 0; i < 64; ++i) { - if (i == 0) in.push_back(1); - else in.push_back(0); -// in.push_back(sin(i * M_PI / 2.0)); +// if (i == 0) in.push_back(1); +// else in.push_back(0); + in.push_back(sin(i * M_PI / 2.0)); } ConstantQ k(8, 1, 4, 4); diff -r 99fb93c72053 -r a25abb7a21c0 vamp/CQVamp.cpp --- a/vamp/CQVamp.cpp Thu Nov 28 11:26:53 2013 +0000 +++ b/vamp/CQVamp.cpp Thu Nov 28 11:46:39 2013 +0000 @@ -14,7 +14,9 @@ m_cq(0), m_maxFrequency(inputSampleRate/2), m_minFrequency(46), - m_bpo(24) + m_bpo(24), + m_haveStartTime(false), + m_columnCount(0) { } @@ -160,6 +162,8 @@ (m_inputSampleRate, m_minFrequency, m_maxFrequency, m_bpo); } m_prevFeature.clear(); + m_haveStartTime = false; + m_columnCount = 0; } size_t @@ -197,7 +201,7 @@ CQVamp::FeatureSet CQVamp::process(const float *const *inputBuffers, - Vamp::RealTime /* timestamp */) + Vamp::RealTime timestamp) { if (!m_cq) { cerr << "ERROR: CQVamp::process: " @@ -206,6 +210,11 @@ return FeatureSet(); } + if (!m_haveStartTime) { + m_startTime = timestamp; + m_haveStartTime = true; + } + vector data; for (int i = 0; i < m_blockSize; ++i) data.push_back(inputBuffers[0][i]); @@ -223,7 +232,6 @@ CQVamp::FeatureSet CQVamp::convertToFeatures(const vector > &cqout) { - FeatureSet returnFeatures; for (int i = 0; i < (int)cqout.size(); ++i) { @@ -242,10 +250,20 @@ m_prevFeature = column; Feature feature; - feature.hasTimestamp = false; + feature.hasTimestamp = true; + feature.timestamp = m_startTime + Vamp::RealTime::frame2RealTime + (m_columnCount * m_cq->getColumnHop() - m_cq->getLatency(), + m_inputSampleRate); feature.values = column; feature.label = ""; - returnFeatures[0].push_back(feature); + + cerr << "timestamp = " << feature.timestamp << " (latency = " << m_cq->getLatency() << ", sample rate " << m_inputSampleRate << ")" << endl; + + if (feature.timestamp >= m_startTime) { + returnFeatures[0].push_back(feature); + } + + ++m_columnCount; } return returnFeatures; diff -r 99fb93c72053 -r a25abb7a21c0 vamp/CQVamp.h --- a/vamp/CQVamp.h Thu Nov 28 11:26:53 2013 +0000 +++ b/vamp/CQVamp.h Thu Nov 28 11:46:39 2013 +0000 @@ -47,6 +47,10 @@ int m_stepSize; int m_blockSize; + Vamp::RealTime m_startTime; + bool m_haveStartTime; + int m_columnCount; + std::vector m_prevFeature; FeatureSet convertToFeatures(const std::vector > &); };