Order of Stepper Pins in Stepper Library

I'm learning how to use a 28BYJ-48 stepper motor with the ULN2003AN driver. After doing a lot reading on how steppers work and the specific sequences in which the coils must be powered on and off in order to operate, I still am confused about how to use the stepper library which comes with the arduino.

For full step instead of half step, the motor wants power to the wires in the following order: BP - PY - YO - OB. I have those pins connects to arduino, via the driver, as follows: B=3, P=4, Y=5, O=6. So the pins need to be powered in the order: 34 - 45 - 56 - 63. The included library (Stepper.h, Stepper.cpp) requires declaring a stepper with pins in the order 3, 5, 4, 6.

The library defines the Stepper using this code:

Stepper(int number_of_steps, int motor_pin_1, int motor_pin_2,
                                      int motor_pin_3, int motor_pin_4)

Then to actually turn the motor, it uses the following code:

switch (thisStep) {
      case 0:  // 1010
        digitalWrite(motor_pin_1, HIGH);
        digitalWrite(motor_pin_2, LOW);
        digitalWrite(motor_pin_3, HIGH);
        digitalWrite(motor_pin_4, LOW);
      break;
      case 1:  // 0110
        digitalWrite(motor_pin_1, LOW);
        digitalWrite(motor_pin_2, HIGH);
        digitalWrite(motor_pin_3, HIGH);
        digitalWrite(motor_pin_4, LOW);
      break;
      case 2:  //0101
        digitalWrite(motor_pin_1, LOW);
        digitalWrite(motor_pin_2, HIGH);
        digitalWrite(motor_pin_3, LOW);
        digitalWrite(motor_pin_4, HIGH);
      break;
      case 3:  //1001
        digitalWrite(motor_pin_1, HIGH);
        digitalWrite(motor_pin_2, LOW);
        digitalWrite(motor_pin_3, LOW);
        digitalWrite(motor_pin_4, HIGH);
      break;
    }

I don't understand why it sets pin1 and pin3 to HIGH at the first step and not pin1 and pin2. As far as I can tell, this is what causes the need to call the function with
Stepper(num_steps, 3, 5, 4, 6)
instead of
Stepper(num_steps, 3, 4, 5, 6)

Is there an advantage to doing it this way? I would write it to be

switch (thisStep) {
      case 0:  // 1100
        digitalWrite(motor_pin_1, HIGH);
        digitalWrite(motor_pin_2, HIGH);
        digitalWrite(motor_pin_3, LOW);
        digitalWrite(motor_pin_4, LOW);
      break;
      case 1:  // 0110
        digitalWrite(motor_pin_1, LOW);
        digitalWrite(motor_pin_2, HIGH);
        digitalWrite(motor_pin_3, HIGH);
        digitalWrite(motor_pin_4, LOW);
      break;
      case 2:  // 0011
        digitalWrite(motor_pin_1, LOW);
        digitalWrite(motor_pin_2, LOW);
        digitalWrite(motor_pin_3, HIGH);
        digitalWrite(motor_pin_4, HIGH);
      break;
      case 3:  // 1001
        digitalWrite(motor_pin_1, HIGH);
        digitalWrite(motor_pin_2, LOW);
        digitalWrite(motor_pin_3, LOW);
        digitalWrite(motor_pin_4, HIGH);
      break;
    }

This would allow the pins to be entered as
Stepper(num_steps, 3, 4, 5, 6)

But then I'm new to electronics and programing with controllers, so maybe I am not aware of something here?

Did You read the topic "Stepper basics"? Try that!

Are the pin numbers not arbitrary? I think you can assign motor phases to almost any pins you like.

Yeah I can connect the wires to whichever pins I want, but the order they are connected is always different than the order they are called in the Stepper function. The middle two are always swapped. I just used 3, 4, 5, and 6 as an example.

Post the schematics.
My guess is that pin 1 and 2 controls one coil and 3 and 4 handles the other coil. Setting both pins for the same coil to the same logical state gives an "Off" to the coil. Setting one pin On and one pin Off creates current in that coil.

I think the internal details of the library, are not important in this case. Only, clear documentation about which phases to connect to which pins, and the order in which to declare them in the program.

It has to do with the order the pins are wired to the coils in the motor.
28BYJ-48-Pinout-Wirings
If they are mismatched, the current doesn't flow correctly and the motor won't spin.

I didn't get any results when I searched for "stepper" in topics.

Mine looks similar to that except the Blue and Pink are switched and the Orange and Yellow are switched. In terms of them coming out of the motor. They connect into the driver in the order BPYOR. This is a diagram I have the the situation with it connecting to the driver:


The table shows the Half step mode instead of full step, but the order should be the same for full step, right?

I have 16 motors wired up to a Mega.
Mine are also blue-pink-red-orange-yellow coming out of the motor.
They plug onto the ULN2003 board as red-blue-pink-yellow-orange.
I did have a small batch of motors (out of 96) that rotated opposite direction from all the rest, and I depinned the ULN2003 connector end and replugged in the wires to turn the same direction as the rest, the one I am looking at might be one of them.
IN1-2-3-4 connect to 4 adjacent pins, and I have a note in my code that Stepper pin call out is important

Stepper stepper0(STEPS, 5, 3, 4, 2); //create the stepper0  <<< Order here is important
Stepper stepper1(STEPS, 6, 8, 7, 9); //create the stepper1  <<< Order here is important
Stepper stepper2(STEPS, 10, 12, 11, 13); //create the stepper2  <<< Order here is important
Stepper stepper3(STEPS, 17, 15, 16, 14); //create the stepper3  <<< Order here is important
Stepper stepper4(STEPS, 21, 19, 20, 18); //create the stepper4  <<< Order here is important
Stepper stepper5(STEPS, 22, 24, 23, 25); //create the stepper5  <<< Order here is important
Stepper stepper6(STEPS, 29, 27, 28, 26); //create the stepper5  <<< Order here is important

Stepper stepper7(STEPS, 33, 31, 32, 30); //create the stepper7  <<< Order here is important
Stepper stepper8(STEPS, 37, 35, 36, 34); //create the stepper8  <<< Order here is important
Stepper stepper9(STEPS, 41, 39, 40, 38); //create the stepper9  <<< Order here is important
Stepper stepper10(STEPS, 45, 43, 44, 42); //create the stepper10  <<< Order here is important
Stepper stepper11(STEPS, 49, 47, 48, 46); //create the stepper11  <<< Order here is important
Stepper stepper12(STEPS, 53, 51, 52, 50); //create the stepper12  <<< Order here is important
Stepper stepper13(STEPS, 57, 55, 56, 54); //create the stepper13  <<< Order here is important
Stepper stepper14(STEPS, 61, 59, 60, 58); //create the stepper14  <<< Order here is important
Stepper stepper15(STEPS, 65, 63, 64, 62); //create the stepper15  <<< Order here is important
Stepper stepper16(STEPS, 69, 67, 68, 66); //create the stepper16  <<< Order here is important

Figure out what yours is, and stick to it.

I still don't get why it's in that order in the stepper program, but I tried connecting the stepper and driver to the arduino and powering it on. I think maybe I have a bad driver board? The ULN2003 board has 4 little LEDs on it that appear to correspond to the four coil wires. I also connected 4 LEDs between the arduino and the driver board to also indicate those wires. I'm having this issue where all LEDs behave as expected when the motor IS NOT connected to the board. Once the motor is connected, the LEDs between the board and the arduino continue to operate as expected but the LEDs on the driver board turn off completely. I am using an external power supply that came with my kit to power the motor, not the arduino. I've included a photo of my setup.

With no motor, all lights are working. With motor attached, board lights turn off and the light on the power supply turns off.

If any two wires are removed from the motor connection (except the red) then a pair of lights on the board will function, but the others remain off. Is there a problem with my motor or board?

The order is so the current pulses in the coils can push/pull the motor core in the correct order to allow it to spin.

As you can see from this code, four steps can be used to make it simpler.
The 28BYJ48 is geared, so using 8 steps is really over kill unless you want to make reeeeeaaally small movements. With just 4 steps, the motor can be run at nearly 20 Hz.

        //if (upDown == 1) { // Extend (unwind) looking at shaft
        case 1:
          switch (stepNumber[0]) {         // 0110, 1100, 1001, 0011
            case 0:
              digitalWriteFast (54, 0); // 0110
              digitalWriteFast (55, 1);
              digitalWriteFast (56, 1);
              digitalWriteFast (57, 0);
              stepNumber[0] = 1;
              break;
            case 1:
              digitalWriteFast (54, 1); // 1100
              digitalWriteFast (55, 1);
              digitalWriteFast (56, 0);
              digitalWriteFast (57, 0);
              stepNumber[0] = 2;
              break;
            case 2:
              digitalWriteFast (54, 1); // 1001
              digitalWriteFast (55, 0);
              digitalWriteFast (56, 0);
              digitalWriteFast (57, 1);
              stepNumber[0] = 3;
              break;
            case 3:
              digitalWriteFast (54, 0); // 0011
              digitalWriteFast (55, 0);
              digitalWriteFast (56, 1);
              digitalWriteFast (57, 1);
              stepNumber[0] = 0;
              break;
          }
          break; // upDown 1
        case 2:
          //if (upDown == 2) { // Retract (wind up) looking at shaft
          switch (stepNumber[0]) {         // 0011, 1001, 1100, 0110
            case 0:
              digitalWriteFast (54, 0); // 0011
              digitalWriteFast (55, 0);
              digitalWriteFast (56, 1);
              digitalWriteFast (57, 1);
              stepNumber[0] = 1;
              break;
            case 1:
              digitalWriteFast (54, 1); // 1001
              digitalWriteFast (55, 0);
              digitalWriteFast (56, 0);
              digitalWriteFast (57, 1);
              stepNumber[0] = 2;
              break;
            case 2:
              digitalWriteFast (54, 1); // 1100
              digitalWriteFast (55, 1);
              digitalWriteFast (56, 0);
              digitalWriteFast (57, 0);
              stepNumber[0] = 3;
              break;
            case 3:
              digitalWriteFast (54, 0); // 0110
              digitalWriteFast (55, 1);
              digitalWriteFast (56, 1);
              digitalWriteFast (57, 0);
              stepNumber[0] = 0;
              break;
          }
          break; // upDown 2

Because the stepper program is not only for your stepper. If you want to drive a bipolar stepper with a double H-bridge, the order is different.Also if you use a different unipolar stepper it may be different. You cannot make it suitable for all.
What is really the problem?

Oh okay. Yeah that makes sense. I knew these was something I was overlooking. None of the online tutorials I looked through mentioned the WHY beyond "so that they turn on/off correctly." But knowing that the code is supposed to work for other types of motors which would require different on/off sequences makes sense. Thanks.

No, we are talking about a 5-wire motor, there are 4 coils sharing a common, so there's no easy way to figure out the correct sequence (if undocumented) other than trial and error - 8 out of the 24 possible wire permutations will work (4 go one way, 4 the other). 16 possibilities won't work.

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.