From 3340c471e8d35e501395d245a20cee10f3beddf6 Mon Sep 17 00:00:00 2001 From: Jan Holthuis Date: Tue, 17 Aug 2021 20:45:56 +0200 Subject: [PATCH] LoopingControlTest: Use mixxx::audio::FramePos consistently --- src/test/looping_control_test.cpp | 453 ++++++++++++++++-------------- 1 file changed, 235 insertions(+), 218 deletions(-) diff --git a/src/test/looping_control_test.cpp b/src/test/looping_control_test.cpp index e2a72aeabbe..f955e7d90fb 100644 --- a/src/test/looping_control_test.cpp +++ b/src/test/looping_control_test.cpp @@ -11,16 +11,16 @@ #include "test/mockedenginebackendtest.h" #include "util/memory.h" +namespace { + // Due to rounding errors loop positions should be compared with EXPECT_NEAR instead of EXPECT_EQ. // NOTE(uklotzde, 2017-12-10): The rounding errors currently only appeared with GCC 7.2.1. constexpr double kLoopPositionMaxAbsError = 0.000000001; -class LoopingControlTest : public MockedEngineBackendTest { - public: - LoopingControlTest() - : kTrackLengthSamples(300000000) { - } +constexpr auto kTrackEndPosition = mixxx::audio::FramePos{150000000}; +} // namespace +class LoopingControlTest : public MockedEngineBackendTest { protected: void SetUp() override { MockedEngineBackendTest::SetUp(); @@ -32,7 +32,7 @@ class LoopingControlTest : public MockedEngineBackendTest { m_pClosestBeat = std::make_unique(m_sGroup1, "beat_closest"); m_pClosestBeat->set(-1); m_pTrackSamples = std::make_unique(m_sGroup1, "track_samples"); - m_pTrackSamples->set(kTrackLengthSamples); + m_pTrackSamples->set(kTrackEndPosition.toEngineSamplePos()); m_pButtonLoopIn = std::make_unique(m_sGroup1, "loop_in"); m_pButtonLoopOut = std::make_unique(m_sGroup1, "loop_out"); m_pButtonLoopExit = std::make_unique(m_sGroup1, "loop_exit"); @@ -73,13 +73,11 @@ class LoopingControlTest : public MockedEngineBackendTest { return m_pLoopEnabled->get() > 0.0; } - void seekToSampleAndProcess(double samplePosition) { - const auto position = mixxx::audio::FramePos::fromEngineSamplePos(samplePosition); + void setCurrentPosition(mixxx::audio::FramePos position) { m_pChannel1->getEngineBuffer()->queueNewPlaypos(position, EngineBuffer::SEEK_STANDARD); ProcessBuffer(); } - const int kTrackLengthSamples; std::unique_ptr m_pNextBeat; std::unique_ptr m_pClosestBeat; std::unique_ptr m_pQuantizeEnabled; @@ -117,173 +115,174 @@ class LoopingControlTest : public MockedEngineBackendTest { }; TEST_F(LoopingControlTest, LoopSet) { - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(100); - seekToSampleAndProcess(50); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_FALSE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); } -TEST_F(LoopingControlTest, LoopSetOddSamples) { - m_pLoopStartPoint->set(1); - m_pLoopEndPoint->set(101.5); - seekToSampleAndProcess(50); - EXPECT_EQ(1, m_pLoopStartPoint->get()); - EXPECT_EQ(101.5, m_pLoopEndPoint->get()); +TEST_F(LoopingControlTest, LoopSetFractionalFrames) { + m_pLoopStartPoint->set(mixxx::audio::FramePos{0.5}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{50.75}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{25}); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{0.5}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{50.75}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopInSetInsideLoopContinues) { - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(100); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); - m_pLoopStartPoint->set(10); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); + m_pLoopStartPoint->set(mixxx::audio::FramePos{10}.toEngineSamplePos()); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(10, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{10}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopInSetAfterLoopOutStops) { - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(100); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); - m_pLoopStartPoint->set(110); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); + m_pLoopStartPoint->set(mixxx::audio::FramePos{110}.toEngineSamplePos()); EXPECT_FALSE(isLoopEnabled()); - EXPECT_EQ(110, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{110}, m_pLoopStartPoint); EXPECT_EQ(-1, m_pLoopEndPoint->get()); } TEST_F(LoopingControlTest, LoopOutSetInsideLoopContinues) { - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(100); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); - m_pLoopEndPoint->set(80); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); + m_pLoopEndPoint->set(mixxx::audio::FramePos{80}.toEngineSamplePos()); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(80, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{80}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopOutSetBeforeLoopInIgnored) { - m_pLoopStartPoint->set(10); - m_pLoopEndPoint->set(100); + m_pLoopStartPoint->set(mixxx::audio::FramePos{10}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(10, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); - m_pLoopEndPoint->set(0); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{10}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); + m_pLoopEndPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(10, m_pLoopStartPoint->get()); - EXPECT_EQ(100, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{10}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{100}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopInButton_QuantizeDisabled) { m_pQuantizeEnabled->set(0); m_pClosestBeat->set(100); m_pNextBeat->set(100); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pButtonLoopIn->set(1); m_pButtonLoopIn->set(0); ProcessBuffer(); - EXPECT_EQ(50, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{50}, m_pLoopStartPoint); } TEST_F(LoopingControlTest, LoopInButton_QuantizeEnabledNoBeats) { m_pQuantizeEnabled->set(1); m_pClosestBeat->set(-1); m_pNextBeat->set(-1); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pButtonLoopIn->set(1); m_pButtonLoopIn->set(0); - EXPECT_EQ(50, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{50}, m_pLoopStartPoint); } TEST_F(LoopingControlTest, LoopInButton_AdjustLoopInPointOutsideLoop) { - m_pLoopStartPoint->set(1000); - m_pLoopEndPoint->set(2000); + m_pLoopStartPoint->set(mixxx::audio::FramePos{1000}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); m_pButtonLoopIn->set(1); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pButtonLoopIn->set(0); - EXPECT_EQ(50, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{50}, m_pLoopStartPoint); } TEST_F(LoopingControlTest, LoopInButton_AdjustLoopInPointInsideLoop) { - m_pLoopStartPoint->set(1000); - m_pLoopEndPoint->set(2000); + m_pLoopStartPoint->set(mixxx::audio::FramePos{1000}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); m_pButtonLoopIn->set(1); - seekToSampleAndProcess(1500); + setCurrentPosition(mixxx::audio::FramePos{1500}); m_pButtonLoopIn->set(0); - EXPECT_EQ(1500, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1500}, m_pLoopStartPoint); } TEST_F(LoopingControlTest, LoopOutButton_QuantizeDisabled) { m_pQuantizeEnabled->set(0); m_pClosestBeat->set(1000); m_pNextBeat->set(1000); - seekToSampleAndProcess(500); - m_pLoopStartPoint->set(0); + setCurrentPosition(mixxx::audio::FramePos{500}); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopOutButton_QuantizeEnabledNoBeats) { m_pQuantizeEnabled->set(1); m_pClosestBeat->set(-1); m_pNextBeat->set(-1); - seekToSampleAndProcess(500); - m_pLoopStartPoint->set(0); + setCurrentPosition(mixxx::audio::FramePos{500}); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopOutButton_AdjustLoopOutPointOutsideLoop) { - m_pLoopStartPoint->set(1000); - m_pLoopEndPoint->set(2000); + m_pLoopStartPoint->set(mixxx::audio::FramePos{1000}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); m_pButtonLoopOut->set(1); - seekToSampleAndProcess(3000); + setCurrentPosition(mixxx::audio::FramePos{3000}); m_pButtonLoopOut->set(0); - EXPECT_EQ(3000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{3000}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopOutButton_AdjustLoopOutPointInsideLoop) { - m_pLoopStartPoint->set(100); - m_pLoopEndPoint->set(2000); + m_pLoopStartPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); m_pButtonLoopOut->set(1); - seekToSampleAndProcess(1500); + setCurrentPosition(mixxx::audio::FramePos{1500}); m_pButtonLoopOut->set(0); - EXPECT_EQ(1500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1500}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopInOutButtons_QuantizeEnabled) { - m_pTrack1->trySetBpm(60.0); + const auto bpm = mixxx::Bpm{60}; + m_pTrack1->trySetBpm(bpm); m_pQuantizeEnabled->set(1); - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{250}); m_pButtonLoopIn->set(1); m_pButtonLoopIn->set(0); EXPECT_EQ(m_pClosestBeat->get(), m_pLoopStartPoint->get()); @@ -292,14 +291,16 @@ TEST_F(LoopingControlTest, LoopInOutButtons_QuantizeEnabled) { m_pButtonBeatJumpForward->set(1); m_pButtonBeatJumpForward->set(0); ProcessBuffer(); - EXPECT_DOUBLE_EQ(m_pPlayPosition->get() * kTrackLengthSamples, (44100 * 2 * 4) + 500); + EXPECT_FRAMEPOS_EQ(kTrackEndPosition * m_pPlayPosition->get(), + mixxx::audio::FramePos{(44100 * 4) + 250}); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); ProcessBuffer(); EXPECT_EQ(m_pLoopEndPoint->get(), 44100 * 2 * 4); - EXPECT_DOUBLE_EQ(m_pPlayPosition->get() * kTrackLengthSamples, (44100 * 2 * 4) + 500); + EXPECT_FRAMEPOS_EQ(kTrackEndPosition * m_pPlayPosition->get(), + mixxx::audio::FramePos{(44100 * 4) + 250}); - EXPECT_EQ(4, m_pBeatLoopSize->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{2}, m_pBeatLoopSize); EXPECT_TRUE(m_pBeatLoop4Enabled->toBool()); // Check that beatloop_4_enabled is reset to 0 when changing the loop size. @@ -317,23 +318,23 @@ TEST_F(LoopingControlTest, ReloopToggleButton_TogglesLoop) { m_pQuantizeEnabled->set(0); m_pClosestBeat->set(-1); m_pNextBeat->set(-1); - seekToSampleAndProcess(500); - m_pLoopStartPoint->set(0); + setCurrentPosition(mixxx::audio::FramePos{500}); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); EXPECT_FALSE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); // Ensure that the Loop Exit button works, and that it doesn't act as a // toggle. m_pButtonLoopExit->set(1); @@ -345,20 +346,20 @@ TEST_F(LoopingControlTest, ReloopToggleButton_TogglesLoop) { } TEST_F(LoopingControlTest, ReloopToggleButton_DoesNotJumpAhead) { - m_pLoopStartPoint->set(1000); - m_pLoopEndPoint->set(2000); - seekToSampleAndProcess(0); + m_pLoopStartPoint->set(mixxx::audio::FramePos{1000}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::kStartFramePos); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_LE(currentFramePos().toEngineSamplePos(), m_pLoopStartPoint->get()); } TEST_F(LoopingControlTest, ReloopAndStopButton) { - m_pLoopStartPoint->set(1000); - m_pLoopEndPoint->set(2000); - seekToSampleAndProcess(1500); + m_pLoopStartPoint->set(mixxx::audio::FramePos{1000}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{1500}); m_pButtonReloopToggle->set(1); m_pButtonReloopToggle->set(0); m_pButtonReloopAndStop->set(1); @@ -369,65 +370,65 @@ TEST_F(LoopingControlTest, ReloopAndStopButton) { } TEST_F(LoopingControlTest, LoopScale_DoublesLoop) { - seekToSampleAndProcess(0); + setCurrentPosition(mixxx::audio::kStartFramePos); m_pButtonLoopIn->set(1); m_pButtonLoopIn->set(0); - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{500}); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); m_pLoopScale->set(2.0); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); m_pLoopScale->set(2.0); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(2000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{2000}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopScale_HalvesLoop) { - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(2000); - seekToSampleAndProcess(1800); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(2000, m_pLoopEndPoint->get()); - EXPECT_EQ(1800, currentFramePos().toEngineSamplePos()); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{2000}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{1800}); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{2000}, m_pLoopEndPoint); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{1800}, currentFramePos()); EXPECT_FALSE(isLoopEnabled()); m_pLoopScale->set(0.5); ProcessBuffer(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); // The loop was not enabled so halving the loop should not move the playhead // even though it is outside the loop. - EXPECT_EQ(1800, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{1800}, currentFramePos()); m_pButtonReloopToggle->set(1); EXPECT_TRUE(isLoopEnabled()); m_pLoopScale->set(0.5); ProcessBuffer(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(500, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopEndPoint); // Since the current sample was out of range of the new loop, // the current sample should reseek based on the new loop size. mixxx::audio::FramePos targetPosition; const mixxx::audio::FramePos triggerPosition = m_pChannel1->getEngineBuffer()->m_pLoopingControl->nextTrigger( - false, mixxx::audio::FramePos(900), &targetPosition); - EXPECT_EQ(mixxx::audio::FramePos(150), targetPosition); - EXPECT_EQ(mixxx::audio::FramePos(900), triggerPosition); + false, mixxx::audio::FramePos{1800}, &targetPosition); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{300}, targetPosition); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{1800}, triggerPosition); } TEST_F(LoopingControlTest, LoopDoubleButton_IgnoresPastTrackEnd) { - seekToSampleAndProcess(50); - m_pLoopStartPoint->set(kTrackLengthSamples / 2.0); - m_pLoopEndPoint->set(kTrackLengthSamples); - EXPECT_EQ(kTrackLengthSamples / 2.0, m_pLoopStartPoint->get()); - EXPECT_EQ(kTrackLengthSamples, m_pLoopEndPoint->get()); + setCurrentPosition(mixxx::audio::FramePos{50}); + m_pLoopStartPoint->set(kTrackEndPosition.toEngineSamplePos() / 2.0); + m_pLoopEndPoint->set(kTrackEndPosition.toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(kTrackEndPosition / 2.0, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(kTrackEndPosition, m_pLoopEndPoint); m_pButtonLoopDouble->set(1); m_pButtonLoopDouble->set(0); - EXPECT_EQ(kTrackLengthSamples / 2.0, m_pLoopStartPoint->get()); - EXPECT_EQ(kTrackLengthSamples, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(kTrackEndPosition / 2.0, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(kTrackEndPosition, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopDoubleButton_DoublesBeatloopSize) { @@ -441,18 +442,18 @@ TEST_F(LoopingControlTest, LoopDoubleButton_DoublesBeatloopSize) { } TEST_F(LoopingControlTest, LoopDoubleButton_DoesNotResizeManualLoop) { - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{500}); m_pButtonLoopIn->set(1.0); m_pButtonLoopIn->set(0.0); - seekToSampleAndProcess(1000); + setCurrentPosition(mixxx::audio::FramePos{1000}); m_pButtonLoopOut->set(1.0); m_pButtonLoopOut->set(0.0); - EXPECT_EQ(500, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); m_pButtonLoopDouble->set(1); m_pButtonLoopDouble->set(0); - EXPECT_EQ(500, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopDoubleButton_UpdatesNumberedBeatloopActivationControls) { @@ -471,14 +472,14 @@ TEST_F(LoopingControlTest, LoopDoubleButton_UpdatesNumberedBeatloopActivationCon TEST_F(LoopingControlTest, LoopHalveButton_IgnoresTooSmall) { ProcessBuffer(); - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(40); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(40, m_pLoopEndPoint->get()); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{40}.toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{40}, m_pLoopEndPoint); m_pButtonLoopHalve->set(1); m_pButtonLoopHalve->set(0); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(40, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{40}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopHalveButton_HalvesBeatloopSize) { @@ -492,18 +493,18 @@ TEST_F(LoopingControlTest, LoopHalveButton_HalvesBeatloopSize) { } TEST_F(LoopingControlTest, LoopHalveButton_DoesNotResizeManualLoop) { - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{500}); m_pButtonLoopIn->set(1.0); m_pButtonLoopIn->set(0.0); - seekToSampleAndProcess(1000); + setCurrentPosition(mixxx::audio::FramePos{1000}); m_pButtonLoopOut->set(1.0); m_pButtonLoopOut->set(0.0); - EXPECT_EQ(500, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); m_pButtonLoopHalve->set(1); m_pButtonLoopHalve->set(0); - EXPECT_EQ(500, m_pLoopStartPoint->get()); - EXPECT_EQ(1000, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{500}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{1000}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopHalveButton_UpdatesNumberedBeatloopActivationControls) { @@ -521,32 +522,34 @@ TEST_F(LoopingControlTest, LoopHalveButton_UpdatesNumberedBeatloopActivationCont } TEST_F(LoopingControlTest, LoopMoveTest) { - m_pTrack1->trySetBpm(120); - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(300); - seekToSampleAndProcess(10); + const auto bpm = mixxx::Bpm{120}; + m_pTrack1->trySetBpm(bpm); + + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{150}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{5}); m_pButtonReloopToggle->set(1); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(300, m_pLoopEndPoint->get()); - EXPECT_EQ(10, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{150}, m_pLoopEndPoint); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{5}, currentFramePos()); // Move the loop out from under the playposition. m_pButtonBeatMoveForward->set(1.0); m_pButtonBeatMoveForward->set(0.0); ProcessBuffer(); - EXPECT_EQ(44100, m_pLoopStartPoint->get()); - EXPECT_EQ(44400, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{22050}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{22200}, m_pLoopEndPoint); ProcessBuffer(); // Should seek to the corresponding offset within the moved loop - EXPECT_EQ(44110, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{22055}, currentFramePos()); // Move backward so that the current position is outside the new location of the loop - seekToSampleAndProcess(44300); + setCurrentPosition(mixxx::audio::FramePos{22150}); m_pButtonBeatMoveBackward->set(1.0); m_pButtonBeatMoveBackward->set(0.0); ProcessBuffer(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); EXPECT_NEAR(300, m_pLoopEndPoint->get(), kLoopPositionMaxAbsError); ProcessBuffer(); EXPECT_NEAR(200, @@ -562,19 +565,19 @@ TEST_F(LoopingControlTest, LoopMoveTest) { m_pButtonBeatMoveForward->set(1.0); m_pButtonBeatMoveForward->set(0.0); ProcessBuffer(); - EXPECT_EQ(44100, m_pLoopStartPoint->get()); - EXPECT_EQ(44400, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{22050}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{22200}, m_pLoopEndPoint); // Should not seek inside the moved loop when the loop is disabled EXPECT_NEAR(200, currentFramePos().toEngineSamplePos(), kLoopPositionMaxAbsError); // Move backward so that the current position is outside the new location of the loop - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{250}); m_pButtonBeatMoveBackward->set(1.0); m_pButtonBeatMoveBackward->set(0.0); ProcessBuffer(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); EXPECT_NEAR(300, m_pLoopEndPoint->get(), kLoopPositionMaxAbsError); EXPECT_NEAR(500, currentFramePos().toEngineSamplePos(), @@ -590,14 +593,14 @@ TEST_F(LoopingControlTest, LoopResizeSeek) { m_pQuantizeEnabled->set(0.0); m_pTrack1->trySetBpm(23520); - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(600); - seekToSampleAndProcess(500); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{300}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{250}); m_pButtonReloopToggle->set(1); EXPECT_TRUE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(600, m_pLoopEndPoint->get()); - EXPECT_EQ(500, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{300}, m_pLoopEndPoint); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{250}, currentFramePos()); // Activate a shorter loop m_pButtonBeatLoop2Activate->set(1.0); @@ -606,27 +609,27 @@ TEST_F(LoopingControlTest, LoopResizeSeek) { // The loop is resized and we should have seeked to a mid-beat part of the // loop. - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(450, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{225}, m_pLoopEndPoint); ProcessBuffer(); - EXPECT_EQ(50, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{25}, currentFramePos()); // But if looping is not enabled, no warping occurs. - m_pLoopStartPoint->set(0); - m_pLoopEndPoint->set(600); - seekToSampleAndProcess(500); + m_pLoopStartPoint->set(mixxx::audio::kStartFramePos.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{300}.toEngineSamplePos()); + setCurrentPosition(mixxx::audio::FramePos{250}); m_pButtonReloopToggle->set(1); EXPECT_FALSE(isLoopEnabled()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(600, m_pLoopEndPoint->get()); - EXPECT_EQ(500, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{300}, m_pLoopEndPoint); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{250}, currentFramePos()); m_pButtonBeatLoop2Activate->set(1.0); ProcessBuffer(); - EXPECT_EQ(500, m_pLoopStartPoint->get()); - EXPECT_EQ(950, m_pLoopEndPoint->get()); - EXPECT_EQ(500, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{250}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{475}, m_pLoopEndPoint); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{250}, currentFramePos()); } TEST_F(LoopingControlTest, BeatLoopSize_SetAndToggle) { @@ -657,7 +660,9 @@ TEST_F(LoopingControlTest, BeatLoopSize_IgnoresPastTrackEnd) { // TODO: actually calculate that the beatloop would go beyond // the end of the track m_pTrack1->trySetBpm(60.0); - seekToSampleAndProcess(m_pTrackSamples->get() - 400); + setCurrentPosition(mixxx::audio::FramePos::fromEngineSamplePosMaybeInvalid( + m_pTrackSamples->get()) - + 200); m_pBeatLoopSize->set(64.0); EXPECT_NE(64.0, m_pBeatLoopSize->get()); EXPECT_FALSE(m_pBeatLoop64Enabled->toBool()); @@ -700,7 +705,7 @@ TEST_F(LoopingControlTest, BeatLoopSize_SetDoesNotStartLoop) { } TEST_F(LoopingControlTest, BeatLoopSize_ResizeKeepsStartPosition) { - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pTrack1->trySetBpm(160.0); m_pBeatLoopSize->set(2.0); m_pButtonBeatLoopActivate->set(1.0); @@ -716,7 +721,7 @@ TEST_F(LoopingControlTest, BeatLoopSize_ResizeKeepsStartPosition) { } TEST_F(LoopingControlTest, BeatLoopSize_ValueChangeDoesNotActivateLoop) { - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pTrack1->trySetBpm(160.0); m_pBeatLoopSize->set(2.0); m_pButtonBeatLoopActivate->set(1.0); @@ -732,7 +737,7 @@ TEST_F(LoopingControlTest, BeatLoopSize_ValueChangeDoesNotActivateLoop) { } TEST_F(LoopingControlTest, BeatLoopSize_ValueChangeResizesBeatLoop) { - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pTrack1->trySetBpm(160.0); m_pBeatLoopSize->set(2.0); m_pButtonBeatLoopActivate->set(1.0); @@ -756,13 +761,13 @@ TEST_F(LoopingControlTest, BeatLoopSize_ValueChangeResizesBeatLoop) { } TEST_F(LoopingControlTest, BeatLoopSize_ValueChangeDoesNotResizeManualLoop) { - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); m_pTrack1->trySetBpm(160.0); m_pQuantizeEnabled->set(0); m_pBeatLoopSize->set(4.0); m_pButtonLoopIn->set(1); m_pButtonLoopIn->set(0); - seekToSampleAndProcess(500); + setCurrentPosition(mixxx::audio::FramePos{500}); m_pButtonLoopOut->set(1); m_pButtonLoopOut->set(0); double oldLoopStart = m_pLoopStartPoint->get(); @@ -796,65 +801,77 @@ TEST_F(LoopingControlTest, LegacyBeatLoopControl) { } TEST_F(LoopingControlTest, Beatjump_JumpsByBeats) { - m_pTrack1->trySetBpm(120.0); + const auto bpm = mixxx::Bpm{120}; + m_pTrack1->trySetBpm(bpm); ProcessBuffer(); - double beatLength = m_pNextBeat->get(); - EXPECT_NE(0, beatLength); + const mixxx::audio::FrameDiff_t beatLengthFrames = 60.0 * 44100.0 / bpm.value(); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames}, m_pNextBeat); + EXPECT_NE(0, beatLengthFrames); m_pBeatJumpSize->set(4.0); m_pButtonBeatJumpForward->set(1.0); m_pButtonBeatJumpForward->set(0.0); ProcessBuffer(); - EXPECT_EQ(beatLength * 4, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ(mixxx::audio::FramePos{beatLengthFrames * 4}, currentFramePos()); m_pButtonBeatJumpBackward->set(1.0); m_pButtonBeatJumpBackward->set(0.0); ProcessBuffer(); - EXPECT_EQ(0, currentFramePos().toEngineSamplePos()); + EXPECT_FRAMEPOS_EQ(mixxx::audio::kStartFramePos, currentFramePos()); } TEST_F(LoopingControlTest, Beatjump_MovesActiveLoop) { - m_pTrack1->trySetBpm(120.0); + const auto bpm = mixxx::Bpm{120}; + m_pTrack1->trySetBpm(bpm); ProcessBuffer(); + const mixxx::audio::FrameDiff_t beatLengthFrames = 60.0 * 44100.0 / bpm.value(); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames}, m_pNextBeat); + EXPECT_NE(0, beatLengthFrames); + m_pBeatLoopSize->set(4.0); m_pButtonBeatLoopActivate->set(1.0); m_pButtonBeatLoopActivate->set(0.0); - double beatLength = m_pNextBeat->get(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 4, m_pLoopEndPoint->get()); + const auto loopStartPosition = mixxx::audio::kStartFramePos; + const auto loopEndPosition = mixxx::audio::FramePos{beatLengthFrames * 4}; + EXPECT_FRAMEPOS_EQ_CONTROL(loopStartPosition, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(loopEndPosition, m_pLoopEndPoint); m_pBeatJumpSize->set(1.0); m_pButtonBeatJumpForward->set(1.0); m_pButtonBeatJumpForward->set(0.0); - EXPECT_EQ(beatLength, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 5, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(loopStartPosition + beatLengthFrames, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(loopEndPosition + beatLengthFrames, m_pLoopEndPoint); // jump backward with playposition outside the loop should not move the loop m_pButtonBeatJumpBackward->set(1.0); m_pButtonBeatJumpBackward->set(0.0); - EXPECT_EQ(beatLength, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 5, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(loopStartPosition + beatLengthFrames, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(loopEndPosition + beatLengthFrames, m_pLoopEndPoint); - seekToSampleAndProcess(beatLength); + setCurrentPosition(mixxx::audio::FramePos{beatLengthFrames}); m_pButtonBeatJumpBackward->set(1.0); m_pButtonBeatJumpBackward->set(0.0); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 4, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(loopStartPosition, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(loopEndPosition, m_pLoopEndPoint); } TEST_F(LoopingControlTest, Beatjump_MovesLoopBoundaries) { // Holding down the loop in/out buttons and using beatjump should // move only the loop in/out point, but not shift the entire loop forward/backward - m_pTrack1->trySetBpm(120.0); + const auto bpm = mixxx::Bpm{120}; + m_pTrack1->trySetBpm(bpm); ProcessBuffer(); + const mixxx::audio::FrameDiff_t beatLengthFrames = 60.0 * 44100.0 / bpm.value(); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames}, m_pNextBeat); + EXPECT_NE(0, beatLengthFrames); + m_pBeatLoopSize->set(4.0); m_pButtonBeatLoopActivate->set(1.0); m_pButtonBeatLoopActivate->set(0.0); - double beatLength = m_pNextBeat->get(); - EXPECT_EQ(0, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 4, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames * 4}, m_pLoopEndPoint); m_pButtonLoopIn->set(1.0); m_pBeatJumpSize->set(1.0); @@ -863,8 +880,8 @@ TEST_F(LoopingControlTest, Beatjump_MovesLoopBoundaries) { ProcessBuffer(); m_pButtonLoopIn->set(0.0); ProcessBuffer(); - EXPECT_EQ(beatLength, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 4, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames * 4}, m_pLoopEndPoint); m_pButtonLoopOut->set(1.0); m_pButtonBeatJumpForward->set(1.0); @@ -872,19 +889,19 @@ TEST_F(LoopingControlTest, Beatjump_MovesLoopBoundaries) { ProcessBuffer(); m_pButtonLoopOut->set(0.0); ProcessBuffer(); - EXPECT_EQ(beatLength, m_pLoopStartPoint->get()); - EXPECT_EQ(beatLength * 2, m_pLoopEndPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames}, m_pLoopStartPoint); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{beatLengthFrames * 2}, m_pLoopEndPoint); } TEST_F(LoopingControlTest, LoopEscape) { - m_pLoopStartPoint->set(100); - m_pLoopEndPoint->set(200); + m_pLoopStartPoint->set(mixxx::audio::FramePos{100}.toEngineSamplePos()); + m_pLoopEndPoint->set(mixxx::audio::FramePos{200}.toEngineSamplePos()); m_pButtonReloopToggle->set(1.0); m_pButtonReloopToggle->set(0.0); ProcessBuffer(); EXPECT_TRUE(isLoopEnabled()); // seek outside a loop should disable it - seekToSampleAndProcess(300); + setCurrentPosition(mixxx::audio::FramePos{300}); EXPECT_FALSE(isLoopEnabled()); m_pButtonReloopToggle->set(1.0); @@ -892,7 +909,7 @@ TEST_F(LoopingControlTest, LoopEscape) { ProcessBuffer(); EXPECT_TRUE(isLoopEnabled()); // seek outside a loop should disable it - seekToSampleAndProcess(50); + setCurrentPosition(mixxx::audio::FramePos{50}); EXPECT_FALSE(isLoopEnabled()); } @@ -971,23 +988,23 @@ TEST_F(LoopingControlTest, BeatLoopRoll_StartPoint) { m_pTrack1->trySetBpm(120.0); // start a 4 beat loop roll, start point should be overridden to play position - m_pLoopStartPoint->set(8); + m_pLoopStartPoint->set(mixxx::audio::FramePos{8}.toEngineSamplePos()); m_pButtonBeatLoopRoll4Activate->set(1.0); EXPECT_TRUE(m_pLoopEnabled->toBool()); EXPECT_TRUE(m_pBeatLoop4Enabled->toBool()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); // move the start point, activate a 1 beat loop roll, new start point be preserved - m_pLoopStartPoint->set(8); + m_pLoopStartPoint->set(mixxx::audio::FramePos{8}.toEngineSamplePos()); m_pButtonBeatLoopRoll1Activate->set(1.0); EXPECT_TRUE(m_pLoopEnabled->toBool()); EXPECT_TRUE(m_pBeatLoop1Enabled->toBool()); - EXPECT_EQ(8, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{8}, m_pLoopStartPoint); // end the 1 beat loop roll m_pButtonBeatLoopRoll1Activate->set(0.0); EXPECT_TRUE(m_pLoopEnabled->toBool()); - EXPECT_EQ(8, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::FramePos{8}, m_pLoopStartPoint); EXPECT_TRUE(m_pBeatLoop4Enabled->toBool()); // end the 4 beat loop roll @@ -999,5 +1016,5 @@ TEST_F(LoopingControlTest, BeatLoopRoll_StartPoint) { m_pButtonBeatLoopRoll4Activate->set(1.0); EXPECT_TRUE(m_pLoopEnabled->toBool()); EXPECT_TRUE(m_pBeatLoop4Enabled->toBool()); - EXPECT_EQ(0, m_pLoopStartPoint->get()); + EXPECT_FRAMEPOS_EQ_CONTROL(mixxx::audio::kStartFramePos, m_pLoopStartPoint); }