Skip to content

Commit

Permalink
Add parameterized tests for G-carriage detection
Browse files Browse the repository at this point in the history
  • Loading branch information
jonathanperret committed Oct 13, 2024
1 parent a3e242a commit 226b99b
Showing 1 changed file with 159 additions and 66 deletions.
225 changes: 159 additions & 66 deletions test/test_e2e.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,28 @@ struct E2ETest : public ::testing::Test {
WireMock *m_WireMock;
};

struct WithTargetNeedle: public E2ETest, public testing::WithParamInterface<int> {

};

struct NeedleToStringParamName {
std::string operator()(const TestParamInfo<int>& info) const {
return (info.param < 0 ? std::string("neg") : std::string() ) + PrintToString(std::abs(info.param));
}
};

INSTANTIATE_TEST_SUITE_P(E2EParameterizedRight,
WithTargetNeedle,
testing::Range(150, 250),
NeedleToStringParamName()
);
INSTANTIATE_TEST_SUITE_P(E2EParameterizedLeft,
WithTargetNeedle,
testing::Range(-50, 50),
NeedleToStringParamName()
);


TEST_F(E2ETest, BeeperBeeps) {
int millisElapsed = 0;
int buzzerValue = -1;
Expand Down Expand Up @@ -187,135 +209,206 @@ TEST_F(E2ETest, EncodersDetectKCarriageOnTheLeft) {
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Knit);
}

TEST_F(E2ETest, EncodersDetectKCarriageOnTheRight_KH910) {
TEST_F(E2ETest, EncodersDetectLCarriageOnTheLeft) {
KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock, KnittingMachineAdapter::DigitalRightSensor);
KnittingMachineAdapter kma(km, *m_arduinoMock);

// Simulate a KH-910 K carriage, starting outside of the bed
km.addCarriageMagnet(0, true);
km.putCarriageCenterInFrontOfNeedle(250);
// Simulate a KH-910 L carriage, starting outside of the bed
km.addCarriageMagnet(0, false);
km.putCarriageCenterInFrontOfNeedle(-50);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh910);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Move the carriage to the left until its magnet gets just past the right sensor
while (km.moveCarriageCenterTowardsNeedle(198)) {
// Move the carriage to the right until its magnet gets in front of the sensor
while (km.moveCarriageCenterTowardsNeedle(1)) {
GlobalKnitter::isr();
}

// position should have been reset
ASSERT_NEAR(m_Encoders.getPosition(),
END_RIGHT_MINUS_OFFSET[(uint8_t)MachineType::Kh910], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Knit);
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Lace);
}

TEST_F(E2ETest, EncodersDetectKCarriageOnTheRight_KH930) {
TEST_F(E2ETest, EncodersDetectGCarriageOnTheLeft) {
KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock);

// Simulate a KH-930 K carriage, starting outside of the bed
km.addCarriageMagnet(0, true);
km.putCarriageCenterInFrontOfNeedle(201);
// Simulate a KH-910 G carriage, starting outside of the bed
km.addGCarriageMagnets();

km.putCarriageCenterInFrontOfNeedle(-150);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh930);
GlobalKnitter::initMachine(MachineType::Kh910);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Move the carriage to the left until its magnet gets just past the right sensor
while (km.moveCarriageCenterTowardsNeedle(198)) {
// Move the carriage to the right until only the right magnet pair
// has passed the sensor
while (km.moveCarriageCenterTowardsNeedle(0)) {
GlobalKnitter::isr();
}

// position should have been reset
ASSERT_NEAR(m_Encoders.getPosition(),
END_RIGHT_MINUS_OFFSET[(uint8_t)MachineType::Kh910], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Knit);
}

TEST_F(E2ETest, EncodersDetectLCarriageOnTheLeft) {
KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Garter);
ASSERT_EQ(m_Encoders.getBeltShift(), BeltShift::Shifted);

// Simulate a KH-910 L carriage, starting outside of the bed
km.addCarriageMagnet(0, false);
km.putCarriageCenterInFrontOfNeedle(-50);
// Position should have been reset to END_LEFT_PLUS_OFFSET at the time the
// rightmost magnet passed the sensor, so now that the center is at needle 0,
// the position should be [position of the rightmost magnet] farther.
const int expectedPositionAtNeedle0 =
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910] + 12;

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh910);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);
ASSERT_NEAR(m_Encoders.getPosition(),
expectedPositionAtNeedle0, 1);

// Move the carriage to the right until its magnet gets in front of the sensor
while (km.moveCarriageCenterTowardsNeedle(1)) {
// Move the carriage to the right until the left magnet pair
// has passed the sensor as well
while (km.moveCarriageCenterTowardsNeedle(50)) {
GlobalKnitter::isr();
}

// position should have been reset
// Position should NOT have been reset when the left magnet pair passed the
// sensor, so now it should just be 50 needles to the right of previously
ASSERT_NEAR(m_Encoders.getPosition(),
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Lace);
expectedPositionAtNeedle0 + km.getCarriageCenterNeedle(), 1);
}

TEST_F(E2ETest, EncodersDetectGCarriageOnTheLeft) {
TEST_P(WithTargetNeedle, EncodersKeepTrackOfGCarriage_KH910) {
KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock);
KnittingMachineAdapter kma(km, *m_arduinoMock, KnittingMachineAdapter::DigitalRightSensor);

// Simulate a KH-910 G carriage, starting outside of the bed
km.addCarriageMagnet(12, false);
km.addCarriageMagnet(11, true);
km.addCarriageMagnet(-11, true);
km.addCarriageMagnet(-12, false);
km.addGCarriageMagnets();

km.putCarriageCenterInFrontOfNeedle(-150);
km.putCarriageCenterInFrontOfNeedle(-16);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh910);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Move the carriage to the right until the right magnet pair has passed the
// sensor
while (km.moveCarriageCenterTowardsNeedle(0)) {
// We will be returning to this needle.
const int referenceNeedle = 50;

// Position should be reset to END_LEFT_PLUS_OFFSET at the time the
// rightmost magnet passes the sensor, so we can add that plus the
// position of the rightmost magnet to get the expected position.
const int expectedPositionAtReferenceNeedle =
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910] + 12 + referenceNeedle;

// Move the carriage to the right until its magnets have passed the left
// sensor for initial detection
while (km.moveCarriageCenterTowardsNeedle(50)) {
GlobalKnitter::isr();
}

ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Garter);
// Confirm initial position detection
ASSERT_NEAR(m_Encoders.getPosition(), expectedPositionAtReferenceNeedle, 1);

// It's difficult to assign a specific meaning to either value of the
// "belt shift" at this point. For now we'll just lock down what the
// current code computes.
ASSERT_EQ(m_Encoders.getBeltShift(), BeltShift::Shifted);

// Position should have been reset at the time the rightmost magnet passed the
// sensor.
ASSERT_NEAR(m_Encoders.getPosition(),
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910] + 12, 1);
const int targetNeedle = GetParam();

// Move the carriage to the right until the left magnet pair has passed the
// sensor
while (km.moveCarriageCenterTowardsNeedle(50)) {
// Move the carriage to the target, then back to the reference
while (km.moveCarriageCenterTowardsNeedle(targetNeedle)) {
GlobalKnitter::isr();
}

while (km.moveCarriageCenterTowardsNeedle(referenceNeedle)) {
GlobalKnitter::isr();
}

// Position should have been reset at the time the rightmost magnet passed the
// sensor.
// Check that position and belt shift didn't get messed up
ASSERT_NEAR(m_Encoders.getPosition(),
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910] + 12 + 50, 1);
expectedPositionAtReferenceNeedle, 1);

if (targetNeedle == 190 || targetNeedle == -11) {
GTEST_SKIP() << "Known failure, investigate later";
}
ASSERT_EQ(m_Encoders.getBeltShift(), BeltShift::Shifted);
}


TEST_F(E2ETest, EncodersDetectKCarriageOnTheRight_KH910) {
KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock, KnittingMachineAdapter::DigitalRightSensor);

while (km.moveCarriageCenterTowardsNeedle(-50)) {
// Simulate a KH-910 K carriage, starting outside of the bed
km.addCarriageMagnet(0, true);
km.putCarriageCenterInFrontOfNeedle(250);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh910);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Move the carriage to the left until its magnet gets just past the right sensor
while (km.moveCarriageCenterTowardsNeedle(199)) {
GlobalKnitter::isr();
}

while (km.moveCarriageCenterTowardsNeedle(50)) {
// Position should have been reset to END_RIGHT_MINUS_OFFSET when the magnet
// passed the right sensor
ASSERT_NEAR(m_Encoders.getPosition(),
END_RIGHT_MINUS_OFFSET[(uint8_t)MachineType::Kh910], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Knit);
}

TEST_F(E2ETest, EncodersDetectKCarriageOnTheRight_KH930) {
GTEST_SKIP() << "Known failing (https://github.com/AllYarnsAreBeautiful/ayab-firmware/issues/175)";

KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock);

// Simulate a KH-930 K carriage, starting outside of the bed to the right
km.addCarriageMagnet(0, true);
km.putCarriageCenterInFrontOfNeedle(250);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh930);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Move the carriage to the left until its magnet gets just past the right sensor
while (km.moveCarriageCenterTowardsNeedle(198)) {
GlobalKnitter::isr();
}

ASSERT_EQ(km.getCarriageCenterNeedle(), 50);
// Position should have been reset to END_RIGHT_MINUS_OFFSET when the magnet
// passed the right sensor
ASSERT_NEAR(m_Encoders.getPosition(),
END_RIGHT_MINUS_OFFSET[(uint8_t)MachineType::Kh930], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Knit);
}

TEST_F(E2ETest, EncodersDetectLCarriageOnTheRight_KH930) {
GTEST_SKIP() << "Known failing (https://github.com/AllYarnsAreBeautiful/ayab-firmware/issues/176)";

KnittingMachine km;
KnittingMachineAdapter kma(km, *m_arduinoMock);

// Simulate a KH-930 L carriage, starting outside of the bed to the right
km.addCarriageMagnet(0, false);
km.putCarriageCenterInFrontOfNeedle(250);

// TODO trigger this from simulated serial communication
GlobalKnitter::initMachine(MachineType::Kh930);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::NoCarriage);

// Position should have been reset at the time the rightmost magnet passed the
// sensor.
// Move the carriage to the left until its magnet gets just past the right sensor
while (km.moveCarriageCenterTowardsNeedle(198)) {
GlobalKnitter::isr();
}

// Position should have been reset to END_RIGHT_MINUS_OFFSET when the magnet
// passed the right sensor
ASSERT_NEAR(m_Encoders.getPosition(),
END_LEFT_PLUS_OFFSET[(uint8_t)MachineType::Kh910] + 22 + 50, 1);
ASSERT_EQ(m_Encoders.getBeltShift(), BeltShift::Shifted);
END_RIGHT_MINUS_OFFSET[(uint8_t)MachineType::Kh930], 1);
ASSERT_EQ(m_Encoders.getCarriage(), Carriage::Lace);
}

int main(int argc, char *argv[]) {
::testing::InitGoogleMock(&argc, argv);
return RUN_ALL_TESTS();
}
}

0 comments on commit 226b99b

Please sign in to comment.