Go Down

Topic: Step motor speed with TB6560 IC-driver and 2 push buttons  (Read 454 times) previous topic - next topic

viet5d

That seems to me the simplest thing to do.

...R
Here is the full code, compiled without error. Will be tested with hardware.

Code: [Select]



// this version uses millis() to manage timing rather than delay()
// and the movement is determined by a pair of momentary push bottons and switches
// press one of them (button/limit sw) and it turns CW, press the other one and it turns CCW

byte dirPin = 8;   
byte stepPin = 9;         

byte buttonCWpin  = A0;
byte buttonCCWpin = A1;
byte swCWpin  = A2;
byte swCCWpin = A3;

boolean buttonCWpressed = false;
boolean buttonCCWpressed = false;
boolean swCWpressed = false;
boolean swCCWpressed = false;

byte ledPin = 13;

unsigned long curMillis;
unsigned long prevStepPinMillis = 0;
unsigned long millisBetweenSteps = 1; // milliseconds

void setup() {

     Serial.begin(9600);
     Serial.println("Starting Stepper Demo with millis()");

     pinMode(dirPin, OUTPUT);
     pinMode(stepPin, OUTPUT);
     pinMode(ledPin, OUTPUT);

     pinMode(buttonCWpin, INPUT_PULLUP);
     pinMode(buttonCCWpin, INPUT_PULLUP);
     pinMode(swCWpin, INPUT_PULLUP);
     pinMode(swCCWpin, INPUT_PULLUP);
}

void loop() {
   
    curMillis = millis();
    readButtonsAndSw();
    actOnButtonsAndSw();
 
}

void readButtonsAndSw() {
   
    buttonCCWpressed = false;
    buttonCWpressed = false;
    swCCWpressed = false;
    swCWpressed = false;
   
    if ((digitalRead(buttonCWpin) || (digitalRead(swCWpin)) == LOW)) {
        buttonCWpressed = true;
        swCWpressed = true;
        }
     
     if ((digitalRead(buttonCCWpin) || (digitalRead(swCCWpin)) == LOW)) {
        buttonCCWpressed = true;
        swCCWpressed = true;
        }
    }

void actOnButtonsAndSw() {
    if (((buttonCWpressed) || (swCWpressed)) == true) {
        digitalWrite(dirPin, LOW);
        singleStep();
        }
       
    if (((buttonCCWpressed) || (swCCWpressed)) == true) {
        digitalWrite(dirPin, HIGH);
        singleStep();
       }
    }

void singleStep() {
    if (curMillis - prevStepPinMillis >= millisBetweenSteps) {
        // next 2 lines changed 28 Nov 2018
        //prevStepPinMillis += millisBetweenSteps;
        prevStepPinMillis = curMillis;
        digitalWrite(stepPin, HIGH);
        digitalWrite(stepPin, LOW);
        }
    }



viet5d

Here is the full code, compiled without error. Will be tested with hardware.

Code: [Select]



// this version uses millis() to manage timing rather than delay()
// and the movement is determined by a pair of momentary push bottons and switches
// press one of them (button/limit sw) and it turns CW, press the other one and it turns CCW

byte dirPin = 8;  
byte stepPin = 9;        

byte buttonCWpin  = A0;
byte buttonCCWpin = A1;
byte swCWpin  = A2;
byte swCCWpin = A3;

boolean buttonCWpressed = false;
boolean buttonCCWpressed = false;
boolean swCWpressed = false;
boolean swCCWpressed = false;

byte ledPin = 13;

unsigned long curMillis;
unsigned long prevStepPinMillis = 0;
unsigned long millisBetweenSteps = 1; // milliseconds

void setup() {

     Serial.begin(9600);
     Serial.println("Starting Stepper Demo with millis()");

     pinMode(dirPin, OUTPUT);
     pinMode(stepPin, OUTPUT);
     pinMode(ledPin, OUTPUT);

     pinMode(buttonCWpin, INPUT_PULLUP);
     pinMode(buttonCCWpin, INPUT_PULLUP);
     pinMode(swCWpin, INPUT_PULLUP);
     pinMode(swCCWpin, INPUT_PULLUP);
}

void loop() {
  
    curMillis = millis();
    readButtonsAndSw();
    actOnButtonsAndSw();
  
}

void readButtonsAndSw() {
  
    buttonCCWpressed = false;
    buttonCWpressed = false;
    swCCWpressed = false;
    swCWpressed = false;
    
    if ((digitalRead(buttonCWpin) || (digitalRead(swCWpin)) == LOW)) {
        buttonCWpressed = true;
        swCWpressed = true;
        }
      
     if ((digitalRead(buttonCCWpin) || (digitalRead(swCCWpin)) == LOW)) {
        buttonCCWpressed = true;
        swCCWpressed = true;
        }
    }

void actOnButtonsAndSw() {
    if (((buttonCWpressed) || (swCWpressed)) == true) {
        digitalWrite(dirPin, LOW);
        singleStep();
        }
        
    if (((buttonCCWpressed) || (swCCWpressed)) == true) {
        digitalWrite(dirPin, HIGH);
        singleStep();
       }
    }

void singleStep() {
    if (curMillis - prevStepPinMillis >= millisBetweenSteps) {
        // next 2 lines changed 28 Nov 2018
        //prevStepPinMillis += millisBetweenSteps;
        prevStepPinMillis = curMillis;
        digitalWrite(stepPin, HIGH);
        digitalWrite(stepPin, LOW);
        }
    }



First fast testing this code with hardware, I note:

1. With button CW direction is pressed, motor turns in this direction. When the pointer touches the limit "swCWpressed", the motor direction changes to CCW. But I can not use the button CCW (or swCCWpressed) to change the direction after that moment.

2. Same behave to other direction.

Need helps !

Thanks,
V5d    

viet5d

First fast testing this code with hardware, I note:

1. With button CW direction is pressed, motor turns in this direction. When the pointer touches the limit "swCWpressed", the motor direction changes to CCW. But I can not use the button CCW (or swCCWpressed) to change the direction after that moment.

2. Same behave to other direction.

Need helps !

Thanks,
V5d    
Correction point #1:

1. With button CW direction is pressed, motor turns in this direction. When the pointer touches the limit "swCWpressed" and stays in that state (connected to GND), the motor direction changes to CCW. But I can not use the button CCW (or swCCWpressed) to change the direction after that moment. When the "swCWpressed" releases, the moter returns to CW direction immediately.

Thanks,

viet5d

Correction point #1:

1. With button CW direction is pressed, motor turns in this direction. When the pointer touches the limit "swCWpressed" and stays in that state (connected to GND), the motor direction changes to CCW. But I can not use the button CCW (or swCCWpressed) to change the direction after that moment. When the "swCWpressed" releases, the moter returns to CW direction immediately.

Thanks,
Please note: - The button CW/CCW is a contact SPDT type

                        - The 2 limit SWs are the momentary contacts

Thanks,
V5d

groundFungus

#19
Oct 09, 2019, 09:24 pm Last Edit: Oct 09, 2019, 09:25 pm by groundFungus
I woould separate the buttons and limit switches.  Have a separate function for each.  One function handles the buttons and another handles the limit switches. Each time that you step, check the limit swiches.  If one limit swich is activatd, reverse the current direction.

viet5d

... If one limit swich is activatd, reverse the current direction.


Yes, agree.

At that moment, there are 2 possibilities to make the motor changes the direction affected by the sw-button or sw-limit.

I want to change sw-button (SPDT type) in 2 switches button (NO: normal opened) too, because the motor can not start (in any direction) in the beginning when power supply turn on. The motor moves/turns ONLY when the sw-button CW/CWW pressed (closed to GND). It is SAFETY for an operator.    

So, in resume, we should use 2 contacts button-switches to control/drive the motor in 2 directions separated dependent how long it is pressed and 2 momentary limit switches contacts (touche-and-release) to change the direction immediately.

Thanks for reply,
V5d

viet5d

Just for curious, with oscilloscope, I want to check the frequency (F) of Step signal at pin #9 Arduino when I change the value of "millisBetweenSteps" (= MBS) = 1, 5 and 25.

When MBS = 1 -----> F = 970Hz
           MBS = 5 -----> F = 195 Hz
           MBS = 25 ----> F = 40 Hz
   
Pulse width varies from 5.4us to 5.7us.


Robin2

When MBS = 1 -----> F = 970Hz
           MBS = 5 -----> F = 195 Hz
           MBS = 25 ----> F = 40 Hz
That looks about right. The millisBetweenSteps is not the only thing contributing to the time

...R
Two or three hours spent thinking and reading documentation solves most programming problems.

viet5d

As measured, the step pulse width = 5.4us to 5.7us when MBS = 1 (970Hz).

How can I reduce the step pulse less than 5us to use the scale 1/4, 1/8 and 1/16 ?

P.S: Actually, the motor running fast at HALF, and faster at FULL step. 

Thanks,

V5D


Robin2

How can I reduce the step pulse less than 5us to use the scale 1/4, 1/8 and 1/16
I would not bother. 5Āµsecs is a very short pulse.

...R
Two or three hours spent thinking and reading documentation solves most programming problems.

viet5d


I want to remove 2 limit switches for now, and adding 2 switches to change the motor speed (SLOW/FAST) by changing the vaiable "millisBetweenSteps" (MBS = 1 for FAST speed, MBS = 2 for SLOW speed).

I try to modify the code but it not working.

Very appreciated for helps.

Thanks,
V5D

Code: [Select]

/ this version uses millis() to manage timing rather than delay()
// and the movement is determined by a pair of momentary push bottons and switches
// press one of them (button/limit sw) and it turns CW, press the other one and it turns CCW

byte dirPin = 8;   
byte stepPin = 9;         

// 4 buttons
byte buttonCWpin  = A0;   // CW direstion
byte buttonCCWpin = A1;   // CCW direction
byte buttonSLOWpin = A2;  // SLOW speed
byte buttonFASTpin = A3;  // FAST speed

// 4 button states
boolean buttonCWpressed = false;
boolean buttonCCWpressed = false;
boolean buttonSLOWpressed = false;
boolean buttonFASTpressed = false;

byte ledPin = 13;

unsigned long curMillis;
unsigned long prevStepPinMillis = 0;


enum speedState_t: int{MBS1 = 1, MBS2 = 2} speedState;  // MBS = millisBetweenSteps
                                                        // MBS1: Halfs step, MBS2: Full steps

void setup() {

     Serial.begin(9600);
     Serial.println("Starting Stepper Demo with millis()");

     pinMode(dirPin, OUTPUT);
     pinMode(stepPin, OUTPUT);
     pinMode(ledPin, OUTPUT);

     pinMode(buttonCWpin, INPUT_PULLUP);
     pinMode(buttonCCWpin, INPUT_PULLUP);
     pinMode(buttonSLOWpin, INPUT_PULLUP);
     pinMode(buttonFASTpin, INPUT_PULLUP);
}

void loop() {
   switch (speedState){
    case MBS1:
        {   
        curMillis = millis();
        readButtons();
        actOnButtons();
        break;
        }
       
    case MBS2:
        {
        curMillis = millis();
        readButtons();
        actOnButtons();
        break;
        }
       
    default:
        break;
  }

void readButtons() {
   
    buttonCCWpressed = false;
    buttonCWpressed = false;
    buttonSLOWpressed = false;
    buttonFASTpressed = false;
   
    // directions
    if (digitalRead(buttonCWpin) == LOW) {
        buttonCWpressed = true;
        }
     
    if (digitalRead(buttonCCWpin) == LOW) {
        buttonCCWpressed = true;
        }
       
    // speeds
    if (digitalRead(buttonSLOWpin) == LOW) {
        buttonSLOWpressed = true;
        }

    if (digitalRead(buttonFASTpin) == LOW) {
        buttonFASTpressed = true;
        }
    }

void actOnButtons() {

    if ((buttonCWpressed) == true) {
        digitalWrite(dirPin, LOW);
        singleStep();
        }
       
    if ((buttonCCWpressed) == true) {
        digitalWrite(dirPin, HIGH);
        singleStep();
       }     
    }

void singleStep() {
    if (curMillis - prevStepPinMillis >= MBS1) {
        prevStepPinMillis = curMillis;
        digitalWrite(stepPin, HIGH);
        digitalWrite(stepPin, LOW);
    }

    if (curMillis - prevStepPinMillis >= MBS2) {
        prevStepPinMillis = curMillis;
        digitalWrite(stepPin, HIGH);
        digitalWrite(stepPin, LOW);
    }
  }





 


Go Up