How to run two stepper motors together

Hi i was struggling to run two stepper motors perfectly together as the library would only let me run one step per motor at a time. So i went through the library code and made a sketch that will run two steppers together or singly or inverted from each other “turning in opposite directions”. It only supports 4 wire stepper motors but if you glance at the Stepper library code you can easily convert it to run 5+ wires.

Any way here is the code “it could do with some minor touch ups to make it more efficient” but work fine as it is.

int step_number = 0;
int direction = 0;
unsigned long last_step_time = 0;
unsigned long step_delay;
unsigned long steps = 200;
const byte stepperOnePin_1 = 4;
const byte stepperOnePin_2 = 5;
const byte stepperOnePin_3 = 6;
const byte stepperOnePin_4 = 7;
const byte stepperTwoPin_1 = 8;
const byte stepperTwoPin_2 = 9;
const byte stepperTwoPin_3 = 10;
const byte stepperTwoPin_4 = 11;
int speed = 30; // 30 rmp
unsigned long currentMillis;

void setup() {
  Serial.begin(115200);
  step_delay = ((60000UL / steps) / speed);
  Serial.print("step_delay ");
  Serial.println(step_delay);
}

void loop() {
  stepTwo(200, true, true, false); // steps, select motor 1, select motor 2, invert directions "turn opposite direction to each other" 
  delay(3000); // not needed, just added to slow down loop !
  stepTwo(-200, true, true, false); // now test the steppers in reverse 
  delay(3000); // not needed, just added to slow down loop !
}

void stepTwo(int step, bool selectMotorOne, bool selectMotorTwo, bool invert) {
  int steps_left = abs(step);
  if (step > 0) {
    direction = 1;
    Serial.print("steps_left ");
    Serial.println(steps_left);
  }
  else if (step < 0) {
    direction = 0;
    Serial.print("steps_right ");
    Serial.println(steps_left);
  }
  while (steps_left > 0) {
    currentMillis = millis();
    if (currentMillis - last_step_time >= step_delay) {
      //Serial.println("timer met");
      last_step_time = currentMillis;
      if (direction == 1)
      {
        step_number++;
        if (step_number == steps) {
          step_number = 0;
        }
      }
      else
      {
        if (step_number == 0) {
          step_number = steps;
        }
        step_number--;
      }
      // decrement the steps left:
      steps_left--;
      int thisStep = step_number % 4;
      //Serial.println(step_number % 4);
      if (!invert) {
        switch (thisStep) {
          case 0:  // 1010
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, HIGH);
              digitalWrite(stepperOnePin_2, LOW);
              digitalWrite(stepperOnePin_3, HIGH);
              digitalWrite(stepperOnePin_4, LOW);
            }
            if (selectMotorTwo) {// motor 2
              digitalWrite(stepperTwoPin_1, HIGH);
              digitalWrite(stepperTwoPin_2, LOW);
              digitalWrite(stepperTwoPin_3, HIGH);
              digitalWrite(stepperTwoPin_4, LOW);
            }
            break;
          case 1:  // 0110
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, LOW);
              digitalWrite(stepperOnePin_2, HIGH);
              digitalWrite(stepperOnePin_3, HIGH);
              digitalWrite(stepperOnePin_4, LOW);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, LOW);
              digitalWrite(stepperTwoPin_2, HIGH);
              digitalWrite(stepperTwoPin_3, HIGH);
              digitalWrite(stepperTwoPin_4, LOW);
            }
            break;
          case 2:  // 0101
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, LOW);
              digitalWrite(stepperOnePin_2, HIGH);
              digitalWrite(stepperOnePin_3, LOW);
              digitalWrite(stepperOnePin_4, HIGH);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, LOW);
              digitalWrite(stepperTwoPin_2, HIGH);
              digitalWrite(stepperTwoPin_3, LOW);
              digitalWrite(stepperTwoPin_4, HIGH);
            }
            break;
          case 3:  // 1001
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, HIGH);
              digitalWrite(stepperOnePin_2, LOW);
              digitalWrite(stepperOnePin_3, LOW);
              digitalWrite(stepperOnePin_4, HIGH);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, HIGH);
              digitalWrite(stepperTwoPin_2, LOW);
              digitalWrite(stepperTwoPin_3, LOW);
              digitalWrite(stepperTwoPin_4, HIGH);
            }
            break;
        }
      }
      else {
        Serial.println("inverted");
        switch (thisStep) {
          case 0: // 1001
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, HIGH);
              digitalWrite(stepperOnePin_2, LOW);
              digitalWrite(stepperOnePin_3, HIGH);
              digitalWrite(stepperOnePin_4, LOW);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, HIGH);
              digitalWrite(stepperTwoPin_2, LOW);
              digitalWrite(stepperTwoPin_3, LOW);
              digitalWrite(stepperTwoPin_4, HIGH);
            }
            break;
          case 1:  // 0101
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, LOW);
              digitalWrite(stepperOnePin_2, HIGH);
              digitalWrite(stepperOnePin_3, HIGH);
              digitalWrite(stepperOnePin_4, LOW);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, LOW);
              digitalWrite(stepperTwoPin_2, HIGH);
              digitalWrite(stepperTwoPin_3, LOW);
              digitalWrite(stepperTwoPin_4, HIGH);
            }
            break;
          case 2:  //0101
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, LOW);
              digitalWrite(stepperOnePin_2, HIGH);
              digitalWrite(stepperOnePin_3, LOW);
              digitalWrite(stepperOnePin_4, HIGH);
            }
            if (selectMotorTwo) {
              digitalWrite(stepperTwoPin_1, LOW);
              digitalWrite(stepperTwoPin_2, HIGH);
              digitalWrite(stepperTwoPin_3, HIGH);
              digitalWrite(stepperTwoPin_4, LOW);
            }
            break;
          case 3:  // 1001
            if (selectMotorOne) { // motor 1
              digitalWrite(stepperOnePin_1, HIGH);
              digitalWrite(stepperOnePin_2, LOW);
              digitalWrite(stepperOnePin_3, LOW);
              digitalWrite(stepperOnePin_4, HIGH);
            }
            if (selectMotorTwo) {// motor 2
              digitalWrite(stepperTwoPin_1, HIGH);
              digitalWrite(stepperTwoPin_2, LOW);
              digitalWrite(stepperTwoPin_3, HIGH);
              digitalWrite(stepperTwoPin_4, LOW);
            }
            break;
        }
      }
    }
  }
}

Thanks for sharing.

The standard Arduino Stepper library is very basic and, unless you make each motor move one step at a time it won't allow you to run two motors at the same time.

The AccelStepper library is a lot more capable and can act on several motors.

...R
Stepper Motor Basics
Simple Stepper Code