Timing interference when a serial is called upon and a stepper motor

Hello

For a project i'm using 2 buttons to move a stepper motor in two directions at a set speed. I want to keep track at how many steps have been taken. I know that every time that my loop completes, 1 step has been taken. So I want to use a variable that increases in value when the loop completes. And I would want to use a serial to read out this number. From the moment I integrate a serial.begin(x) my stepper motor doesn't do anything anymore. I think there is some interference with the timing of my stepper motor and the serial.
How do I make sure this doesn't interfere with each other.
Thanks for the help.

void loop() {
  
  int pressedL = digitalRead(linksom);
  if(pressedL == HIGH)
  {
      digitalWrite(dirPin, HIGH);
      digitalWrite(stepPin,HIGH); 
      delayMicroseconds(500);    // by changing this time delay between the steps we can change the rotation speed
      digitalWrite(stepPin,LOW); 
      delayMicroseconds(500);
      
  
      
    }
  int pressedR = digitalRead(rechtsom);
  if(pressedR == HIGH)
  {
      digitalWrite(dirPin, LOW);
      digitalWrite(stepPin,HIGH); 
      delayMicroseconds(500);    // by changing this time delay between the steps we can change the rotation speed
      digitalWrite(stepPin,LOW); 
      delayMicroseconds(500); 
    }
  }
type or paste code here

The problem must be in the code you did not post.

Post you entire sketch, or a reduced sketch based on your entire sketch that has the same issue.

a7

So this is the entire code:
In the serial monitor I get to see my variable. That part works. So the loop is being run trough. Only my stepper motor doesn't run anymore. If I remove the Serial part. It works fine.

const int stepPin = 0;
const int dirPin = 4;
const int linksom = 3;
const int rechtsom = 6;
int loopCounter = 0; // Variabele om het aantal keer dat de loop is doorlopen bij te houden

void setup() {
  pinMode(stepPin, OUTPUT); 
  pinMode(dirPin, OUTPUT);
  pinMode(linksom, INPUT);
  pinMode(rechtsom, INPUT);

  Serial.begin(9600); // Begin seriële communicatie met baudrate 9600
}

void loop() {
   // Verhoog de loopCounter elke keer als de loop wordt doorlopen

  int pressedL = digitalRead(linksom);
  if (pressedL == HIGH) {
    digitalWrite(dirPin, HIGH);
    digitalWrite(stepPin, HIGH); 
    delayMicroseconds(500);    // door dit tijdsinterval tussen de stappen te veranderen, kunnen we de rotatiesnelheid wijzigen
    digitalWrite(stepPin, LOW); 
    delayMicroseconds(500);
    loopCounter++;
    Serial.println(loopCounter);
  }

  int pressedR = digitalRead(rechtsom);
  if (pressedR == HIGH) {
    digitalWrite(dirPin, LOW);
    digitalWrite(stepPin, HIGH); 
    delayMicroseconds(500);    // door dit tijdsinterval tussen de stappen te veranderen, kunnen we de rotatiesnelheid wijzigen
    digitalWrite(stepPin, LOW); 
    delayMicroseconds(500);
    loopCounter++;
    Serial.println(loopCounter);
  }
}

Serial uses pins 0 and 1, so you'll have to move your step output.

Thank you, that seemed to be the problem. However my speed of my motor seemes to be depending on the baudrate I chose. Any way I can avoid this?

const int stepPin = 2;
const int dirPin = 4;
const int linksom = 3;
const int rechtsom = 6;
const int reset = 9;
int loopCounter = 0; // Variabele om het aantal keer dat de loop is doorlopen bij te houden

void setup() {
  pinMode(stepPin, OUTPUT); 
  pinMode(dirPin, OUTPUT);
  pinMode(linksom, INPUT);
  pinMode(rechtsom, INPUT);
  pinMode(reset, INPUT);

  Serial.begin(57600); // Begin seriële communicatie met baudrate 9600
}

void loop() {
   // Verhoog de loopCounter elke keer als de loop wordt doorlopen

  int pressedL = digitalRead(linksom);
  if (pressedL == HIGH) {
    digitalWrite(dirPin, HIGH);
    digitalWrite(stepPin, HIGH); 
    delayMicroseconds(500);    // door dit tijdsinterval tussen de stappen te veranderen, kunnen we de rotatiesnelheid wijzigen
    digitalWrite(stepPin, LOW); 
    delayMicroseconds(500);
    loopCounter++;
    Serial.println(loopCounter);
  }

  int pressedR = digitalRead(rechtsom);
  if (pressedR == HIGH) {
    digitalWrite(dirPin, LOW);
    digitalWrite(stepPin, HIGH); 
    delayMicroseconds(500);    // door dit tijdsinterval tussen de stappen te veranderen, kunnen we de rotatiesnelheid wijzigen
    digitalWrite(stepPin, LOW); 
    delayMicroseconds(500);
    loopCounter++;
    Serial.println(loopCounter);
  }
  int pressedReset = digitalRead(reset);{
    if (pressedReset == HIGH){
      loopCounter =0;
    }
  }
}

You are printing in every loop, ~1000 times per second based on your delays.
Your Serial output has a limited buffer length(). Once you fill that buffer, your serial prints block, only returning when enough room has been created for the characters you're trying to print. So, you can only loop at a speed proportional to your serial baud rate, once the buffer fills.
Don't print so often. Increasing the baud rate will help Serial keep up, but the way you're doing it right now, you'd need a stupidly high baud rate; even 115200, for example, only sends about 11 characters per millisecond.

1 Like

I would suggest you use a millis() timecheck to simply send a count update every half second or so. That way, your process will continue but you won't flood Serial.

2 Likes

@klaasvdb do you really need a count update? Step aside the problem and just install an all normal heartbeat running a LED.

Here's one way, grabbed from @LarryD, who gets royalties for each beat of every beating heart LED:

Here heartbeatTIME is an unsigned long, and heartbeatLED is a spare pin set to pin mode OUTPUT.


There are quite a few ways to do this, some clever, some obscure but none that block.

The code lives at the top level of the loop() and shoukd make no never mind to any other code in there.

Heart beat stops: bad news.

Heart beat arrhythmia: signs of code blockages from use of delay() or processes that are taking too much time for themselves within one iteration of the loop().

a7

I think the OP wants to know how many steps have been done. But, that's just my interpretation of what was said.

OK, I see. But I get a small finder's fee payment from @LarryD, so just in case. :wink:

a7

1 Like

Yes, My stepper motor is connected to ball screw spindel


I need to be able to track the movement along the axis. I wanted to do this bye tracking that amount of steps the stepper motor takes and then converting it into an axial distance.

I also could use a sensor

@alto777 I prefer donuts, the tax man doesn't know for sure then...

@klaasvdb Okay, but as I suggested, a periodic report should give you what you want. Limit switches are pretty much standard things anyway, to prevent runaways.

And how are you going to view that data? You will still have the transmission issue. Maybe a small LCD might be more useful to monitor the number of turns?

I don't use steppers, but are there not ways to "step without delay"?

It seems often when stepping is the thing there are one or two libraries that pop up that do not time out the steps so crudely.

a7

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