Go Down

Topic: If statements in loop getting hung up - pellet dispenser (Read 357 times) previous topic - next topic

ElHefe

Code: [Select]
/*
Nano board
    R2 Homing works and slow blinks but need to make fast blink if failed home...R4
    R3 Homing does not initiate with M4, always runs. fix this. also ledbuiltin is inop now...R5
    R4 Now waits for M4 command - ok
    R5 enable blink codes on both aux led and led_builtin
    R6 time to rotate drop 3 pellets
    R7 rotate routine works - Every M8 command rotates, TESTED WITH GRBL
    R8
*/

#include <SpeedyStepper.h>
#include <Wire.h>   //  I2C OLED pellet counter

//BELOW IS EXPANDED GRBL I/O FOR NANO*************************************

const int LED_PIN = LED_BUILTIN;    // D13
const int EN = 2;  //eventually connect aux DRV8825 to grbl board enable pins

const int MOTOR_DIRECTION_PIN = 3;
const int MOTOR_STEP_PIN = 4;
const int LIMIT_SWITCH_PIN = 5;

const int ROTATE = A3; //output command //COOLANT M8^/M9  SPINDLE STEP
const int HOMESW = A0; //output command //SPINDLE M3/M4^ HOMING ROUTINE

const int ROTATE_INDICATOR = 7;       //COOLANT M8^/M9
const int HOME_INDICATOR = 9;         //SPINDLE M3/M4^

SpeedyStepper stepper;

void setup()    //********************************SETUP**************************
{
//  display.begin(SSD1306_SWITCHCAPVCC, 0x3c);  //I2C OLED pellet counter
  pinMode(LED_PIN, OUTPUT); //led_builtin to indicate home status
  pinMode(HOME_INDICATOR, OUTPUT);
  pinMode(ROTATE_INDICATOR, OUTPUT);
  pinMode(LIMIT_SWITCH_PIN, INPUT_PULLUP);
  Serial.begin(9600);
  stepper.connectToPins(MOTOR_STEP_PIN, MOTOR_DIRECTION_PIN);
}

void loop()   //************************************LOOP*****************************
{
  {
    if (digitalRead (HOMESW) == HIGH)   //A0 homeRoutine()
    {
      digitalWrite (HOME_INDICATOR, HIGH);
      homeRoutine();
    }
    else digitalWrite (HOME_INDICATOR, LOW);
  }

  {
    if (digitalRead (ROTATE) == HIGH)   //A3 rotateRoutine()
    {
      digitalWrite (ROTATE_INDICATOR, HIGH);
      rotateRoutine();
    }
    else digitalWrite (ROTATE_INDICATOR, LOW);
  }
}

void rotateRoutine()    //*******************************ROTATE***********************
{
  stepper.setCurrentPositionInMillimeters(0);
  stepper.setStepsPerRevolution(50 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(100.0);   //set accel
  stepper.moveToPositionInSteps(50); //  50 steps (200/4=50 steps/360 degrees
  stepper.setCurrentPositionInMillimeters(0);

  return;
}

void homeRoutine()    //**********************************HOME****************************
{
  stepper.setStepsPerRevolution(400 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(10.0);   //set accel
  const float homingSpeedInRevolutions = 1.0;   //find home
  const float maxHomingDistanceInRevolutions = 1;   // 1/2 revoution to fine home. If no find, then fault
  const int directionTowardHome = -1;        // direction to move toward limit switch: 1 goes positive direction, -1 backward

  if (stepper.moveToHomeInRevolutions(directionTowardHome, homingSpeedInRevolutions, maxHomingDistanceInRevolutions, LIMIT_SWITCH_PIN) != true)
  {
    while (true)
    {
      blinkFast();
    }
  }
  delay(500);
  stepper.setCurrentPositionInMillimeters(0);
  while (true)  {
    blinkSlow();
  }
  return;
}

void blinkFast()    //FAIL angryLed :-(
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (100);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (100);
}

void blinkSlow()    //SUCCESS happyLed : -)
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (1000);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (1000);
}


Working on a covid test tube pellet dispenser project and am having problem with my loop getting stuck. Ideally, I want to home a rotary stepper motor axis at the start of the loop (void HOMESW) ONE time, then proceed to the void ROTATE routine. The homing sequence works but does not respond to ROTATE routine, just seems to ignore it. I tried, among many things, to put the homing sequence in SETUP since it can only run once at the start but that only homed if the input HOMESW was already high at reset. I guess that makes sense. Both routines run individually (if i just put one routine in the loop) but fail when I try to integrate them.
I'm a rookie so it is really hard to make this clear. Let me know what i've missed. Thx





ElHefe

I got the homing sequence to work once (like it should) by adding it to the setup() but the rotate if statement still will not run. [EDIT] I think that the return at the bottom of the HOMESW routine might send it back to setup() where it was called. hmmm.

Code: [Select]
/*
    R2 Homing works and slow blinks but need to make fast blink if failed home...R4
    R3 Homing does not initiate with M4, always runs. fix this. also ledbuiltin is inop now...R5
    R4 Now waits for M4 command - ok
    R5 enable blink codes on both aux led and led_builtin
    R6 time to rotate drop 3 pellets
    R7 rotate routine works - Every M8 command rotates, TESTED WITH GRBL
    R8
*/

#include <SpeedyStepper.h>
#include <Wire.h>   //  I2C OLED pellet counter

//BELOW IS EXPANDED GRBL I/O FOR NANO*************************************

const int LED_PIN = LED_BUILTIN;    // D13
const int EN = 2;  //eventually connect aux DRV8825 to grbl board enable pins

const int MOTOR_DIRECTION_PIN = 3;
const int MOTOR_STEP_PIN = 4;
const int LIMIT_SWITCH_PIN = 5;

const int ROTATE = A3; //output command //COOLANT M8^/M9  SPINDLE STEP
const int HOMESW = A0; //output command //SPINDLE M3/M4^ HOMING ROUTINE

const int ROTATE_INDICATOR = 7;       //COOLANT M8^/M9
const int HOME_INDICATOR = 9;         //SPINDLE M3/M4^

SpeedyStepper stepper;

void setup()    //********************************SETUP**************************
{

  //  display.begin(SSD1306_SWITCHCAPVCC, 0x3c);  //I2C OLED pellet counter
  pinMode(LED_PIN, OUTPUT); //led_builtin to indicate home status
  pinMode(HOME_INDICATOR, OUTPUT);
  pinMode(ROTATE_INDICATOR, OUTPUT);
  pinMode(LIMIT_SWITCH_PIN, INPUT_PULLUP);
  Serial.begin(9600);
  stepper.connectToPins(MOTOR_STEP_PIN, MOTOR_DIRECTION_PIN);
  {
    while   (digitalRead (HOMESW) == LOW); {
      homeRoutine();
    }
  }
}

void loop()   //************************************LOOP*****************************
{
  {
    if (digitalRead (ROTATE) == HIGH)   //A3 rotateRoutine()
    {
      rotateRoutine();
      digitalWrite (ROTATE_INDICATOR, HIGH);
    }
    else digitalWrite (ROTATE_INDICATOR, LOW);
  }
}

void rotateRoutine()    //*******************************ROTATE***********************
{
  stepper.setCurrentPositionInMillimeters(0);
  stepper.setStepsPerRevolution(50 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(100.0);   //set accel
  stepper.moveToPositionInSteps(50); //  50 steps (200/4=50 steps/360 degrees
  stepper.setCurrentPositionInMillimeters(0);

  return;
}

void homeRoutine()    //**********************************HOME****************************
{
  stepper.setStepsPerRevolution(400 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(10.0);   //set accel
  const float homingSpeedInRevolutions = 1.0;   //find home
  const float maxHomingDistanceInRevolutions = 1;   // 1/2 revoution to fine home. If no find, then fault
  const int directionTowardHome = -1;        // direction to move toward limit switch: 1 goes positive direction, -1 backward

  if (stepper.moveToHomeInRevolutions(directionTowardHome, homingSpeedInRevolutions, maxHomingDistanceInRevolutions, LIMIT_SWITCH_PIN) != true)
  {
    while (true)
    {
      blinkFast();
    }
  }
  delay(500);
  stepper.setCurrentPositionInMillimeters(0);
  while (true)  {
    blinkSlow();
  }
  return;
}

void blinkFast()    //****************************FAIL angryLed :-(
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (100);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (100);
}

void blinkSlow()    //**************************SUCCESS happyLed : -)
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (1000);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (1000);
}

wildbill

You're missing a pinMode for ROTATE. Not that it necessarily matters, input is the default. I see you've used the internal pull-ups on the other button - how is the rotate button wired?

ElHefe

That was a good catch but my comments were misleading. That is an input (output from another microcontroller) 

TheMemberFormerlyKnownAsAWOL

#4
Nov 19, 2020, 10:30 am Last Edit: Nov 19, 2020, 10:30 am by TheMemberFormerlyKnownAsAWOL
Code: [Select]
while   (digitalRead (HOMESW) == LOW); {Oops
Please don't PM technical questions - post them on the forum, then everyone benefits/suffers equally

ElHefe

Thanks AWOL, fixed that. I was trying something, forgot to go back to it.

Ok, so back to LOOP...My homing routine works. The stepper waits for a 5v high command from HOMESW, then executes homeRoutine() and waits. Now the problem is that I expect the rotateRoutine to start at the second if statement but it just hangs out smoking cigarettes. Can i do this with an if statement? Seems like loop should continuously scan looking for changes in the "if".

Code: [Select]
/*
    R2 Homing works and slow blinks but need to make fast blink if failed home...R4
    R3 Homing does not initiate with M4, always runs. fix this. also ledbuiltin is inop now...R5
    R4 Now waits for M4 command - ok
    R5 enable blink codes on both aux led and led_builtin
    R6 time to rotate drop 3 pellets
    R7 rotate routine works - Every M8 command rotates, TESTED WITH GRBL
    R8 Added home to setup() it works but rotate in loop() doesnt. close?
    tried moving rotate to if while. it only works after a reset if both ROTATE and HOMESW are HIGH
    R9
*/
#include <SpeedyStepper.h>
#include <Wire.h>   //  I2C OLED pellet counter

//BELOW IS EXPANDED GRBL I/O FOR NANO*************************************

const int LED_PIN = LED_BUILTIN;    // D13
const int EN = 2;  // unused now

const int MOTOR_DIRECTION_PIN = 3;
const int MOTOR_STEP_PIN = 4;
const int LIMIT_SWITCH_PIN = 5;

const int ROTATE = A3;     //output command from GRBL//COOLANT M8^/M9  SPINDLE STEP
const int HOMESW = A0;     //output command from GRBL//SPINDLE M3/M4^ HOMING ROUTINE

const int ROTATE_INDICATOR = 7;       //COOLANT M8^/M9
const int HOME_INDICATOR = 9;         //SPINDLE M3/M4^

SpeedyStepper stepper;

void setup()    //********************************SETUP**************************
{

  //  display.begin(SSD1306_SWITCHCAPVCC, 0x3c);  //I2C OLED pellet counter
  pinMode(LED_PIN, OUTPUT); //led_builtin to indicate home status
  pinMode(HOME_INDICATOR, OUTPUT);
  pinMode(ROTATE_INDICATOR, OUTPUT);
  pinMode(LIMIT_SWITCH_PIN, INPUT_PULLUP);
  Serial.begin(9600);
  stepper.connectToPins(MOTOR_STEP_PIN, MOTOR_DIRECTION_PIN);
}

void loop()   //************************************LOOP*****************************
{
  {
    while (digitalRead (HOMESW) == HIGH && digitalRead (ROTATE) == LOW)
    {
      homeRoutine();
      digitalWrite (HOME_INDICATOR, HIGH);
    }
  }
  { if (digitalRead (HOMESW) == LOW && digitalRead (ROTATE) == HIGH)
    {
      rotateRoutine();
      digitalWrite (ROTATE_INDICATOR, HIGH);
    }
    else digitalWrite (ROTATE_INDICATOR, LOW);
  }
}

void rotateRoutine()    //*******************************ROTATE***********************
{
  stepper.setCurrentPositionInMillimeters(0);
  stepper.setStepsPerRevolution(50 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(100.0);   //set accel
  stepper.moveToPositionInSteps(50); //  50 steps (200/4=50 steps/360 degrees
  stepper.setCurrentPositionInMillimeters(0);
  return;
}

void homeRoutine()    //**********************************HOME****************************
{
  stepper.setStepsPerRevolution(400 * 1);    // 1x microstepping
  stepper.setSpeedInRevolutionsPerSecond(5);    //set speed
  stepper.setAccelerationInMillimetersPerSecondPerSecond(10.0);   //set accel
  const float homingSpeedInRevolutions = 1.0;   //find home
  const float maxHomingDistanceInRevolutions = 1;   // 1/2 revoution to fine home. If no find, then fault
  const int directionTowardHome = -1;        // direction to move toward limit switch: 1 goes positive direction, -1 backward

  if (stepper.moveToHomeInRevolutions(directionTowardHome, homingSpeedInRevolutions, maxHomingDistanceInRevolutions, LIMIT_SWITCH_PIN) != true)
  {
    while (true)
    {
      blinkFast();
    }
  }
  delay(500);
  stepper.setCurrentPositionInMillimeters(0);
  while (true)  {
    blinkSlow();
  }
  return;
}

void blinkFast()    //****************************FAIL angryLed*********
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (100);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (100);
  return;
}

void blinkSlow()    //**************************PASS happyLed*******
{
  digitalWrite (HOME_INDICATOR, HIGH);
  digitalWrite (LED_BUILTIN, HIGH);
  delay (1000);
  digitalWrite (HOME_INDICATOR, LOW);
  digitalWrite (LED_BUILTIN, LOW);
  delay (1000);
  return;
}

ElHefe

#6
Nov 20, 2020, 06:00 am Last Edit: Nov 20, 2020, 06:04 am by ElHefe Reason: forgot img
Wildbill: Wiring diagram of limit switch connection:


ElHefe

Not sure why my picture didn't post. The link is there and i just tested it.

I noticed something. With ROTATE (A3) already high and HOMESW low and I hit the reset, it goes straight to the rotateRoutine, skipping homeRoutine. Not what I want it to do.
I want it to successfully home once and wait. Do nothing until it sees a command to rotate. Should I put them on interrupts?


ElHefe

Never mind, I'll find a workaround.

Go Up