Last active
June 2, 2020 10:19
-
-
Save polluxlabs/ce34a6b39425c00540e882fa8cba721f to your computer and use it in GitHub Desktop.
ISS Tracker with an ESP8266
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/********* | |
pollux labs, 2020 | |
https://polluxlabs.net | |
*********/ | |
#include <Wire.h> //I2C | |
#include <Adafruit_GFX.h> //OLED-Display | |
#include <Adafruit_SSD1306.h> //OLED-Display | |
#include <ESP8266WiFi.h> //WiFI | |
#include <ArduinoJson.h> //JSON | |
#include <ESP8266HTTPClient.h> //API Call | |
//Convert Unixtime in readable format | |
#include <RTClib.h> | |
// WIFI Credentials | |
const char* ssid = "YOUR SSID"; | |
const char* password = "YOUR WIFI PASSWORD"; | |
//Your coordinates | |
const float latitude = 00.00; | |
const float longitude = 00.00; | |
const float myAltitude = 100.00; | |
// 'iss', 128x32px | |
const unsigned char iss [] PROGMEM = { | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xf8, 0x3f, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x0f, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0f, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x1b, 0xfa, 0xaf, 0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, | |
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xfa, 0xbf, 0xe0, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0e, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0e, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xfa, 0xbf, 0xe0, 0x40, 0x00, 0x01, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x84, 0x4c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x84, 0x4c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x7c, 0x7c, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0xa0, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0xa0, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x7c, 0x7c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x21, 0x84, 0x4c, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x10, | |
0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x01, 0x84, 0x4c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x04, 0x40, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, | |
0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x0f, 0xfa, 0xbf, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0e, 0xe0, 0x20, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0e, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0xfa, 0xbe, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1b, 0xfa, 0xaf, 0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x18, 0x0f, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x10, 0x0f, 0xe0, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xf8, 0x3f, 0xe0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, | |
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 | |
}; | |
//Variables for time and duration | |
long riseTime = 0; | |
long currentTime = 0; | |
int duration = 0; | |
//OLED Display | |
#define SCREEN_WIDTH 128 // Breite des Displays in Pixeln | |
#define SCREEN_HEIGHT 32 // Höhe des Displays in Pixeln | |
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); | |
void getCurrentTime() { | |
HTTPClient http; | |
http.begin("http://worldtimeapi.org/api/timezone/Europe/Berlin"); //URL zur Zeitabfrage | |
int httpCode = http.GET(); | |
if (httpCode == 200) { //Check for the returning code | |
String payload = http.getString(); | |
const size_t capacity = JSON_OBJECT_SIZE(15) + 550; | |
DynamicJsonDocument doc(capacity); | |
DeserializationError error = deserializeJson(doc, payload); | |
http.end(); | |
if (error) { | |
Serial.print(F("deserializeJson() failed(current time): ")); | |
Serial.println(error.c_str()); | |
return; | |
} | |
currentTime = doc["unixtime"]; | |
Serial.print("current time= "); | |
Serial.println(currentTime); | |
} else { | |
Serial.println("Error on HTTP request"); | |
} | |
} | |
void apiCall() { | |
if ((WiFi.status() == WL_CONNECTED)) { | |
getCurrentTime(); //get the current time :) | |
HTTPClient http; | |
http.begin("http://api.open-notify.org/iss-pass.json?lat=" + String(latitude) + "&lon=" + String(longitude) + "&alt=" + String(myAltitude) + "&n=5"); //URL for API Call | |
int httpCode = http.GET(); | |
Serial.println(httpCode); | |
if (httpCode == 200) { | |
String payload = http.getString(); | |
const size_t capacity = JSON_ARRAY_SIZE(5) + 5 * JSON_OBJECT_SIZE(2) + JSON_OBJECT_SIZE(3) + JSON_OBJECT_SIZE(5) + 190; | |
DynamicJsonDocument doc(capacity); | |
DeserializationError error = deserializeJson(doc, payload); | |
http.end(); | |
if (error) { | |
Serial.print(F("deserializeJson() failed: ")); | |
Serial.println(error.c_str()); | |
return; | |
} | |
JsonArray response = doc["response"]; | |
duration = response[0]["duration"]; //Duration of the next flyover | |
riseTime = response[0]["risetime"]; //Time when the ISS rises | |
if (riseTime < currentTime) { //If the last flyover is already over...take the next one. | |
duration = response[1]["duration"]; | |
riseTime = response[1]["risetime"]; | |
} | |
Serial.print("Risetime = "); | |
Serial.println(riseTime); | |
DateTime time = riseTime + 7200; //IMPORTANT: Adjust to your deviation from UTC | |
String flyoverDate = time.timestamp(DateTime::TIMESTAMP_DATE); | |
String flyoverTime = time.timestamp(DateTime::TIMESTAMP_TIME); | |
Serial.println(flyoverDate); | |
Serial.println(flyoverTime); | |
display.clearDisplay(); | |
display.setCursor(35, 7); | |
display.println(flyoverDate); | |
display.setCursor(40, 23); | |
display.println(flyoverTime); | |
display.display(); | |
} | |
else { | |
Serial.println("Error on HTTP request"); | |
} | |
} | |
} | |
void setup() { | |
pinMode (12, OUTPUT); //LED Pin (on ESP8266 -> D6) | |
Serial.begin(115200); | |
if (!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { //Display address: 0x3C | |
Serial.println(F("SSD1306 allocation failed")); | |
for (;;); | |
} | |
display.setTextSize(1); | |
display.setTextColor(WHITE); | |
WiFi.begin(ssid, password); | |
while (WiFi.status() != WL_CONNECTED) { | |
delay(1000); | |
display.clearDisplay(); | |
display.setCursor(0, 10); | |
display.println("Connecting to WiFi..."); | |
display.display(); | |
} | |
delay(1000); | |
display.clearDisplay(); | |
display.setCursor(0, 10); | |
display.println("Hello, world!"); | |
display.display(); | |
} | |
void loop() { | |
apiCall(); //Call the API for ISS flyovers | |
while (riseTime != currentTime) { | |
delay(1000); | |
currentTime += 1; | |
Serial.println(currentTime); | |
if ((riseTime - currentTime) <= 60 && riseTime > currentTime) { | |
digitalWrite(12, HIGH); | |
} | |
} | |
if (riseTime == currentTime) { | |
int maxDuration = duration; //Save max value of duration for later mapping | |
for (duration; duration >= 0; duration--) { | |
display.clearDisplay(); | |
int xOnDisplay = map(duration, maxDuration, 0, -94, 128); //Calculate animation on display | |
display.drawBitmap(xOnDisplay, 0, iss, 128, 32, WHITE); //show animation | |
display.display(); | |
delay(1000); | |
} | |
digitalWrite(12, LOW); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment