From fd6c7ad9d3fe5f96a4e9a6610c1fce9122fdaf24 Mon Sep 17 00:00:00 2001 From: t0mpr1c3 Date: Thu, 28 Sep 2023 18:59:02 -0400 Subject: [PATCH] ignore beltshift for KH270 --- src/ayab/encoders.cpp | 24 ++++++++++------- src/ayab/encoders.h | 8 +++--- src/ayab/opKnit.cpp | 4 +-- src/ayab/solenoids.h | 1 + test/test_OpKnit.cpp | 61 +++++++++++++++++++++++++++++++++--------- test/test_encoders.cpp | 36 ++++++++++++++++--------- 6 files changed, 93 insertions(+), 41 deletions(-) diff --git a/src/ayab/encoders.cpp b/src/ayab/encoders.cpp index f1d828b92..2d6fde150 100644 --- a/src/ayab/encoders.cpp +++ b/src/ayab/encoders.cpp @@ -162,10 +162,12 @@ void Encoders::encA_rising() { return; } - // In front of Left Hall Sensor? + // Hall value is used to detect whether carriage is in front of Left Hall sensor uint16_t hallValue = analogRead(EOL_PIN_L); + if ((hallValue < FILTER_L_MIN[static_cast(m_machineType)]) || (hallValue > FILTER_L_MAX[static_cast(m_machineType)])) { + // In front of Left Hall Sensor m_hallActive = Direction_t::Left; Carriage detected_carriage = Carriage_t::NoCarriage; @@ -192,10 +194,11 @@ void Encoders::encA_rising() { return; } else { m_carriage = detected_carriage; - } - // Belt shift signal only decided in front of hall sensor - m_beltShift = digitalRead(ENC_PIN_C) ? BeltShift::Regular : BeltShift::Shifted; + // Belt shift signal only decided in front of Hall sensor + // Belt shift is ignored for KH270 + m_beltShift = digitalRead(ENC_PIN_C) ? BeltShift::Regular : BeltShift::Shifted; + } // Known position of the carriage -> overwrite position m_position = start_position; @@ -218,27 +221,30 @@ void Encoders::encA_falling() { m_position = m_position - 1; } - // In front of Right Hall Sensor? + // Hall value is used to detect whether carriage is in front of Right Hall sensor uint16_t hallValue = analogRead(EOL_PIN_R); // Avoid 'comparison of unsigned expression < 0 is always false' // by being explicit about that behaviour being expected. bool hallValueSmall = false; - hallValueSmall = (hallValue < FILTER_R_MIN[static_cast(m_machineType)]); if (hallValueSmall || (hallValue > FILTER_R_MAX[static_cast(m_machineType)])) { + // In front of Right Hall Sensor m_hallActive = Direction_t::Right; - // The garter carriage has a second set of magnets that are going to + // The Garter carriage has a second set of magnets that are going to // pass the sensor and will reset state incorrectly if allowed to // continue. if (hallValueSmall && (m_carriage != Carriage_t::Garter)) { m_carriage = Carriage_t::Knit; } - // Belt shift signal only decided in front of hall sensor - m_beltShift = digitalRead(ENC_PIN_C) ? BeltShift::Shifted : BeltShift::Regular; + // Belt shift is ignored for KH270 + if (m_machineType != Machine_t::Kh270) { + // Belt shift signal only decided in front of Hall sensor + m_beltShift = digitalRead(ENC_PIN_C) ? BeltShift::Shifted : BeltShift::Regular; + } // Known position of the carriage -> overwrite position m_position = END_RIGHT_MINUS_OFFSET[static_cast(m_machineType)]; diff --git a/src/ayab/encoders.h b/src/ayab/encoders.h index 5bc17cbde..031d5b987 100644 --- a/src/ayab/encoders.h +++ b/src/ayab/encoders.h @@ -84,19 +84,19 @@ constexpr uint8_t START_OFFSET[NUM_MACHINES][NUM_DIRECTIONS][NUM_CARRIAGES] = { { // K, L, G {40U, 40U, 32U}, // Left - {16U, 16U, 56U} // Right + {16U, 16U, 56U} // Right }, // KH930 { // K, L, G {40U, 40U, 8U}, // Left - {16U, 16U, 32U} // Right + {16U, 16U, 32U} // Right }, // KH270 { // K {28U, 0U, 0U}, // Left: x % 12 == 4 - {16U, 0U, 0U} // Right: (x + 6) % 12 == 10 + {16U, 0U, 0U} // Right: (x + 6) % 12 == 10 }}; // Should be calibrated to each device @@ -108,8 +108,6 @@ constexpr uint16_t FILTER_L_MAX[NUM_MACHINES] = { 600U, 600U, 600U}; constexpr uint16_t FILTER_R_MIN[NUM_MACHINES] = { 200U, 0U, 0U}; constexpr uint16_t FILTER_R_MAX[NUM_MACHINES] = {1023U, 600U, 600U}; -constexpr uint16_t SOLENOIDS_BITMASK = 0xFFFFU; - constexpr uint8_t MAGNET_DISTANCE_270 = 12U; /*! diff --git a/src/ayab/opKnit.cpp b/src/ayab/opKnit.cpp index 55b88c3f7..6224eeba6 100644 --- a/src/ayab/opKnit.cpp +++ b/src/ayab/opKnit.cpp @@ -191,7 +191,7 @@ void OpKnit::encodePosition() { // only act if there is an actual change of position // store current encoder position for next call of this function m_sOldPosition = position; - calculatePixelAndSolenoid(); + (void) calculatePixelAndSolenoid(); GlobalCom::send_indState(Err_t::Unspecified_failure); // FIXME is this the right error code? } } @@ -333,8 +333,8 @@ void OpKnit::reqLine(uint8_t lineNumber) { bool OpKnit::calculatePixelAndSolenoid() { uint8_t startOffset = 0; - auto direction = GlobalController::getDirection(); auto position = GlobalController::getPosition(); + auto direction = GlobalController::getDirection(); auto beltShift = GlobalController::getBeltShift(); auto carriage = GlobalController::getCarriage(); auto machineType = GlobalController::getMachineType(); diff --git a/src/ayab/solenoids.h b/src/ayab/solenoids.h index f5c895806..793e5d63e 100644 --- a/src/ayab/solenoids.h +++ b/src/ayab/solenoids.h @@ -36,6 +36,7 @@ constexpr uint8_t SOLENOIDS_NUM[NUM_MACHINES] = {16U, 16U, 12U}; constexpr uint8_t HALF_SOLENOIDS_NUM[NUM_MACHINES] = {8U, 8U, 6U}; constexpr uint8_t SOLENOIDS_I2C_ADDRESS_MASK = 0x20U; constexpr uint8_t SOLENOID_BUFFER_SIZE = 16U; +constexpr uint16_t SOLENOIDS_BITMASK = 0xFFFFU; class SolenoidsInterface { public: diff --git a/test/test_OpKnit.cpp b/test/test_OpKnit.cpp index 275af52cf..c909e58cf 100644 --- a/test/test_OpKnit.cpp +++ b/test/test_OpKnit.cpp @@ -143,6 +143,11 @@ class OpKnitTest : public ::testing::Test { controller->cacheEncoders(); } + void expected_cacheISR(uint16_t pos, Direction_t dir, BeltShift_t belt, Carriage_t carriage) { + expect_cacheISR(pos, dir, Direction_t::NoDirection, belt, carriage); + controller->cacheEncoders(); + } + void expect_cacheISR(Direction_t dir, Direction_t hall) { expect_cacheISR(1, dir, hall, BeltShift::Regular, Carriage_t::Knit); } @@ -646,57 +651,87 @@ TEST_F(OpKnitTest, test_calculatePixelAndSolenoid) { // No direction // Lace carriage, no direction, need to change position to enter test - expected_cacheISR(100, Direction_t::NoDirection, Direction_t::Right, BeltShift::Shifted, Carriage_t::Lace); + expected_cacheISR(100, Direction_t::NoDirection, BeltShift::Shifted, Carriage_t::Lace); ASSERT_FALSE(opKnit->calculatePixelAndSolenoid()); + // opKnit->pixelToSet not set + // opKnit->m_solenoidToSet not set // Right direction // Lace carriage, no belt on Right, have not reached offset - expected_cacheISR(39, Direction_t::Right, Direction_t::Left, BeltShift::Unknown, Carriage_t::Lace); + expected_cacheISR(39, Direction_t::Right, BeltShift::Unknown, Carriage_t::Lace); ASSERT_FALSE(opKnit->calculatePixelAndSolenoid()); + // opKnit->pixelToSet not set + // opKnit->m_solenoidToSet not set // Lace carriage, no belt on Right, need to change position to enter test - expected_cacheISR(100, Direction_t::Right, Direction_t::Right, BeltShift::Unknown, Carriage_t::Lace); + expected_cacheISR(100, Direction_t::Right, BeltShift::Unknown, Carriage_t::Lace); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, (100 - 40) + 8); + // opKnit->m_solenoidToSet not set // Lace carriage, regular belt on Right - expected_cacheISR(100, Direction_t::Right, Direction_t::Right, BeltShift::Regular, Carriage_t::Lace); + expected_cacheISR(100, Direction_t::Right, BeltShift::Regular, Carriage_t::Lace); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, (100 - 40) + 8); + ASSERT_EQ(opKnit->m_solenoidToSet, 100 % 16); - // Lace carriage, shifted belt on Right, new position, active Hall - expected_cacheISR(100, Direction_t::Right, Direction_t::Right, BeltShift::Shifted, Carriage_t::Lace); + // Lace carriage, shifted belt on Right + expected_cacheISR(100, Direction_t::Right, BeltShift::Shifted, Carriage_t::Lace); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, (100 - 40) + 8); + ASSERT_EQ(opKnit->m_solenoidToSet, (100 - 8) % 16); // Left direction // Lace carriage, no belt on Left, off of Right end, position is changed - expected_cacheISR(END_RIGHT[static_cast(Machine_t::Kh910)] - 15, Direction_t::Left, Direction_t::Right, BeltShift::Unknown, Carriage_t::Lace); + expected_cacheISR(END_RIGHT[static_cast(Machine_t::Kh910)] - 15, Direction_t::Left, BeltShift::Unknown, Carriage_t::Lace); ASSERT_FALSE(opKnit->calculatePixelAndSolenoid()); + // opKnit->pixelToSet not set + // opKnit->m_solenoidToSet not set // Lace carriage, no belt on Left - expected_cacheISR(100, Direction_t::Left, Direction_t::Right, BeltShift::Unknown, Carriage_t::Lace); + expected_cacheISR(100, Direction_t::Left, BeltShift::Unknown, Carriage_t::Lace); + ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, 100 - 16 - 16); + // opKnit->m_solenoidToSet not set + + // Lace carriage, regular belt on Left + expected_cacheISR(100, Direction_t::Left, BeltShift::Regular, Carriage_t::Lace); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, 100 - 16 - 16); + ASSERT_EQ(opKnit->m_solenoidToSet, (100 + 8) % 16); // Garter Carriage, no belt on Left, need to change position to enter test - expected_cacheISR(101, Direction_t::Left, Direction_t::Right, BeltShift::Unknown, Carriage_t::Garter); + expected_cacheISR(100, Direction_t::Left, BeltShift::Unknown, Carriage_t::Garter); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, 100 - 56); + // opKnit->m_solenoidToSet not set // Garter carriage, regular belt on Left, need to change position to enter test - expected_cacheISR(101, Direction_t::Left, Direction_t::Right, BeltShift::Regular, Carriage_t::Garter); + expected_cacheISR(100, Direction_t::Left, BeltShift::Regular, Carriage_t::Garter); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, 100 - 56); + ASSERT_EQ(opKnit->m_solenoidToSet, (100 + 8) % 16); // Garter carriage, shifted belt on Left, need to change position to enter test - expected_cacheISR(100, Direction_t::Left, Direction_t::Right, BeltShift::Shifted, Carriage_t::Garter); + expected_cacheISR(100, Direction_t::Left, BeltShift::Shifted, Carriage_t::Garter); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, 100 - 56); + ASSERT_EQ(opKnit->m_solenoidToSet, 100 % 16); // KH270 controller->setMachineType(Machine_t::Kh270); // K carriage, no belt on Left - expected_cacheISR(0, Direction_t::Left, Direction_t::Right, BeltShift::Unknown, Carriage_t::Knit); + expected_cacheISR(0, Direction_t::Left, BeltShift::Unknown, Carriage_t::Knit); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, static_cast(0 - 16)); + ASSERT_EQ(opKnit->m_solenoidToSet, static_cast(0 + 6) % 12 + 3); // K carriage, no belt on Right - expected_cacheISR(END_RIGHT[static_cast(Machine_t::Kh270)], Direction_t::Right, Direction_t::Left, BeltShift::Unknown, Carriage_t::Knit); + expected_cacheISR(END_RIGHT[static_cast(Machine_t::Kh270)], Direction_t::Right, BeltShift::Unknown, Carriage_t::Knit); ASSERT_TRUE(opKnit->calculatePixelAndSolenoid()); + ASSERT_EQ(opKnit->m_pixelToSet, (140 - 28)); + ASSERT_EQ(opKnit->m_solenoidToSet, 140 % 12 + 3); // Test expectations without destroying instance ASSERT_TRUE(Mock::VerifyAndClear(solenoidsMock)); diff --git a/test/test_encoders.cpp b/test/test_encoders.cpp index 376762d42..6aae8441f 100644 --- a/test/test_encoders.cpp +++ b/test/test_encoders.cpp @@ -155,26 +155,38 @@ TEST_F(EncodersTest, test_encA_rising_in_front_KH270) { // In front of Left Hall Sensor EXPECT_CALL(*arduinoMock, analogRead(EOL_PIN_L)) .WillOnce(Return(FILTER_L_MIN[static_cast(Machine_t::Kh270)] - 1)); - // BeltShift is regular - EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_C)).WillOnce(Return(true)); + // BeltShift is ignored + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_C)).Times(0); encoders->isr(); ASSERT_EQ(encoders->getDirection(), Direction_t::Right); ASSERT_EQ(encoders->getHallActive(), Direction_t::Left); ASSERT_EQ(encoders->getPosition(), END_LEFT_PLUS_OFFSET[static_cast(Machine_t::Kh270)]); ASSERT_EQ(encoders->getCarriage(), Carriage_t::Knit); - ASSERT_EQ(encoders->getBeltShift(), BeltShift::Regular); + ASSERT_EQ(encoders->getBeltShift(), BeltShift::Unknown); - // Create a falling edge, then a rising edge: - EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_A)).WillOnce(Return(false)).WillOnce(Return(true)); - EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_B)).WillOnce(Return(false)).WillOnce(Return(true)); - // Not in front of Left Hall Sensor + // Enter falling function + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_A)).WillOnce(Return(false)); + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_B)).WillOnce(Return(false)); + // In front of Left Hall Sensor EXPECT_CALL(*arduinoMock, analogRead(EOL_PIN_R)) - .WillOnce(Return(FILTER_R_MIN[static_cast(encoders->getMachineType())])); + .WillOnce(Return(FILTER_R_MIN[static_cast(encoders->getMachineType())] - 1)); + // BeltShift is ignored + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_C)).Times(0); + encoders->isr(); + + ASSERT_EQ(encoders->getDirection(), Direction_t::Right); + ASSERT_EQ(encoders->getHallActive(), Direction_t::Right); + ASSERT_EQ(encoders->getPosition(), END_RIGHT_MINUS_OFFSET[static_cast(Machine_t::Kh270)]); + ASSERT_EQ(encoders->getCarriage(), Carriage_t::Knit); + ASSERT_EQ(encoders->getBeltShift(), BeltShift::Unknown); + + // Create a rising edge + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_A)).WillOnce(Return(true)); + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_B)).WillOnce(Return(true)); // We will not enter the rising function EXPECT_CALL(*arduinoMock, analogRead(EOL_PIN_L)).Times(0); encoders->isr(); - encoders->isr(); } TEST_F(EncodersTest, test_encA_rising_after_KH270) { @@ -193,15 +205,15 @@ TEST_F(EncodersTest, test_encA_rising_after_KH270) { // After Left Hall Sensor EXPECT_CALL(*arduinoMock, analogRead(EOL_PIN_L)) .WillOnce(Return(FILTER_L_MAX[static_cast(encoders->getMachineType())] + 1)); - // BeltShift is regular - EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_C)).WillOnce(Return(true)); + // BeltShift is ignored + EXPECT_CALL(*arduinoMock, digitalRead(ENC_PIN_C)).Times(0); encoders->isr(); ASSERT_EQ(encoders->getDirection(), Direction_t::Right); ASSERT_EQ(encoders->getHallActive(), Direction_t::Left); ASSERT_EQ(encoders->getPosition(), END_LEFT_PLUS_OFFSET[static_cast(Machine_t::Kh270)] + MAGNET_DISTANCE_270); ASSERT_EQ(encoders->getCarriage(), Carriage_t::Knit); - ASSERT_EQ(encoders->getBeltShift(), BeltShift::Regular); + ASSERT_EQ(encoders->getBeltShift(), BeltShift::Unknown); } TEST_F(EncodersTest, test_G_carriage) {