Belt Driven Position Control

Hi!

I"m working on a linear stage type of device. This linear stage is a two axis only. I’m using NEMA 17 + Big Easy driver. Previously I used simple method to digitalwrite(high - low), but would like to make use of Accelstepper library as it has acceleration and deceleration features (Avoids jerks and has better position control). I am unable to figure out the setMaxspeed. portion. All I’m trying to do at the moment is make the motor move one revolution for once in a second. Later, we plan to have a user input for how much the user wants to move the stage. For example, when +10 is inputed, the motor moves required steps/revs to move the platform 10 cm.

I’ve searched a lot to find tutorial and guides to use accelstepper, but have been unsuccessful. I’d like to move one rev, so it would be 6400 steps for my motor, but what does setMAxSpeed(3000) and setAcceleration(1000) mean??? When I upload this program on arduino, the motor just vibrates. I have no clue how to adjust setMaxSpeed. I have tried lots of different combinations.

Also, I’d appreciate your input on how to convert user input to number of steps required to move to desired position. Is there a guide, book, or tutorial to find this out??

Here’s the motor: http://www.canadarobotix.com/stepper-motor-68-oz-in-400steps-rev
400 Steps/rev

This is the code from Big Easy driver examples site.

#include <AccelStepper.h>

// Define a stepper and the pins it will use
AccelStepper stepper(1, 9, 8);

int pos = 3600;

void setup()
{  
  stepper.setMaxSpeed(3000);
  stepper.setAcceleration(1000);
}

void loop()
{
  if (stepper.distanceToGo() == 0)
  {
    delay(500);
    pos = -pos;
    stepper.moveTo(pos);
  }
  stepper.run();
}

Sincerely,
bluehawk

Have you looked on the AccelStepper website which has good documentation on all the methods.

setMaxSpeed is measured in steps per second setAcceleration is measured in steps per second per second

...R

Separate out all the concerns - first does your motor work when given step pulses explicitly at a slow rate (say 10/s)? Try both directions.

Once that's established move to the AccelStepper library. Read the documentation carefully before you write any code, and start with one of the provided examples as your basis.

At some point you have to determine the max speed and acceleration that your setup can tolerate - this is done by experiment. Once the limits are found you back off a bit and program those limits into your sketch.

You will need to avoid using busy-waiting or calling delay() in your sketch as AccelStepper requires a frequent call from loop() to the run() method to allow steps to happen.

I have looked at the documentation on AccelStepper. It didn’t help. It’s not explained how they used those 3000 and 1000 numbers.

This is the simple program that I wrote. I used three position switch to make the motor run.

int m1_neutral = 1; 
int m1_forward_button = 2; 
int m1_reverse_button = 3; 

// Initialize step and direction for motors 
int m1_dir_pin= 8; 
int m1_step_pin = 9; 

void setup() 
{ 
  pinMode(m1_forward_button, INPUT_PULLUP); 
  pinMode(m1_reverse_button, INPUT_PULLUP); 

  pinMode(m1_dir_pin, OUTPUT); 
  pinMode(m1_step_pin, OUTPUT); 
}

void loop()
{
  if (digitalRead(m1_forward_button) == LOW)
  {
    digitalWrite(m1_dir_pin, HIGH); 
  
  digitalWrite(m1_step_pin, HIGH); 
    delayMicroseconds(50); 
  
    digitalWrite(m1_step_pin, LOW); 
      delayMicroseconds(50);  
  }
  
   if (digitalRead(m1_reverse_button) == LOW)
   {
   digitalWrite(m1_dir_pin,LOW); 
   
   digitalWrite(m1_step_pin, HIGH); 
   delayMicroseconds(50); 
  
   digitalWrite(m1_step_pin, LOW); 
   delayMicroseconds(50); 
   }
   
}

I got the motor to move 1 rev using constant speed. I have no idea how the maxspeed and setspeed number works. I can’t find info on documentation either. I’d really like to know this.

#include <AccelStepper.h>

// Define a stepper and the pins it will use
AccelStepper stepper(1, 9, 8);

void setup()
{  
   stepper.setMaxSpeed(1000);
   stepper.setSpeed(1500);        
}
void loop()
{  
  stepper.moveTo(6400); 
  stepper.run();
}

bluehawk91: I have looked at the documentation on AccelStepper. It didn't help. It's not explained how they used those 3000 and 1000 numbers.

It is explained in the link in my earlier Post and I repeated the explanation in my Post.

...R

Okay, I thought there was much more than steps per second. My motor has 400 Steps (full)/rev and as I’m running big easy driver with default 1/16 stepping, it’s required 6400 steps to make a revolution. Suppose I want to make one revolution in one second, I should put setMaxSpeed(6400) (ignoring the acceleration value). Sorry for asking stupid question.

#include <AccelStepper.h>

// Define a stepper and the pins it will use
AccelStepper stepper(1, 9, 8);

int pos = 6400;
int revdistance = 60; // moves 60mm in one revolution 
//int data;
void setup()
{  
  Serial.begin(9600);
  stepper.setMaxSpeed(6400);
  stepper.setAcceleration(2500);
}

if (Serial.available() > 0)
{
data = Serial.read(); //Read byte of data
Serial.print(data); //Print byte of data
if (data =='1')
{ 
stepper.moveTo(pos);
stepper.run();
}
}
}

bluehawk91: Suppose I want to make one revolution in one second, I should put setMaxSpeed(6400) (ignoring the acceleration value).

As far as I know, yes.

But wouldn't it be far quicker and more satisfying just to try it out and see what happens?

I love learning-by-doing with my Arduinos.

...R

I have tried many many many times. Lots of different values, but can’t seem to reach decent speed. I calculated maximum speed using this calculator and converted into steps per second (5013 steps/second). but it is still slow whereas the simple digitalwrite high and low seem to be at decent speed. Accelstepper is taking about 4/5 seconds to complete a revolution (for 6400 Maxspeed).

I have one more question regarding the position control. What would be the best way to input values (keypad or keyboard)?
I’m also trying to read values from keyboard presently and making it rotate if right value is found.
Next, I’d like to input 10F, 10R, 5U, 5D, so it moves respective position from base.
F = forward
R = Reverse
U= Up
D= Down.

Which would be the best way to recognize letters and numbers together?

#include <AccelStepper.h>

// Define a stepper and the pins it will use
AccelStepper stepper(1, 9, 8);

int pos = 6400;
char key; 

void setup()
{  
  Serial.begin(9600);
  stepper.setMaxSpeed(6400);
  stepper.setAcceleration(2000);
}

void loop()
{
  if (Serial.available() > 0)
{
  key  = Serial.read(); //Read byte of data
  if (stepper.distanceToGo() == 0)
  {
    if (key =='1');
    {
    delay(500);
    pos = -pos;
    stepper.moveTo(pos);
    }
  }
}
  stepper.run();
}

I’m intrigued that AccelStepper is not making the motors move at the expected speed. Are you sure they can go at that speed?
Have you tried a short sketch using AccelStepper without acceleration?
Have you allowed enough total steps for all the acceleration to happen?

Edit to add …
I think you need to specify the DRIVER option when you initialize AccelStepper so it knows you are using a stepper motor driver board.

If you want to send multi-character data then you need to collect all of the data before you decide what do with it. There are as many solutions as there are programmers. A simple strategy would be always to send (say) 3 characters. The the Arduino can check if (Serial.available >= 3) {. It would also simplify matters if the first character is always a letter (F or R) and the other 2 are digits as that will make parsing the data easier.

This demo may help to shed some light on the problem. This one is a little more complex, but more reliable.

…R

The AccelStepper library has comments, if you read them it will explain its limitations:

/// The fastest motor speed that can be reliably supported is about 4000 steps per /// second at a clock frequency of 16 MHz on Arduino such as Uno etc.

Unless you have a good reason, don't use the 1/16 stepping. You need too many pulses per second and it consumes more power.

Use single steps, you only need 400 pulses per second.