Hi all!
Here is a little update, so far I have been able to control the 3 motors with 2 optical endstops as I wanted to (ie motX rorating continuously while MotY and MotZ alternate depending of the endstops states).
Here are the different states of the system:
ID is quite straightforward: MotorY ON = 1000, endstopY ON = 100, MotorZ ON = 10 & endstopZ ON = 1. Then you sum it.
I had to introduce 2 variables isMotorYstarting & isMotorZstarting so that in certain states one can decide whether Motor shall continue running or stop (since as I use endstops for rotation, you have to "push through" the endstop activation at startup).
Here is the cycle:
Here is the code:
#include <MobaTools.h>
const int stepsPerRevolution = 200; // number of steps per revolution of the steppers used
MoToStepper MotorX(stepsPerRevolution, STEPDIR); // create one bipolar stepper using stepper mode, since motor is connected via DRV8825, with 200 steps per revolution
MoToStepper MotorY(stepsPerRevolution, STEPDIR); // Idem
MoToStepper MotorZ(stepsPerRevolution, STEPDIR); // Idem
#define limitSwitchY 10 // To later on allocate pin 10 to the limit switch associated with MotorY
#define limitSwitchZ 9 // To later on allocate pin 9 to the limit switch associated with MotorZ (did this on pin 9 cause pin 11 = Z on cnc shield is not working)
unsigned int state; // Variable to characterize the state of the system depending on the state of its different components
unsigned int isMotorYstarting = 1; // Variable to distinguish if we're in the starting phase of MotorY or not
unsigned int isMotorZstarting = 1; // Variable to distinguish if we're in the starting phase of MotorZ or not
void setup() {
// ----Constants----
MotorX.attach(2,5); // STEPpin, DIRpin arccording to CNC shield routing
MotorY.attach(3,6); // Idem
MotorZ.attach(4,7); // Idem
MotorX.setSpeed(60); // Set rotation speed of motor X to 6 rpm
MotorX.setRampLen(10); // Set 10 steps acceleration ramp for MotorX
MotorY.setSpeed(200); // Set rotation speed of motor Y to 20 rpm
MotorY.setRampLen(20); // Set 20 steps acceleration ramp for MotorY
MotorZ.setSpeed(200); // Set rotation speed of motor Z to 20 rpm
MotorZ.setRampLen(20); // Set 20 steps acceleration ramp for MotorZ
pinMode(limitSwitchY, INPUT); // Set input sense for limitSwitchY (pin 10)
pinMode(limitSwitchZ, INPUT); // Set input sense for limitSwitchZ (pin 9)
// ----Initialization actions----
MotorY.rotate(1); // This instruction and the 2 ones below aim to home motorY. MotorY starts to rotate
while (digitalRead(limitSwitchY) == LOW) {} // Nothing happens whils the limitSwitchY is not activated (assuming value = HIGH while activated)
MotorY.stop(); // Then when we quit the while loop, meaning limitSwitchY is activated, MotorY is stopped
MotorZ.rotate(1); // Idem than the 3 instructions above but on MotorZ
while (digitalRead(limitSwitchZ) == LOW) {} // Idem
MotorZ.stop(); // Idem
MotorX.rotate(1); // MotorX starts to rotate forward continuously to initiate the casefeeding action
}
void loop() {
state = 0;
if (MotorY.moving()) {state += 1000;}
if (digitalRead(limitSwitchY) == HIGH) {state += 100;}
if (MotorZ.moving()) {state += 10;}
if (digitalRead(limitSwitchZ) == HIGH) {state += 1;}
switch (state) {
case 0: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 1: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 10: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 11: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 100: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 101: //MotorY is stopped and homed & Motor Z is stopped and homed, it means we are at the start of the cycle and shall start
MotorY.rotate(1);
isMotorYstarting = 1;
isMotorZstarting = 1;
break;
case 110: // Case 110 = MotorY stopped and homed, and MotorZ is running out of the endstop, action shall continue
if(isMotorZstarting == 1){isMotorZstarting = 0;}
break;
case 111: // Case 111 = MotorY is stopped and homed & MotorZ runs and reaches the reference position so that endstopZ is activated, thus MotorZ shall be stopped, and MotorY started
if (isMotorZstarting == 0){
MotorZ.stop();
MotorY.rotate(1);
isMotorZstarting = 1;
}
break;
case 1000: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 1001: // Case 1001 = MotorZ stopped and homed, and MotorY is running out of the endstop, action shall continue
if (isMotorYstarting == 1){isMotorYstarting = 0;}
break;
case 1010: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 1011: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 1100: // Case 1100 = MotorZ is stopped and homed & MotorY runs and reaches the reference position so that endstopZ is activated, thus MotorY shall be stopped, and MotorZ started
break;
case 1101: // Not a valid case, kept to be able to report errors later on when lcd will be on
if (isMotorYstarting == 0){
MotorY.stop();
MotorZ.rotate(1);
isMotorYstarting = 1;
}
break;
case 1110: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
case 1111: // Not a valid case, kept to be able to report errors later on when lcd will be on
break;
}
}
Now next steps are:
- Troubleshooting my CNC shield: I ordered a second CNC shield in v3.51 to elecrow to replace the v3.0 I have that has a broken power supply connector (I will fix it later). It turns out the elecrow one have an issue with the endstop Z pins, that are not funtional (no electrical continuity with arduino pin 11). I emailed customer service about that.
- Integrate the proximity sensors to be able to trigger start / stops of MotorX
- Integrate the LCD screen and the button for feedback and basic pause / stop / resume commands implementation
If you have any question or feedback regarding all of this, please feel free to share, that's why I'm posting this!