- lemonbotfirstday.jpg (88.39 KiB) Viewed 1104 times
Stepper Shield Lemonade Stand
Moderators: adafruit_support_bill, adafruit
Please be positive and constructive with your questions and comments.
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
The Eagle has landed. The debut at Kasiloff River, Alaska, was a smash, with six customers
- adafruit_support_bill
- Posts: 88154
- Joined: Sat Feb 07, 2009 10:11 am
Re: Stepper Shield Lemonade Stand
Awesome! And solar powered too!
Alaska is a long way to go for ordinary lemonade. But it might just be worth the drive for laser treated.
Alaska is a long way to go for ordinary lemonade. But it might just be worth the drive for laser treated.
- egutting
- Posts: 297
- Joined: Wed Nov 14, 2012 12:57 am
Re: Stepper Shield Lemonade Stand
This is so awesome!!
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
The Man eventually kicked us out of our spot at the Kasilof river boat launch. Our initial post-marketing analysis reveals the following:
1. You can't trust the Man if you're running a small business.
2. The electrodes that detect when the cup is full are very twitchy. Analog things are like a very hot girlfriend with borderline personality- you really want to make it work, but the instability gets old after a while. We believe that after a dunk in the lemonade, the electrolytes on the electrodes change the conductivity. If they have time to dry, it make them less sensitive. If they are wet, they are too sensitive. We can change the electrodes with each sale, but that is tedious. We tried the TMP 36, but its too slow to react. We will try a plain thermistor. The ultimate fall-back is to fill the cup with a timer. As long as the ice in consistent, this works, and still satisfies the unknowing masses, but its not satisfying to us. We will try once again to go it on a digital pin with a pull-up. Any ideas are appreciated, but not expected.
3. We got rid of our "Basic Laser Treatment." We only do"plain" lemonade, and "deluxe" laser treatment, because that is what our customers tell us they want. We have converted the "basic" protocol into laser treatment for bottled water so we can expand into the low carb market.
1. You can't trust the Man if you're running a small business.
2. The electrodes that detect when the cup is full are very twitchy. Analog things are like a very hot girlfriend with borderline personality- you really want to make it work, but the instability gets old after a while. We believe that after a dunk in the lemonade, the electrolytes on the electrodes change the conductivity. If they have time to dry, it make them less sensitive. If they are wet, they are too sensitive. We can change the electrodes with each sale, but that is tedious. We tried the TMP 36, but its too slow to react. We will try a plain thermistor. The ultimate fall-back is to fill the cup with a timer. As long as the ice in consistent, this works, and still satisfies the unknowing masses, but its not satisfying to us. We will try once again to go it on a digital pin with a pull-up. Any ideas are appreciated, but not expected.
3. We got rid of our "Basic Laser Treatment." We only do"plain" lemonade, and "deluxe" laser treatment, because that is what our customers tell us they want. We have converted the "basic" protocol into laser treatment for bottled water so we can expand into the low carb market.
- adafruit_support_bill
- Posts: 88154
- Joined: Sat Feb 07, 2009 10:11 am
Re: Stepper Shield Lemonade Stand
I've used ultrasonic sensors in my Arduwino to detect fluid levels in wine glasses with good results. The Maxbotix sensors we carry here have a close-range limit of about 6". If you can find a Ping sensor, they go as close as a few centimeters.
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
Your idea is great. I actually have a Ping Sensor and have positioned it on the sensor arm. It functions well when I put in on an independent arduino with just the snesing loop. It detects a fluid level at 2cm, which is great. Unfortunately, when I put the same code into the lemonade program where I have previously put the electrode or the TMP 36 (they worked, just not as accurately as required) it doesn't fire the filling solonoid valve. Also it doesn't serial print the range.
Another issue is that the Stepper the moves the sensor module locks into position, even when the program is in the 'resting' phase (where waits for the 3 Bool paths). This only occurs after the protocol has been run once.
if (plain) //This runs plain lemonade without laser treatment. What loser wants that? Lasers are the WAY.
{
// turns the red "underway" light on
digitalWrite(rightLight,HIGH); // turns on the right switchlight- this is the white adafruit MOM switch
myStepper2->step(2025, BACKWARD, DOUBLE);//move conveyor to the fill position
myStepper1->step(55, FORWARD, MICROSTEP);//put in the fill sensor
delay(500 );
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
while (uS / US_ROUNDTRIP_CM > 3);
{
delay(50);
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
digitalWrite(fillRelay,LOW);
}
digitalWrite(fillRelay,HIGH);//closes the fill valve
myStepper1->step(55, BACKWARD, MICROSTEP);// moves the sensor out of the lemonade
delay(500);
myStepper2->step(2000 , FORWARD, DOUBLE);// moves drink back to the start
//resets the ready green light
// stops the red 'underway' light
digitalWrite(rightLight,LOW);// turns the right light off
}
- adafruit_support_bill
- Posts: 88154
- Joined: Sat Feb 07, 2009 10:11 am
Re: Stepper Shield Lemonade Stand
Hard to say. Often when microcontroller programs start acting wacky after an incremental change memory problems are to blame. http://learn.adafruit.com/memories-of-an-arduino
If you post the whole code we can take a look.
When posting code, use the </> button instead of the quote button. That makes it easier for us to cut & paste into an editor. All that pretty HTML color coding confuses the heck out of the compiler.
If you post the whole code we can take a look.
When posting code, use the </> button instead of the quote button. That makes it easier for us to cut & paste into an editor. All that pretty HTML color coding confuses the heck out of the compiler.
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
Ok. Here is the entire code: I think I need to run a loop that pings every 50microseconds, that keep the fill solonoid open, and then escapes when the distance <= 2 cm, closing the valve. The previous analog sensors didn't need to keep pinging.
Code: Select all
/*
This is a test sketch for the Adafruit assembled Motor Shield for Arduino v2 It won't work with v1.x motor shields! Only for the v2's with built in PWM control
For use with the Adafruit Motor Shield v2
----> http://www.adafruit.com/products/1438
*/
#include <Wire.h>
#include <Adafruit_MotorShield.h>
#include "utility/Adafruit_PWMServoDriver.h"
#include <NewPing.h>
Adafruit_MotorShield AFMStop(0x60);// Default address- no jmpers.
Adafruit_MotorShield AFMSbot(0x61); // Rightmost jumper closed Adafruit_MotorShield AFMStop(0x60);
Adafruit_StepperMotor *myStepper1 = AFMStop.getStepper(200,1);
Adafruit_StepperMotor *myStepper2 = AFMStop.getStepper(200,2);
Adafruit_StepperMotor *myStepper3 = AFMSbot.getStepper(200,1);
Adafruit_StepperMotor *myStepper4 = AFMSbot.getStepper(200,2);
#define TRIGGER_PIN 12
#define ECHO_PIN 11
#define MAX_DISTANCE 200
NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE);
int basicSwitch = 4;
int plainSwitch = 3;
int deluxeSwitch = 5;
int fillSensor = 0;
int fillRelay = 7;
int blueLaser = 8;
int greenLaser = 9;
int rightLight = 10;
int middleLight = 1;
int leftLight = 2;
int redLaser= 13;
int delayPeriod = 1000;
void setup ()
{
AFMSbot.begin(); // Start the bottom shield
AFMStop.begin(); // Start the top shield
Serial.begin(115200); //
myStepper1->setSpeed(30); //sensor speed
myStepper2->setSpeed(100); //conveyor speed
myStepper3->setSpeed(200); //laser horizontal
myStepper4->setSpeed(50); //laser vertical speed
Serial.begin(115200); // set up Serial library at 115200 for the ping ;
pinMode(basicSwitch,INPUT_PULLUP); //select basic lemonade
pinMode(plainSwitch,INPUT_PULLUP); //select the basic laser
pinMode(deluxeSwitch,INPUT_PULLUP); //select deluxe laser
//pinMode(fillSensor,INPUT_PULLUP)// the fill sensor has been changed from digital 6 to analog 0
pinMode(fillRelay,OUTPUT);//the valve filling the cup- relay #1
pinMode(blueLaser,OUTPUT);//the blue laser relay- relay #2
pinMode(greenLaser,OUTPUT);//the green laser- relay #3
pinMode(redLaser,OUTPUT);//the red laser- relay #4
pinMode(rightLight,OUTPUT); //the right switch light
pinMode(middleLight, OUTPUT);//the middle switch light
pinMode(leftLight,OUTPUT);//the left switch light
}
//relay #1 is fillRelay, relay #2 is greenLaser, relay #3 is blueLaser, relay# 4 is redLaser.
void loop()
{
bool plain = digitalRead(plainSwitch) == LOW; // the right switch for plain lemonade
bool basic = digitalRead(basicSwitch) == LOW; // the middle switch for basic laser treatment
bool deluxe = digitalRead(deluxeSwitch) == LOW; // the right switch for deluxe laser treatment
digitalWrite(fillRelay,HIGH); //keeps the fill relay OFF
digitalWrite(blueLaser,HIGH); //keeps the blue laser relay OFF- this is LOW=ON relay
digitalWrite(greenLaser,HIGH); //keeps the green laser relay OFF-this is LOW=ON relay
digitalWrite(redLaser,HIGH); //keeps the red laser relay OFF-this is LOW=ON relay
if (plain) //This runs plain lemonade without laser treatment. What loser wants that? Lasers are the WAY.
{
// turns the red "underway" light on
digitalWrite(rightLight,HIGH); // turns on the right switchlight- this is the white adafruit MOM switch
myStepper2->step(2025, BACKWARD, DOUBLE);//move conveyor to the fill position
myStepper1->step(55, FORWARD, MICROSTEP);//put in the fill sensor
delay(500 );
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
while (uS / US_ROUNDTRIP_CM > 3);
{
delay(50);
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
digitalWrite(fillRelay,LOW);
}
digitalWrite(fillRelay,HIGH);//closes the fill valve
myStepper1->step(55, BACKWARD, MICROSTEP);// moves the sensor out of the lemonade
delay(500);
myStepper2->step(2000 , FORWARD, DOUBLE);// moves drink back to the start
digitalWrite(rightLight,LOW);// turns the right light off
}
else if ( basic) //this runs boittled water
{
digitalWrite(middleLight,HIGH); // turns on the middle switchlight- this is the blue adafruit MOM switch
myStepper3->step(170,FORWARD,MICROSTEP);//rotate the laser horizontal over the track
myStepper2->step(100, BACKWARD, DOUBLE);//move conveyor to shot position #1
myStepper4->step(90,FORWARD,SINGLE);// aim Laser to position 1
digitalWrite(blueLaser,LOW);
delay(1000);
digitalWrite(blueLaser,HIGH);
myStepper2->step(200,BACKWARD,DOUBLE);//move the cup to shot #2
myStepper4->step(2,BACKWARD,SINGLE);//re-aim the laser
digitalWrite(greenLaser,LOW);
delay(500);
digitalWrite(greenLaser,HIGH);
digitalWrite(blueLaser,LOW);
delay(500);
digitalWrite(blueLaser,HIGH);
myStepper2->step(200,BACKWARD,DOUBLE); //move cup to potion 3
myStepper4->step(3,BACKWARD,SINGLE);//aim position 3
digitalWrite(greenLaser,LOW);
delay(500);
digitalWrite(greenLaser,HIGH);
digitalWrite(blueLaser,LOW);
delay(500);
digitalWrite(blueLaser,HIGH);
myStepper3->step(170,BACKWARD,MICROSTEP);// halfway back for final shot
myStepper2->step(925,BACKWARD,DOUBLE);//moves conveyor to final
digitalWrite(greenLaser,LOW);
delay(500);
digitalWrite(greenLaser,HIGH);
digitalWrite(blueLaser,LOW);
delay(300);
digitalWrite(blueLaser,HIGH);
myStepper4->step(85,BACKWARD,SINGLE);//back to start
myStepper2->step(1425,FORWARD,DOUBLE);//back to the beginning of conveyor
digitalWrite(middleLight,LOW);
}
else if ( deluxe )
{
digitalWrite(leftLight,HIGH); // turns on the leeft switchlight- this is the white adafruit MOM switch
myStepper3->step(190,FORWARD,MICROSTEP);//rotate the laser horizontal over the track
myStepper2->step(1100, BACKWARD, DOUBLE);//move conveyor to halfway
myStepper4->step(50,FORWARD,SINGLE);//aim the laserto halfway point
digitalWrite(greenLaser,LOW);//midway 'treatment" of the empty cup
delay(500);
digitalWrite(greenLaser,HIGH);
digitalWrite(blueLaser,LOW);
delay(1000);
digitalWrite(blueLaser,HIGH);
myStepper4->step(50,BACKWARD,SINGLE);
myStepper2->step(900,BACKWARD,DOUBLE);//finish moving conveyor to the fill station
myStepper1->step(55, FORWARD, MICROSTEP);//put in the fill sensor
delay(50);
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
while (uS / US_ROUNDTRIP_CM > 3);
{
delay(50);
int uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
digitalWrite(fillRelay,LOW);
}
digitalWrite(fillRelay,HIGH);//closes the fill valve
digitalWrite(redLaser,HIGH);//turns the red laser off
myStepper1->step(55,BACKWARD,MICROSTEP);//remove fill sensor
myStepper2->step(500,FORWARD,DOUBLE);//move conveyor quarter way back back.
myStepper4->step(22,FORWARD,SINGLE);//aim laser cannon to quarter way home
digitalWrite(greenLaser, LOW);
delay(delayPeriod);
digitalWrite(greenLaser,HIGH);
delay(delayPeriod);
digitalWrite(blueLaser,LOW);
delay(delayPeriod);
digitalWrite(blueLaser,HIGH);
delay(delayPeriod);
digitalWrite(greenLaser,LOW);
delay(500);
digitalWrite(greenLaser,HIGH);
delay(500);
myStepper2->step(500,FORWARD,DOUBLE);//move halfway back
myStepper4->step(40,FORWARD,SINGLE);//aim cannon to halfway back
digitalWrite(greenLaser, LOW);
delay(delayPeriod);
digitalWrite(greenLaser,HIGH);
delay(delayPeriod);
digitalWrite(blueLaser,LOW);
delay(delayPeriod);
digitalWrite(blueLaser,HIGH);
myStepper4->step(62,BACKWARD,SINGLE);
myStepper2->step(1000,FORWARD,DOUBLE); //return cup to the beginning
myStepper3->step(190,BACKWARD,MICROSTEP);
digitalWrite(leftLight,LOW);
}
}
Last edited by adafruit_support_bill on Wed Jun 11, 2014 1:14 pm, edited 3 times in total.
Reason: please use the </> button when submitting code. press </>, then paste your code between the [code] [/code] tags.
Reason: please use the </> button when submitting code. press </>, then paste your code between the [code] [/code] tags.
- adafruit_support_bill
- Posts: 88154
- Joined: Sat Feb 07, 2009 10:11 am
Re: Stepper Shield Lemonade Stand
The problem is you have 2 variables called uS. One is defined outside the loop and is the one you test in the loop conditional expression.
The other one is defined inside the loop. it is local to the loop and is created and destroyed on each iteration of the loop.
Removing the 'int' eliminates the dual definition. Now your original uS variable should be updated by the loop.
The other one is defined inside the loop. it is local to the loop and is created and destroyed on each iteration of the loop.
Code: Select all
while (uS / US_ROUNDTRIP_CM > 3);
{
delay(50);
int uS = sonar.ping(); <<<-------------------- This line re-defines a local copy of uS.
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
digitalWrite(fillRelay,LOW);
}
Code: Select all
while (uS / US_ROUNDTRIP_CM > 3);
{
delay(50);
uS = sonar.ping();
Serial.print("Ping: ");
Serial.print(uS / US_ROUNDTRIP_CM);
Serial.println("cm");
digitalWrite(fillRelay,LOW);
}
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
This works. You rule. This photo shows it partly backed off from the fill position.
- AlaskaJeff
- Posts: 37
- Joined: Sat Jan 11, 2014 1:29 am
Re: Stepper Shield Lemonade Stand
Now onto a weather station and fish detector.
Thanks again to this Adafruit for all the help.
- adafruit_support_bill
- Posts: 88154
- Joined: Sat Feb 07, 2009 10:11 am
Re: Stepper Shield Lemonade Stand
Great work! Looking forward to seeing your next projects.
Please be positive and constructive with your questions and comments.