From 0c8ba878f3daa3ec90f82291a68afd2dfea9d933 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Gu=C3=B0ni=20M=C3=A1r=20Gilbert?= Date: Mon, 29 May 2023 12:44:22 +0000 Subject: [PATCH] MMU-239 Add unit test for ejecting slots 0-4 This test ejects slots 0 to 4 and goes through the state machine without creating any errors like FINDA_FLICKERS. It also verifies the selector parking position is correct for each ejected filament slot. --- .../eject_filament/test_eject_filament.cpp | 64 +++++++++++-------- 1 file changed, 36 insertions(+), 28 deletions(-) diff --git a/tests/unit/logic/eject_filament/test_eject_filament.cpp b/tests/unit/logic/eject_filament/test_eject_filament.cpp index baf4562..5812c9d 100644 --- a/tests/unit/logic/eject_filament/test_eject_filament.cpp +++ b/tests/unit/logic/eject_filament/test_eject_filament.cpp @@ -1,4 +1,5 @@ #include "catch2/catch_test_macros.hpp" +#include "catch2/generators/catch_generators.hpp" #include "../../../../src/modules/buttons.h" #include "../../../../src/modules/finda.h" @@ -19,53 +20,60 @@ #include "../helpers/helpers.ipp" -// temporarily disabled -TEST_CASE("eject_filament::eject0", "[eject_filament][.]") { +TEST_CASE("eject_filament::eject0-4", "[eject_filament]") { using namespace logic; + uint8_t ejectSlot = GENERATE(0, 1, 2, 3, 4); + uint8_t selectorParkedPos = (ejectSlot <= 2) ? 4 : 0; + ForceReinitAllAutomata(); - REQUIRE(EnsureActiveSlotIndex(0, mg::FilamentLoadState::AtPulley)); + + REQUIRE(EnsureActiveSlotIndex(ejectSlot, mg::FilamentLoadState::AtPulley)); EjectFilament ef; // restart the automaton - ef.Reset(0); + ef.Reset(ejectSlot); main_loop(); - // it should have instructed the selector and idler to move to slot 1 - // check if the idler and selector have the right command - CHECK(mm::AxisNearestTargetPos(mm::Idler) == mi::Idler::SlotPosition(0).v); - CHECK(mm::AxisNearestTargetPos(mm::Selector) == ms::Selector::SlotPosition(4).v); + // Start at UnloadingFilament + REQUIRE(ef.TopLevelState() == ProgressCode::UnloadingFilament); - // now cycle at most some number of cycles (to be determined yet) and then verify, that the idler and selector reached their target positions - REQUIRE(WhileTopState(ef, ProgressCode::SelectingFilamentSlot, 5000)); + REQUIRE(WhileTopState(ef, ProgressCode::UnloadingFilament, 5000)); - // idler and selector reached their target positions and the CF automaton will start feeding to FINDA as the next step - REQUIRE(ef.TopLevelState() == ProgressCode::FeedingToFinda); - // prepare for simulated finda trigger - hal::gpio::WritePin(FINDA_PIN, hal::gpio::Level::high); - REQUIRE(WhileTopState(ef, ProgressCode::FeedingToFinda, 50000)); + REQUIRE(ef.TopLevelState() == ProgressCode::ParkingSelector); - // filament fed into FINDA, cutting... - REQUIRE(ef.TopLevelState() == ProgressCode::PreparingBlade); - REQUIRE(WhileTopState(ef, ProgressCode::PreparingBlade, 5000)); + REQUIRE(WhileTopState(ef, ProgressCode::ParkingSelector, selectorMoveMaxSteps)); + // Engaging idler REQUIRE(ef.TopLevelState() == ProgressCode::EngagingIdler); + REQUIRE(WhileTopState(ef, ProgressCode::EngagingIdler, 5000)); - // the idler should be at the active slot @@TODO - REQUIRE(ef.TopLevelState() == ProgressCode::PushingFilament); - REQUIRE(WhileTopState(ef, ProgressCode::PushingFilament, 5000)); + REQUIRE(mi::idler.Engaged()); + REQUIRE(ef.TopLevelState() == ProgressCode::EjectingFilament); - // filament pushed - performing cut - REQUIRE(ef.TopLevelState() == ProgressCode::PerformingCut); - REQUIRE(WhileTopState(ef, ProgressCode::PerformingCut, 5000)); + REQUIRE(WhileTopState(ef, ProgressCode::EjectingFilament, 5000)); - // returning selector - REQUIRE(ef.TopLevelState() == ProgressCode::ReturningSelector); - REQUIRE(WhileTopState(ef, ProgressCode::ReturningSelector, 5000)); + // should end up in error disengage idler + REQUIRE(VerifyState2(ef, mg::FilamentLoadState::AtPulley, ejectSlot, selectorParkedPos, false, true, ejectSlot, ml::off, ml::blink0, ErrorCode::RUNNING, ProgressCode::ERRDisengagingIdler)); - // the next states are still @@TODO + SimulateErrDisengagingIdler(ef, ErrorCode::FILAMENT_EJECTED); + + // Pulley should now be disabled + REQUIRE(VerifyState2(ef, mg::FilamentLoadState::AtPulley, mi::idler.IdleSlotIndex(), selectorParkedPos, false, false, ejectSlot, ml::off, ml::blink0, ErrorCode::FILAMENT_EJECTED, ProgressCode::ERRWaitingForUser)); + + // Now press Done button + PressButtonAndDebounce(ef, mb::Middle, true); + ClearButtons(ef); + + // Idler and Selector are not on HOLD state + REQUIRE(mi::idler.State() != mm::MovableBase::OnHold); + REQUIRE(ms::selector.State() != mm::MovableBase::OnHold); + + // Error code is now OK + // LEDs turn off at the ejected slot + REQUIRE(VerifyState2(ef, mg::FilamentLoadState::AtPulley, mi::idler.IdleSlotIndex(), selectorParkedPos, false, false, ejectSlot, ml::off, ml::off, ErrorCode::OK, ProgressCode::OK)); } TEST_CASE("eject_filament::invalid_slot", "[eject_filament]") {