Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /* ==================================================================================
- Arduino IDE - board: ESP32 Dev Module of DOIT ESP32 DEVKIT V1
- sketch voor ESP32-3248S035 - https://nl.aliexpress.com/item/1005006398547061.html
- De ESP moet de huidige tijd hebben, om de string te kunnen samenstellen
- om de juiste link aan te maken (met epochtijd in dit voorbeeld):
- https://api.energy-charts.info/price?bzn=BE&start=1715503187&end=1715632787
- =====================================================================================
- In de JSON die de API retourneert zit per paar
- - UNIX-tijd (epochtijd: aantal seconden sinds 1/1/1970 middernacht), per uur oplopend
- - de prijs per MWh voor dat uur
- =====================================================================================
- Zie https://shorturl.at/gjlLX voor een grafische weergave van dezelfde gegevens
- De API geeft niet altijd evenveel elementen terug. Dit varieert volgens het uur
- tussen 11 en 36 items. De code moet daar uiteraard op inspelen.
- Elk uur (HH:01:02) wordt de ESP herstart (opzettelijk niet HH:00:00 gekozen)
- =====================================================================================
- De sketch kan de gegevens weergeven op het display
- * cijfermatig in een lijst
- * in een grafiek
- De gebruiker kan dit kiezen met de flashknop (toggle). De voorkeur wordt opgeslagen in
- het flash-geheugen, zodat bij herstart de keuze onthouden wordt.
- */
- #include <TFT_eSPI.h> // https://github.com/Bodmer/TFT_eSPI
- #include <WiFiManager.h> // https://github.com/tzapu/WiFiManager/
- #include <ArduinoJson.h> // https://github.com/bblanchon/ArduinoJson
- #include <HTTPClient.h> // voor verbinding met API
- #include <Preferences.h> // https://github.com/vshymanskyy/Preferences
- TFT_eSPI tft = TFT_eSPI(); // User_Setup.h instellingen kan je vinden op https://espgo.be bij ESP32-3248S035
- WiFiManager myWiFi;
- Preferences flash;
- #define API_ITEMS 36 // max aantal API-records die je wil verwerken
- #define WAARDE_ROOD 100 // stroomprijs in rode kleur indien hoger dan deze waarde
- #define UTC_OFFSET_ZOMER 7200
- #define UTC_OFFSET_WINTER 3600
- struct tm tInfo; // https://cplusplus.com/reference/ctime/tm/
- bool grafiek = false; // er is weergave in cijfers en ook in grafiek (toggle met flashknop)
- const char* time_Zone = "CET-1CEST,M3.5.0,M10.5.0/3"; // https://github.com/nayarsystems/posix_tz_db/blob/master/zones.csv
- char* verbind[] = { "WiFi: geen verbinding", "Verbind met hotspot", "S035_ESP", "Start een browser op adres",
- "192.168.4.1", "om netwerk en paswoord", "in te brengen" };
- double prijzen[API_ITEMS]; // de prijzen in de API
- time_t epo[API_ITEMS]; // voor de epochtijden uit de Json
- String mijnLink = "https://api.energy-charts.info/price?bzn=BE&start="; // link wordt verderop aangevuld met de tijden
- void setup() {
- Serial.begin(115200);
- pinMode(16, OUTPUT), digitalWrite(16, HIGH); // LED groen uit
- pinMode(17, OUTPUT), digitalWrite(17, HIGH); // LED blauw uit
- tft.init();
- tft.setRotation(3); // USB bovenaan
- tft.fillScreen(TFT_BLACK); // schermen van vorige sessies wissen
- showLogoWiFi(TFT_GREEN);
- myWiFi.setAPCallback(toonBerichtGeenVerbinding); // indien geen WiFi gevonden wordt
- myWiFi.autoConnect("S035_ESP"); // verbinden met laatst gekende WiFi, zoniet start access point "S035_ESP"
- configTzTime(time_Zone, "be.pool.ntp.org");
- tft.fillScreen(TFT_BLACK);
- tft.drawCentreString("Tijd SNTP Ophalen", 240, 160, 4);
- getLocalTime(&tInfo);
- tft.fillScreen(TFT_BLACK);
- tft.setTextColor(TFT_ORANGE);
- tft.drawCentreString("Json Data Ophalen", 240, 160, 4);
- ophalen_Data();
- flash.begin("grafi", true); // flash uitlezen (true = read only)
- grafiek = flash.getBool("grafiek", 0); // voorkeur weergave ophalen - default naar "false"
- flash.end();
- (grafiek) ? tonen_Grafiek() : tonen_Data(); // weergeven volgens eerder opgeslagen voorkeur
- }
- void loop() {
- toonTijd();
- if (!digitalRead(0)) wijzigWeergave(); // flashknop wijzigt tussen grafiek of lijst met cijfers
- // if (prijzen[0] < 0) opladenThuisBatterij(); // prijzen[0] = prijs tijdens het actuele uur
- }
- void wijzigWeergave() {
- grafiek = !grafiek;
- (grafiek) ? tonen_Grafiek() : tonen_Data();
- flash.begin("grafi"); // flashgeheugen, ook schrijven want geen 2de parameter
- flash.putBool("grafiek", grafiek); // voorkeur opslaan
- flash.end();
- delay(800); // UI debouncing voor indrukken knop
- }
- void showLogoWiFi(uint32_t myColor) { // 3 lijnen code = kleiner en sneller dan grafisch bestand laden
- tft.fillCircle(240, 160, 6, myColor);
- for (byte i = 0; i < 4; i++) tft.drawSmoothArc(240, 160, 37 - i * 7, 35 - i * 7, 135, 225, myColor, myColor, true);
- }
- void toonTijd() { // toont ook de actuele stroomprijs
- char theDate[11];
- getLocalTime(&tInfo); // SNTP bij opstart en daarna elke 3 uur op een ESP32
- tft.drawRect(-1, 26, 482, 2, WiFi.isConnected() ? TFT_GREEN : TFT_RED); // lijnen zijn groen als WiFi verbonden is
- tft.setTextColor(TFT_CYAN, TFT_BLACK);
- tft.setCursor(0, 0, 4);
- strftime(theDate, sizeof(theDate), "%d-%m-%G", &tInfo); // https://cplusplus.com/reference/ctime/strftime/
- tft.print(theDate);
- tft.setCursor(tft.getCursorX() + 8, 0);
- tft.printf("%02d:%02d:%02d", tInfo.tm_hour, tInfo.tm_min, tInfo.tm_sec);
- tft.setCursor(tft.getCursorX() + 35, 0);
- tft.setTextColor(TFT_MAGENTA, TFT_BLACK);
- tft.print("/MWh: ");
- tft.setTextColor(prijzen[0] > 100 ? TFT_RED : TFT_GREEN);
- if (prijzen[0] < 0) tft.setTextColor(TFT_YELLOW);
- tft.printf("%3.2F", prijzen[0]);
- if ((tInfo.tm_min == 1) && (tInfo.tm_sec == 2)) ESP.restart(); // refresh elk uur gegevens
- }
- void ophalen_Data() { // string met tijden klaarzetten en energiedata opvragen
- time_t now; // time_t is eigenlijk een uint32_t
- time(&now); // epochtijd toekennen
- now = now - (now % 3600); // naar onder afronden op gehele uur
- now = now + ((tInfo.tm_isdst) ? UTC_OFFSET_ZOMER : UTC_OFFSET_WINTER); // eerst weergegeven gegevens bij voorkeur in lokale tijd
- mijnLink = mijnLink + String(now) + "&end=" + String(now + (API_ITEMS * 3600));
- Serial.println(mijnLink);
- if (mijnLink.length() > 51) get_JsonData(); // lege invoer niet versturen (bvb. als SNTP een timeout geeft)
- else { // samenstellen string (om naar API te versturen) = mislukt
- tft.fillRect(0, 200, 320, 40, TFT_BLACK);
- tft.drawCentreString("Link API onvolledig", 160, 200, 4);
- }
- tft.fillCircle(255, 9, 9, TFT_MAGENTA); // euro symbool: zit niet bij de fonts
- tft.fillCircle(255, 9, 7, TFT_BLACK), tft.fillRect(258, 4, 8, 12, TFT_BLACK);
- tft.drawRect(247, 7, 9, 2, TFT_MAGENTA), tft.drawRect(249, 10, 6, 2, TFT_MAGENTA);
- }
- void tonen_Grafiek() { // Json gegevens in grafiek tonen op display
- tft.fillRect(0, 28, 480, 290, TFT_BLACK);
- tft.setTextColor(TFT_WHITE);
- for (uint8_t i = 0; i < 6; i++) { // lijnen met waarden tekenen: i voor de verticale coördinaten
- tft.drawFastHLine(0, 40 + i * 50, 480, tft.color565(64, 64, 64));
- for (uint8_t j = 0; j < 3; j++) // j verwerkt de horizontale coördinaat
- tft.drawRightString(String(i * 50 - 50), j * 228 + 23, 286 - i * 50, 1);
- }
- for (uint8_t i = 0; i < API_ITEMS; i++) {
- if (epo[i]) { // lege waarden niet weergeven
- uint16_t mijnKleur = prijzen[i] < WAARDE_ROOD ? TFT_GREEN : TFT_RED;
- if (prijzen[i] < 0) mijnKleur = TFT_YELLOW, tft.fillRect(i * 14, 240, 13, 0 - prijzen[i], mijnKleur);
- else tft.fillRect(i * 14, 240 - prijzen[i], 13, prijzen[i], mijnKleur);
- struct tm* cor; // om de epochtijden om te zetten naar tm-structuur in lokale (geCORrigeerde) tijd
- cor = localtime(&epo[i]); // epochtijden in de lijst aanpassen aan lokale tijd / zomertijd
- tft.setTextColor(prijzen[i] > 0 ? TFT_BLACK : TFT_YELLOW);
- tft.setCursor(1 + i * 14, 230, 1); // uren onderaan grafiek
- tft.printf("%02d", cor->tm_hour);
- tft.setTextColor(TFT_RED);
- tft.setCursor(1 + i * 14, 243, 1);
- tft.printf("%02d", cor->tm_hour);
- }
- }
- }
- void tonen_Data() { // Json gegevens weergeven in lijst met 2 rijen van uren / prijzen
- tft.fillRect(0, 28, 480, 290, TFT_BLACK);
- tft.drawRect(240, 26, 2, 292, WiFi.isConnected() ? TFT_GREEN : TFT_RED);
- for (uint8_t i = 0; i < API_ITEMS; i++) {
- if (epo[i]) { // er worden niet altijd evenveel waarden geretourneerd door de API - lege items niet weergeven
- tft.setTextColor(TFT_LIGHTGREY, TFT_BLACK);
- tft.setCursor(((i < 18) ? 0 : 260), 33 + (i % 18) * 16, 2);
- tft.printf(" %02d. ", i + 1);
- tft.setTextColor(TFT_CYAN, TFT_BLACK);
- struct tm* cor; // om de epochtijden om te zetten naar tm-structuur in lokale (geCORrigeerde) tijd
- cor = localtime(&epo[i]); // epochtijden in de lijst aanpassen aan lokale tijd / zomertijd
- tft.printf("%02d-%02d-%02d %02d:%02d", cor->tm_mday, cor->tm_mon + 1, cor->tm_year + 1900, cor->tm_hour, cor->tm_min);
- tft.setTextColor((prijzen[i] < WAARDE_ROOD) ? TFT_GREEN : TFT_RED); // geel < 0 - blauw tss 0/100 - rood > 100
- if (prijzen[i] < 0) tft.setTextColor(TFT_YELLOW, TFT_BLACK);
- tft.drawRightString(String(prijzen[i]), (i < 18 ? 220 : 480), 33 + (i % 18) * 16, 2);
- }
- }
- }
- void get_JsonData() {
- HTTPClient http;
- http.begin(mijnLink);
- if (http.GET() == 200) {
- DynamicJsonDocument doc(4096); // waarde groot genoeg kiezen om de data te bevatten
- auto error = deserializeJson(doc, http.getString());
- if (error) {
- tft.drawCentreString("deserializeJson() failed", 240, 200, 4);
- tft.drawCentreString(error.c_str(), 240, 250, 4);
- }
- for (uint8_t i = 0; i < API_ITEMS; i++) {
- prijzen[i] = doc["price"][i];
- epo[i] = doc["unix_seconds"][i];
- }
- } else tft.drawCentreString("Error in API response", 240, 160, 4);
- http.end();
- }
- void toonBerichtGeenVerbinding(WiFiManager* myWiFi) { // gestart als WiFi-verbinding niet lukt
- tft.fillScreen(TFT_NAVY);
- tft.setTextColor(TFT_YELLOW), tft.setTextFont(4);
- for (uint8_t i = 0; i < 7; i++) tft.drawCentreString(verbind[i], 240, 40 + i * 30, 4);
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement