Jacob KlineConor Devlin
Published

Flying Stock Market Plane!

Fly away in this plane that moves up and down in real-time as the Boeing stock price rises and falls!!

IntermediateShowcase (no instructions)15 hours466

Things used in this project

Hardware components

Photon
Particle Photon
×1
RGB Backlight LCD - 16x2
Adafruit RGB Backlight LCD - 16x2
×1
Breadboard (generic)
Breadboard (generic)
×2
Adafruit NeoPixel Digital RGB LED Strip 144 LED, 1m White
Adafruit NeoPixel Digital RGB LED Strip 144 LED, 1m White
×1
NEMA 17 Stepper Motor
×1
Fishing Line
×1
SparkFun Limit Switch
×1
60W PCIe 12V 5A Power Supply
Digilent 60W PCIe 12V 5A Power Supply
×1
5V 2.5A Switching Power Supply
Digilent 5V 2.5A Switching Power Supply
×1
Adafruit BREAKOUT TB6612 1.2A MOTOR DVR
×1
SparkFun Trimpot 10K Ohm with Knob
×1
Resistor 220 ohm
Resistor 220 ohm
×1
Electrolytic Capacitor, 10000 µF
Electrolytic Capacitor, 10000 µF
×1

Software apps and online services

Particle Build Web IDE
Particle Build Web IDE
Alpha Vantage Stock Time Series API

Hand tools and fabrication machines

Soldering iron (generic)
Soldering iron (generic)
Solder Wire, 0.022" Diameter
Solder Wire, 0.022" Diameter

Story

Read more

Schematics

Boeing Project Wiring Diagram

Here is the full wiring diagram for the project. We did the project on two separate breadboards because when we began, we underestimated the amount of space the components required. This project could also be completed on one large breadboard.

Code

stockmarketproject.ino

Arduino
This is the software that we developed that runs the whole project. We uploaded this code onto a Particle Photon.
// ***API Documentation webpage https://www.alphavantage.co/documentation/#time-series-data***
//Project Credit for Jacob Kline and Conor Devlin

// This #include statement was automatically added by the Particle IDE.
#include <Stepper.h>                //The library that lets us interact with Stepper Motors

// This #include statement was automatically added by the Particle IDE.
#include <LiquidCrystal.h>          //The library that lets us interact with LCD Screens

// This #include statement was automatically added by the Particle IDE.
#include <neopixel.h>               //The library that lets us interact with the Neopixels

// This #include statement was automatically added by the Particle IDE.
#include <SparkJson.h>              //The library that lets us interact with Json objects

const char *json;

#define LIMIT_SWITCH_PIN A4

#define PIXEL_COUNT 60						// 24 Pixels on our ring
#define PIXEL_PIN D2						// Ring uses D6 as default pin
#define PIXEL_TYPE WS2812B					// Ring uses WS2812 Pixels
Adafruit_NeoPixel strip(PIXEL_COUNT, PIXEL_PIN, PIXEL_TYPE) ;	// Create out ring object

//Initialize the stepper motor
const int stepsPerRevolution = 200 ;        //Lets the software know that this type of stepper motor has 200 steps per full revolution
Stepper myStepper(stepsPerRevolution, 4, 5, 6, 7) ; //Inititalizes what data pins the motor is on the Photon

volatile float previousPrice = 0 ;  
volatile float currentPrice = 0 ;

String price = "0.0" ;

unsigned long lastTime = 0 ;

LiquidCrystal lcd(0, 1, A0, A1, A2, A3) ;   //Initializes the LCD Screen by linking the data pins it's connected to on the Photon

bool hasChangedTwice = false;   //This is used to make sure that the photon has gone through at least one iteration of retrieving data because there is a large jump from $0 to ~$300

void setup() {
    Serial.begin(9600) ;    //Initializes the serial monitor
    Particle.subscribe("hook-response/StockMarketNow", myHandler, MY_DEVICES) ; //Initializes the webhook.
    
    strip.begin() ; //Initializes the Neopixel
    strip.setBrightness(35) ;   //Sets the brightness of the Neopixel
    
    //This sets the color of all of the Neopixels from LED 0 to 10
    for(int i = 0; i <= 10; i++)
    {
        strip.setPixelColor(i, 255, 255, 255) ;
    }
    strip.show() ;  //This actually displays the color that was set onto each LED
    
    lcd.begin(16, 2) ;  //Initializes the LCD screen that has a width of 16 and a height of 2
    lcd.setCursor(0, 0) ;   //Sets the cursor to line 0 columb 0
    lcd.print("Initialzing") ;
    
    myStepper.setSpeed(100) ;   //Sets the "Speed" or "Power" that the stepper motor will use.  Here it is using 100% power
    
    pinMode(LIMIT_SWITCH_PIN, INPUT_PULLUP) ;    //Initializes the switch to be on pin "LIMIT_SWITCH_PIN" and that it will be used for INPUT_PUKLLUP
    
    //This brings the plane all the way down until it pushes the limit switch, where it will then exit this loop
    while(digitalRead(LIMIT_SWITCH_PIN) == LOW)
    {
        myStepper.step(1) ;
    }
    
    //After the switch has been hit, it moves the plane upwards 1003 steps, or halfway up the box so that it sits in the center
    if(digitalRead(LIMIT_SWITCH_PIN) == HIGH)
    {
        myStepper.step(-1003) ;
    }
    
    lcd.setCursor(0, 0) ;
    lcd.print("Initialized!") ;
    delay(3000) ;
    lcd.setCursor(0, 0) ;
    lcd.print("                ") ;
    lcd.setCursor(0, 0) ;
    lcd.print("Welcome to") ;
    lcd.setCursor(0, 1) ;
    lcd.print("Sklar Airlines!") ;
    delay(3000);
}

int steps = 1003 ;

void loop() {
    if(millis() - lastTime >= 120000)    //This checks to see if 10 seconds has gone by since the last time we checked this data
    { 
        lastTime = millis();    //Updates the clock so that it will wait 10 seconds from this point
        previousPrice = price.toFloat() ;   //Sets the previous price to what the price is right before it gets updated
        Particle.publish("StockMarketNow", PRIVATE);    //Sends the command to activate the webhook and get the data, as well as shift into the handler function to access that data
        delay(5000) ;
        currentPrice = price.toFloat() ;    //Sets the new price
        
        if(hasChangedTwice == true)     //This checks to make sure that this isn't the first time we're checking because if it was there would be too big of a jump from previous and current price
        {
            
            lcd.setCursor(0, 0) ;
            lcd.print("Boeing Stock Prc:") ;
            
            lcd.setCursor(0, 1) ;
            lcd.print("                ") ;
            
            lcd.setCursor(0, 1) ;
            lcd.print("Updating") ;
            
            lcd.setCursor(8, 1) ;
            
            for(int i = 1; i < 7; i++)
            {
                lcd.print(".") ;
                delay(500) ;
                if(i % 3 == 0)
                {
                    lcd.setCursor(8, 1) ;
                    lcd.print("   ") ;
                    lcd.setCursor(8, 1) ;
                    delay(500) ;
                }
            }
            
            lcd.setCursor(0, 1) ;
            lcd.print("$" + (String)(currentPrice) + " ") ;
            
            if(currentPrice < previousPrice)
            {
                for(int i = 0; i <= 9; i++)
                {
                    strip.setPixelColor(i, 255, 0, 0) ;
                }
                strip.show() ;
                
                for(int i = 0; i <= (int)(((previousPrice - currentPrice) * 334.3 * 3)); i++)
                {
                    myStepper.step(1) ;
                    steps-- ;
                    if(digitalRead(LIMIT_SWITCH_PIN) == HIGH)
                    {
                        myStepper.step(-1003) ;
                        steps = 1003 ;
                        break ;
                    }
                }
            }
            else if(currentPrice > previousPrice)
            {
                for(int i = 0; i <= 9; i++)
                {   
                    strip.setPixelColor(i, 0, 255,0) ;
                }
                strip.show() ;
                
                for(int i = 0; i <= (int)(((currentPrice - previousPrice) * 334.3 * 3)); i++)
                {
                    myStepper.step(-1) ;
                    steps++ ;
                    if(steps == 1975)
                    {
                        myStepper.step(1003) ;
                        steps = 1003 ;
                        break ;
                    }
                    
                }
            }
            else if(currentPrice == previousPrice)
            {
                for(int i = 0; i <= 9; i++)
                {
                    strip.setPixelColor(i, 255, 255, 255) ;
                }
                strip.show() ;
            }
        }
        else if(hasChangedTwice == false)
        {
            hasChangedTwice = true ;
            
        }
    }
 }
 
 void myHandler(const char *event, const char *data) {
    json = data ;
    
    StaticJsonBuffer<500> jsonBuffer ;
    JsonObject& root = jsonBuffer.parseObject(const_cast<char*>(json)) ;
    
    if(!root.success())
    {
        Serial.print("parseObject() Failed") ;
        return ;
    }
    
    const char* priceCHAR = root["Global Quote"]["05. price"] ;
    price = (String) priceCHAR ;
}

Credits

Jacob Kline

Jacob Kline

1 project • 0 followers
Hey there! My name's Jacob Kline and I'm a CS student at Lane Tech High School. I've recently gotten involved in developing through school!
Conor Devlin

Conor Devlin

1 project • 0 followers
Thanks to Lilly Forsythe and Keira Hickey.

Comments