Controlling 2 Stepper Motors simultaneously (AccelStepper Library)

10,619 views
Skip to first unread message

faeve

unread,
Mar 14, 2012, 3:38:16 PM3/14/12
to accelstepper
Hi everyone,

and thank you for your time and help on this.
I am a it of a newbie with Processing and Arduino; in my project
Processing finds an 'x' amount of words reading google news and then
sends those ints to Arduino, which in turn uses them to set new
positions for 2 stepper motors.
I am using the AccelStepper library to drive the motors.
It is working pretty decently at the moment, only thing is that I
cannot figure out how to control the two steppers simultaneously; so
far one moves, then stops, then the other kicks in. Following some
research done on this forum I had a look at the multistepper example
which comes with the library, but still can't find a way to make them
move at the same time.
Any help would be enourmously appreciated.

Here is my code in Arduino

// Modified from Blocking.pde
// -*- mode: C++ -*-
//
// Shows how to use the blocking call runToNewPosition
// Which sets a new target position and then waits until the stepper
has
// achieved it.
//
// Copyright (C) 2009 Mike McCauley
// $Id: Blocking.pde,v 1.1 2011/01/05 01:51:01 mikem Exp mikem $

#include <AccelStepper.h>

// Define a stepper and the pins it will use
AccelStepper stepper1 (4,2,3,4,5); // Defaults to 4 pins on 2, 3, 4, 5
AccelStepper stepper2 (4,9,10,11,12); // Defaults to 4 pins on 9, 10,
11, 12

//Motor variables
int m1val = 0; //variable controlling position of motor 1
int oldm1val = 0; // old variable controlling position of motor 1
int m3val = 0; //variable controlling position of motor 3
int oldm3val = 0; // old variable controlling position of motor 3

boolean startLine = true; // controls that all motors are reset to '0'
at the beginning,
// this function happens at the end of the
code

// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
//Reset all Motors by pushing a button
const int buttonPin01 = 8; // push button connected to pin 8
int buttonState01 = 0; // variable for reading the pushbutton status

// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

char buff[]= "0000000000"; // this is for the data sent from
Processing

void setup() {
Serial.begin(9600);

stepper1.setMaxSpeed(400.0);
stepper1.setAcceleration(100.0);
stepper2.setMaxSpeed(400.0);
stepper2.setAcceleration(100.0);
pinMode(buttonPin01, INPUT); // push button set to input
}

void loop() {

buttonState01 = digitalRead(buttonPin01); // reads value of the push
button 01

if (buttonState01 == LOW) { //check if button was pressed
delay(10); // waits for 10 milliseconds
Serial.println("RESET MOTORS");
resetMotors();
}

if (startLine == false){
resetMotors();
startLine = true;
}

while (Serial.available()>0) { //It reads the new data sent by
Processing every 10 seconds
for (int i=0; i<10; i++) {
buff=buff[i+1];
}
buff[10]=Serial.read(); //if it recognises one array of chars
ending with P it assigns the 9th value of the array to m1val
if (buff[10]=='P') {
m1val=int(buff[9]);
}

if (buff[10]=='R') {
m3val=int(buff[9]); //same for R and m3val
}

}

if (m1val != oldm1val){ //if the values are different from the ones
previously sent, it then moves the second stepper to a value specified
by m1val
stepper2.enableOutputs();
stepper2.runToNewPosition(m1val*50);
}
else {
stepper2.disableOutputs(); //if nothing happens it disables the
outputs to save energy
}

if (m3val!= oldm3val){ //same for the other stepper motor
stepper1.enableOutputs();
stepper1.runToNewPosition(m3val*50);
}
else {
stepper1.disableOutputs(); //if nothing happens it disables the
outputs to save energy
}



oldm3val = m3val; // stores the value of m3val
old1val = m1val; //stores the value of m1val
}

void resetMotors (){
stepper1.runToNewPosition(0);
stepper1.disableOutputs();
stepper2.runToNewPosition(0);
stepper2.disableOutputs();
}

-------------------------------------------------------------------------------------------------------------------



Please let me know if you need the code from processing

Thanks

Faeve
Message has been deleted

faeve

unread,
Mar 14, 2012, 5:10:01 PM3/14/12
to accelstepper
I have forgot to add that I have read the documentation and found
that
the runToNewPosition shouldn't be used in loops.
It appeared to be the best approach for my project until I realised
it
wasn't working... my bad ....

I guess the question is:
Can I get the 2 steppers run at the same time (as in the Multistepper
example) but in the void loop () function, in a way that doesn't block
the code?
And can I assign a variable to the position of the Motors so that they
can be positioned differently over the course of the code?

Many thanks for your help!

Faeve

Brian Schmalz

unread,
Mar 14, 2012, 5:16:30 PM3/14/12
to accelstepper
Sure. See the last example on my examples page:
http://www.schmalzhaus.com/EasyDriver/Examples/EasyDriverExamples.html

*Brian

faeve

unread,
Mar 14, 2012, 5:25:13 PM3/14/12
to accelstepper
Hi Brian,

thanks for the link, it looks very interesting indeed.
Would I be able to run up to 5 stepper motors that way?
I guess I would need 5 EasyDriver interfaces, am I right?

Are you aware of any other way this could be achieved without the ED?
I should mention that I am using two Hbridges SN754410 to drive two
ASTROSYN 1 MY7001 STEPPER MOTOR, 14, 20MM
These motors are bipolar and have 4 pins.
I will have to move on to control 5 in a bit, hence I thought about
buying an Arduino Mega

Thanks!

Faeve

faeve

unread,
Mar 14, 2012, 5:42:00 PM3/14/12
to accelstepper
Hi Brian,

no probs, I have found the solution by modifying the way the motors
were activated.
The code now looks pretty much like this:

stepper2.moveTo(m2val*50); //where m2val and m1val are variables I
receive from processing
stepper2.run();
stepper1.moveTo(m1val*50);
stepper1.run();

I am loving this library

Best

Faeve

On Mar 14, 9:16 pm, Brian Schmalz <brian.schm...@logicpd.com> wrote:

Brian Schmalz

unread,
Mar 14, 2012, 6:08:26 PM3/14/12
to accelstepper
No reason you need to use EDs at all. You can use your h-bridges just fine. You just have to configure the stepper object a bit differently when you first create it. But that's one of the nice things about the libarary - all functionality is available no matter how you drive your stepper. So yes. And yes, you have to have enough pins!

Now, your max step speed will be pretty slow on an Arduino. But with 5 steppers running at the same time a chipKIT will have no problem running really fast.

Brian Schmalz

unread,
Mar 14, 2012, 6:08:43 PM3/14/12
to accelstepper
Completely agreed. Accelstepper is really awesome. I love it too!

opkach

unread,
Dec 5, 2012, 1:52:33 PM12/5/12
to accels...@googlegroups.com
Is it possible to post the Processing code? I have been having a hard time getting coordinates from Processing to Arduino. Essentially I am trying to plot coordinates accurately using this library but I am getting confused how to implement it properly. I will thumb through this exam more this evening, will be back with some questions soon!

Tavis Hord

unread,
Jun 19, 2014, 10:23:12 PM6/19/14
to accels...@googlegroups.com
I want to run 2 steppers simultaneously as well but wouldn't one be slightly slower because you cal the run function after the first motor?

stepper1.moveTo(length);
stepper2.moveTo(-length);
stepper1.run();
stepper2.run();

Tavis Hord

unread,
Jun 20, 2014, 12:18:33 AM6/20/14
to accels...@googlegroups.com
To be more clear, I don't mean slower it mean that they won't truly be simultaneous, won't they be alternating? Stepper1 will step and then stepper2 will step after? I'm working on a coreXY system where both motors need to be truly stepping at the exact same time.

Sandy Noble

unread,
Jun 20, 2014, 8:08:03 AM6/20/14
to accels...@googlegroups.com
You'e correct, without some kind of hardware buffering, accelstepper (or almost any control software) will never produce simultaneous step signals, this is literally because single-threaded software just can't do two things at once.

So your step signals might be a millisecond apart. Remember that any physical system reacts more slowly than the software, by an order of magnitude, so the portion of time where the motors are moving will usually be proportionally much bigger than the portion of time where only one is moving. The motor takes 20ms to start to move.

Also bear in mind that there is nothing special about CoreXY in the sense of requiring greater synchronisation, versus any other system of positioning. All consumer level 3d printers use this interleaved method of movement with no ill effects. I'm not saying it isn't worth knowing about, I'm just suggesting that you don't let this feature get in the way of your development. I don't think you will find any CNC or motor control type software that does what you want - it is a hardware feature really.


sn


On 20 June 2014 05:18, Tavis Hord <tavis...@gmail.com> wrote:
To be more clear, I don't mean slower it mean that they won't truly be simultaneous, won't they be alternating? Stepper1 will step and then stepper2 will step after? I'm working on a coreXY system where both motors need to be truly stepping at the exact same time.

--
You received this message because you are subscribed to the Google Groups "accelstepper" group.
To unsubscribe from this group and stop receiving emails from it, send an email to accelstepper...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Tavis Hord

unread,
Jun 21, 2014, 12:09:26 AM6/21/14
to accels...@googlegroups.com
Yeah, makes sense. I thought about driving both motors from a single pwm pulse but it doesn't seem to make much difference. I get a little movement on y while sweeping along x either way so it must be the belts. I'm doing a line printer type of project so x needs to be pretty solid and not moving only at all I'm thinking. Maybe this setup is not the best solution for this methond of printing. I need to work more like an ink jet printer.

Sandy Noble

unread,
Jun 21, 2014, 6:28:19 AM6/21/14
to accels...@googlegroups.com
Smaller, faster steps could be a solution too. It isn't really any different than drawing anything except a dead vertical or horizontal line in a regular plotting kind of machine. 

Think carefully about whether accelstepper is the right choice here though - the acceleration curve for each motor will work out identical in the case of where both motors are moving the exact same speed and same distance (eg horizontal and vertical), but for anything else, the acceleration curve will cause a swerve at the beginning or end of your lines.

good luck :)

sn


On 21 June 2014 05:09, Tavis Hord <tavis...@gmail.com> wrote:
Yeah, makes sense. I thought about driving both motors from a single pwm pulse but it doesn't seem to make much difference. I get a little movement on y while sweeping along x either way so it must be the belts. I'm doing a line printer type of project so x needs to be pretty solid and not moving only at all I'm thinking. Maybe this setup is not the best solution for this methond of printing.  I need to work more like an ink jet printer.
--
You received this message because you are subscribed to the Google Groups "accelstepper" group.
To unsubscribe from this group and stop receiving emails from it, send an email to accelstepper...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.



--
Sandy Noble

Yamin Hameed

unread,
Feb 18, 2017, 10:38:15 AM2/18/17
to accelstepper, flant...@gmail.com
Hi Feve, would it be possible to share the final arduino code. I'm working on a smiliar project too but I used the default stepper library and I can't get the steppers to move simultaneously. Just read about the Accelstepper library while doing some research. I have a processing sketch which send X and Y co ordinates to arduino which in turn moves the X and Y steppers.
Thanks

Sandy Noble

unread,
Feb 19, 2017, 4:35:27 AM2/19/17
to accels...@googlegroups.com
Look up the example sketches in Accelstepper to see how simultaneous movement works. Roughly speaking:

set target position for X motor
set target position for Y motor

while X motor and Y motor still have distance to go,
    X motor run()
    Y motor run()




--
You received this message because you are subscribed to the Google Groups "accelstepper" group.
To unsubscribe from this group and stop receiving emails from it, send an email to accelstepper+unsubscribe@googlegroups.com.

For more options, visit https://groups.google.com/d/optout.



--
Sandy Noble
Reply all
Reply to author
Forward
0 new messages