A lot of memory consumption improvements

This commit is contained in:
Djuri Baars 2023-10-28 20:31:10 +02:00
parent 0bf60d160f
commit e1648a9a42
24 changed files with 135 additions and 105 deletions

View file

@ -24,4 +24,6 @@
#define USER_AGENT "BTClock/1.0" #define USER_AGENT "BTClock/1.0"
#define NUM_SCREENS 7
#define I2C_DEV_ADDR 0x55 #define I2C_DEV_ADDR 0x55

View file

@ -43,6 +43,14 @@ void setupSoftAP()
void setupComponents() void setupComponents()
{ {
if (psramInit())
{
Serial.println("\nPSRAM is correctly initialized");
}
else
{
Serial.println("PSRAM not available");
}
#ifdef WITH_RGB_LED #ifdef WITH_RGB_LED
pixels.begin(); pixels.begin();
pixels.setPixelColor(0, pixels.Color(255, 0, 0)); pixels.setPixelColor(0, pixels.Color(255, 0, 0));
@ -299,7 +307,6 @@ void toggleScreenTimer()
} }
} }
void timebasedChangeTask(void *parameter) void timebasedChangeTask(void *parameter)
{ {
uint32_t moment = millis(); uint32_t moment = millis();
@ -393,7 +400,7 @@ void setLights(int r, int g, int b)
void flashTemporaryLights(int r, int g, int b) void flashTemporaryLights(int r, int g, int b)
{ {
#ifdef WITH_RGB_LED #ifdef WITH_RGB_LED
uint32_t oldLights[NEOPIXEL_COUNT]; uint32_t oldLights[NEOPIXEL_COUNT];
@ -404,7 +411,8 @@ void flashTemporaryLights(int r, int g, int b)
} }
// flash three times in given color // flash three times in given color
for (int t = 0; t < 3; t++) { for (int t = 0; t < 3; t++)
{
for (int i = 0; i < NEOPIXEL_COUNT; i++) for (int i = 0; i < NEOPIXEL_COUNT; i++)
{ {
pixels.setPixelColor(i, pixels.Color(r, g, b)); pixels.setPixelColor(i, pixels.Color(r, g, b));
@ -425,7 +433,7 @@ void flashTemporaryLights(int r, int g, int b)
} }
pixels.show(); pixels.show();
#endif #endif
} }
void setupI2C() void setupI2C()

View file

@ -36,7 +36,6 @@ void setupWebserver()
AsyncCallbackJsonWebHandler *handler = new AsyncCallbackJsonWebHandler("/api/show/custom", onApiShowTextAdvanced); AsyncCallbackJsonWebHandler *handler = new AsyncCallbackJsonWebHandler("/api/show/custom", onApiShowTextAdvanced);
server.addHandler(handler); server.addHandler(handler);
server.on("/api/wifi/scan", HTTP_GET, onApiWifiScan);
server.on("/api/restart", HTTP_GET, onApiRestart); server.on("/api/restart", HTTP_GET, onApiRestart);
server.on("/api/countdown", HTTP_GET, onApiCountdown); server.on("/api/countdown", HTTP_GET, onApiCountdown);
@ -76,7 +75,7 @@ void onApiStatus(AsyncWebServerRequest *request)
{ {
AsyncResponseStream *response = request->beginResponseStream("application/json"); AsyncResponseStream *response = request->beginResponseStream("application/json");
DynamicJsonDocument root(1024); StaticJsonDocument<512> root;
root["currentScreen"] = String(getCurrentScreen()); root["currentScreen"] = String(getCurrentScreen());
root["timerRunning"] = timerRunning; root["timerRunning"] = timerRunning;
@ -169,7 +168,7 @@ void onApiActionUpdate(AsyncWebServerRequest *request)
*/ */
void onApiSettingsGet(AsyncWebServerRequest *request) void onApiSettingsGet(AsyncWebServerRequest *request)
{ {
DynamicJsonDocument root(1024); StaticJsonDocument<768> root;
root["fgColor"] = getFgColor(); root["fgColor"] = getFgColor();
root["bgColor"] = getBgColor(); root["bgColor"] = getBgColor();
root["timerSeconds"] = timerSeconds; root["timerSeconds"] = timerSeconds;
@ -208,9 +207,10 @@ void onApiSettingsGet(AsyncWebServerRequest *request)
o["enabled"] = preferences.getBool(key.c_str(), true); o["enabled"] = preferences.getBool(key.c_str(), true);
} }
String responseText; AsyncResponseStream *response = request->beginResponseStream("application/json");
serializeJson(root, responseText); serializeJson(root, *response);
request->send(200, "application/json", responseText);
request->send(response);
} }
bool processEpdColorSettings(AsyncWebServerRequest *request) bool processEpdColorSettings(AsyncWebServerRequest *request)
@ -440,27 +440,27 @@ void onApiRestart(AsyncWebServerRequest *request)
esp_restart(); esp_restart();
} }
void onApiWifiScan(AsyncWebServerRequest *request) // void onApiWifiScan(AsyncWebServerRequest *request)
{ // {
WiFi.scanNetworks(true); // WiFi.scanNetworks(true);
int n = WiFi.scanComplete(); // int n = WiFi.scanComplete();
DynamicJsonDocument doc(1024); // DynamicJsonDocument doc(1024);
for (int i = 0; i < n; ++i) // for (int i = 0; i < n; ++i)
{ // {
JsonObject wifi = doc.createNestedObject(WiFi.BSSID(i)); // JsonObject wifi = doc.createNestedObject(WiFi.BSSID(i));
Serial.println(WiFi.SSID(i)); // Serial.println(WiFi.SSID(i));
wifi["ssid"] = WiFi.SSID(i); // wifi["ssid"] = WiFi.SSID(i);
wifi["rssi"] = WiFi.RSSI(i); // wifi["rssi"] = WiFi.RSSI(i);
wifi["encryptionType"] = WiFi.encryptionType(i); // wifi["encryptionType"] = WiFi.encryptionType(i);
} // }
String responseText; // String responseText;
serializeJson(doc, responseText); // serializeJson(doc, responseText);
request->send(200, "application/json", responseText); // request->send(200, "application/json", responseText);
} // }
void onApiCountdown(AsyncWebServerRequest *request) void onApiCountdown(AsyncWebServerRequest *request)
{ {
@ -514,14 +514,14 @@ void onApiSystemStatus(AsyncWebServerRequest *request)
{ {
AsyncResponseStream *response = request->beginResponseStream("application/json"); AsyncResponseStream *response = request->beginResponseStream("application/json");
DynamicJsonDocument root(1024); StaticJsonDocument<128> root;
root["espFreeHeap"] = ESP.getFreeHeap(); root["espFreeHeap"] = ESP.getFreeHeap();
root["espHeapSize"] = ESP.getHeapSize(); root["espHeapSize"] = ESP.getHeapSize();
root["espFreePsram"] = ESP.getFreePsram(); root["espFreePsram"] = ESP.getFreePsram();
root["espPsramSize"] = ESP.getPsramSize(); root["espPsramSize"] = ESP.getPsramSize();
String responseText; serializeJson(root, *response);
serializeJson(root, responseText);
request->send(200, "application/json", responseText); request->send(response);
} }

View file

@ -26,7 +26,7 @@ void onApiShowTextAdvanced(AsyncWebServerRequest *request, JsonVariant &json);
void onApiFullRefresh(AsyncWebServerRequest *request); void onApiFullRefresh(AsyncWebServerRequest *request);
void onApiCountdown(AsyncWebServerRequest *request); void onApiCountdown(AsyncWebServerRequest *request);
void onApiWifiScan(AsyncWebServerRequest *request); //void onApiWifiScan(AsyncWebServerRequest *request);
void onApiRestart(AsyncWebServerRequest *request); void onApiRestart(AsyncWebServerRequest *request);
void onApiLightsOff(AsyncWebServerRequest *request); void onApiLightsOff(AsyncWebServerRequest *request);

View file

@ -1,7 +1,10 @@
#include "blockheight.hpp" #include "blockheight.hpp"
uint BlockHeightScreen::blockNr = 0; uint BlockHeightScreen::blockNr = 0;
std::array<String, 7> BlockHeightScreen::epdContent = { "", "", "", "", "", "", "" }; std::array<String, NUM_SCREENS> BlockHeightScreen::epdContent = { "", "", "", "", "", "", "" };
//std::array<String, NUM_SCREENS> * BlockHeightScreen::epdContent = (std::array<String, NUM_SCREENS> * ) ps_malloc(7 * sizeof (std::array<String, NUM_SCREENS>));
void BlockHeightScreen::init() void BlockHeightScreen::init()
{ {
@ -13,9 +16,9 @@ void BlockHeightScreen::init()
void BlockHeightScreen::showScreen() void BlockHeightScreen::showScreen()
{ {
std::string blockNrString = String(BlockHeightScreen::blockNr).c_str(); std::string blockNrString = String(BlockHeightScreen::blockNr).c_str();
blockNrString.insert(blockNrString.begin(), 7 - blockNrString.length(), ' '); blockNrString.insert(blockNrString.begin(), NUM_SCREENS - blockNrString.length(), ' ');
epdContent[0] = "BLOCK/HEIGHT"; epdContent[0] = "BLOCK/HEIGHT";
for (uint i = 1; i < 7; i++) for (uint i = 1; i < NUM_SCREENS; i++)
{ {
BlockHeightScreen::epdContent[i] = blockNrString[i]; BlockHeightScreen::epdContent[i] = blockNrString[i];
} }

View file

@ -9,10 +9,10 @@
class BlockHeightScreen { class BlockHeightScreen {
protected: protected:
static uint blockNr; static uint blockNr;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static void onNewBlock(uint blockNr); static void onNewBlock(uint blockNr);
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
}; };

View file

@ -2,7 +2,7 @@
uint CountdownScreen::countdownMinutes = 1; uint CountdownScreen::countdownMinutes = 1;
uint CountdownScreen::countdownSeconds = 0; uint CountdownScreen::countdownSeconds = 0;
std::array<String, 7> CountdownScreen::epdContent = {"COUNT/DOWN", "", "", "", "", "", ""}; std::array<String, NUM_SCREENS> CountdownScreen::epdContent = {"COUNT/DOWN", "", "", "", "", "", ""};
void CountdownScreen::init() void CountdownScreen::init()
{ {
@ -14,7 +14,7 @@ void CountdownScreen::showScreen()
} }
std::array<String, 7> CountdownScreen::getEpdContent() std::array<String, NUM_SCREENS> CountdownScreen::getEpdContent()
{ {
return CountdownScreen::epdContent; return CountdownScreen::epdContent;
} }
@ -27,10 +27,10 @@ void CountdownScreen::countdownTask(void *pvParameters)
{ {
for (int i = CountdownScreen::countdownSeconds; i >= 0; i--) for (int i = CountdownScreen::countdownSeconds; i >= 0; i--)
{ {
char countdownString[7]; char countdownString[NUM_SCREENS];
sprintf(countdownString, "%02d:%02d", i / 60, i % 60); sprintf(countdownString, "%02d:%02d", i / 60, i % 60);
std::string timeString = countdownString; std::string timeString = countdownString;
timeString.insert(timeString.begin(), 7 - timeString.length(), ' '); timeString.insert(timeString.begin(), NUM_SCREENS - timeString.length(), ' ');
CountdownScreen::epdContent[0] = "COUNT/DOWN"; CountdownScreen::epdContent[0] = "COUNT/DOWN";
for (uint i = 1; i < 7; i++) for (uint i = 1; i < 7; i++)
{ {

View file

@ -11,11 +11,11 @@ class CountdownScreen {
protected: protected:
static uint countdownMinutes; static uint countdownMinutes;
static uint countdownSeconds; static uint countdownSeconds;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
static void setCountdownSeconds(uint sec); static void setCountdownSeconds(uint sec);
static void countdownTask(void *pvParameters); static void countdownTask(void *pvParameters);
}; };

View file

@ -1,7 +1,7 @@
#include "custom_text.hpp" #include "custom_text.hpp"
std::string CustomTextScreen::customText = ""; std::string CustomTextScreen::customText = "";
std::array<String, 7> CustomTextScreen::epdContent = {"", "", "", "", "", "", ""}; std::array<String, NUM_SCREENS> CustomTextScreen::epdContent = {"", "", "", "", "", "", ""};
void CustomTextScreen::init() void CustomTextScreen::init()
{ {
@ -12,11 +12,11 @@ void CustomTextScreen::showScreen()
{ {
} }
void CustomTextScreen::setSimpleText(String text) void CustomTextScreen::setSimpleText(const String& text)
{ {
customText = text.c_str(); customText = text.c_str();
customText.insert(customText.begin(), 7 - customText.length(), ' '); customText.insert(customText.begin(), NUM_SCREENS - customText.length(), ' ');
for (uint i = 0; i < 7; i++) for (uint i = 0; i < 7; i++)
{ {
@ -24,7 +24,7 @@ void CustomTextScreen::setSimpleText(String text)
} }
} }
void CustomTextScreen::setText(std::array<String, 7> customContent) void CustomTextScreen::setText(std::array<String, NUM_SCREENS> customContent)
{ {
epdContent = customContent; epdContent = customContent;
} }

View file

@ -10,11 +10,11 @@
class CustomTextScreen { class CustomTextScreen {
protected: protected:
static std::string customText; static std::string customText;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
static void setSimpleText(String text); static void setSimpleText(const String& text);
static void setText(std::array<String, 7> customContent); static void setText(std::array<String, 7> customContent);
}; };

View file

@ -3,7 +3,7 @@
uint HalvingCountdownScreen::currentBlockNr = 0; uint HalvingCountdownScreen::currentBlockNr = 0;
uint HalvingCountdownScreen::halvingBlockNr = 0; uint HalvingCountdownScreen::halvingBlockNr = 0;
std::array<String, 7> HalvingCountdownScreen::epdContent = {"", "", "", "", "", "", ""}; std::array<String, NUM_SCREENS> HalvingCountdownScreen::epdContent = {"", "", "", "", "", "", ""};
void HalvingCountdownScreen::init() void HalvingCountdownScreen::init()
{ {
@ -44,7 +44,7 @@ void HalvingCountdownScreen::onNewBlock(uint blockNr)
HalvingCountdownScreen::showScreen(); HalvingCountdownScreen::showScreen();
} }
std::array<String, 7> HalvingCountdownScreen::getEpdContent() std::array<String, NUM_SCREENS> HalvingCountdownScreen::getEpdContent()
{ {
return HalvingCountdownScreen::epdContent; return HalvingCountdownScreen::epdContent;
} }

View file

@ -10,11 +10,11 @@ class HalvingCountdownScreen {
protected: protected:
static uint currentBlockNr; static uint currentBlockNr;
static uint halvingBlockNr; static uint halvingBlockNr;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static void onNewBlock(uint blockNr); static void onNewBlock(uint blockNr);
static uint getNextHalvingBlockNr(); static uint getNextHalvingBlockNr();
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
}; };

View file

@ -1,7 +1,7 @@
#include "sats_per_dollar.hpp" #include "sats_per_dollar.hpp"
uint SatsPerDollarScreen::satsPerDollar = 0; uint SatsPerDollarScreen::satsPerDollar = 0;
std::array<String, 7> SatsPerDollarScreen::epdContent = { "", "", "", "", "", "", "" }; std::array<String, NUM_SCREENS> SatsPerDollarScreen::epdContent = { "", "", "", "", "", "", "" };
void SatsPerDollarScreen::init() { void SatsPerDollarScreen::init() {
SatsPerDollarScreen::satsPerDollar = int(round(1 / preferences.getFloat("btcPrice", 12345) * 10e7)); SatsPerDollarScreen::satsPerDollar = int(round(1 / preferences.getFloat("btcPrice", 12345) * 10e7));
@ -13,7 +13,7 @@ void SatsPerDollarScreen::showScreen() {
std::string satsPerDollarString = String(SatsPerDollarScreen::satsPerDollar).c_str(); std::string satsPerDollarString = String(SatsPerDollarScreen::satsPerDollar).c_str();
satsPerDollarString.insert(satsPerDollarString.begin(), 7 - satsPerDollarString.length(), ' '); satsPerDollarString.insert(satsPerDollarString.begin(), 7 - satsPerDollarString.length(), ' ');
epdContent[0] = "MSCW/TIME"; epdContent[0] = "MSCW/TIME";
for (uint i = 1; i < 7; i++) for (uint i = 1; i < NUM_SCREENS; i++)
{ {
SatsPerDollarScreen::epdContent[i] = satsPerDollarString[i]; SatsPerDollarScreen::epdContent[i] = satsPerDollarString[i];
} }
@ -25,6 +25,6 @@ void SatsPerDollarScreen::onPriceUpdate(uint price) {
SatsPerDollarScreen::showScreen(); SatsPerDollarScreen::showScreen();
} }
std::array<String, 7> SatsPerDollarScreen::getEpdContent() { std::array<String, NUM_SCREENS> SatsPerDollarScreen::getEpdContent() {
return SatsPerDollarScreen::epdContent; return SatsPerDollarScreen::epdContent;
} }

View file

@ -8,10 +8,10 @@
class SatsPerDollarScreen { class SatsPerDollarScreen {
protected: protected:
static uint satsPerDollar; static uint satsPerDollar;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static void onPriceUpdate(uint price); static void onPriceUpdate(uint price);
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
}; };

View file

@ -1,7 +1,7 @@
#include "ticker.hpp" #include "ticker.hpp"
uint TickerScreen::price = 12345; uint TickerScreen::price = 12345;
std::array<String, 7> TickerScreen::epdContent = { "", "", "", "", "", "", "" }; std::array<String, NUM_SCREENS> TickerScreen::epdContent = { "", "", "", "", "", "", "" };
void TickerScreen::init() { void TickerScreen::init() {
TickerScreen::price = preferences.getFloat("btcPrice", 12345);; TickerScreen::price = preferences.getFloat("btcPrice", 12345);;
@ -11,9 +11,9 @@ void TickerScreen::init() {
void TickerScreen::showScreen() { void TickerScreen::showScreen() {
std::string priceString = ("$" + String(TickerScreen::price)).c_str(); std::string priceString = ("$" + String(TickerScreen::price)).c_str();
priceString.insert(priceString.begin(), 7 - priceString.length(), ' '); priceString.insert(priceString.begin(), NUM_SCREENS - priceString.length(), ' ');
epdContent[0] = "BTC/USD"; epdContent[0] = "BTC/USD";
for (uint i = 1; i < 7; i++) for (uint i = 1; i < NUM_SCREENS; i++)
{ {
TickerScreen::epdContent[i] = priceString[i]; TickerScreen::epdContent[i] = priceString[i];
} }
@ -24,6 +24,6 @@ void TickerScreen::onPriceUpdate(uint price) {
TickerScreen::showScreen(); TickerScreen::showScreen();
} }
std::array<String, 7> TickerScreen::getEpdContent() { std::array<String, NUM_SCREENS> TickerScreen::getEpdContent() {
return TickerScreen::epdContent; return TickerScreen::epdContent;
} }

View file

@ -9,11 +9,11 @@ class TickerScreen
{ {
protected: protected:
static uint price; static uint price;
static std::array<String, 7> epdContent; static std::array<String, NUM_SCREENS> epdContent;
public: public:
static void init(); static void init();
static void showScreen(); static void showScreen();
static void onPriceUpdate(uint price); static void onPriceUpdate(uint price);
static std::array<String, 7> getEpdContent(); static std::array<String, NUM_SCREENS> getEpdContent();
}; };

View file

@ -1,8 +1,6 @@
#include "time.hpp" #include "time.hpp"
String TimeScreen::timeString = ""; std::array<String, NUM_SCREENS> TimeScreen::epdContent = { "", "", "", "", "", "", "" };
String TimeScreen::dateString = "";
std::array<String, 7> TimeScreen::epdContent = { "", "", "", "", "", "", "" };
void TimeScreen::init() { void TimeScreen::init() {
setupMinuteEvent(); setupMinuteEvent();
@ -10,13 +8,13 @@ void TimeScreen::init() {
} }
void TimeScreen::showScreen() { void TimeScreen::showScreen() {
TimeScreen::dateString = String(rtc.getDay()) + "/" + String(rtc.getMonth() + 1); // String(String(rtc.getDay()) + "/" + String(rtc.getMonth() + 1)).toCharArray(TimeScreen::dateString, 5);
TimeScreen::timeString = rtc.getTime("%H:%M").c_str(); // rtc.getTime("%H:%M").toCharArray(TimeScreen::timeString, 5);
std::string timeString = TimeScreen::timeString.c_str(); std::string timeString = rtc.getTime("%H:%M").c_str();
timeString.insert(timeString.begin(), 7 - timeString.length(), ' '); timeString.insert(timeString.begin(), NUM_SCREENS - timeString.length(), ' ');
TimeScreen::epdContent[0] = TimeScreen::dateString; TimeScreen::epdContent[0] = String(rtc.getDay()) + "/" + String(rtc.getMonth() + 1);
for (uint i = 1; i < 7; i++) for (uint i = 1; i < NUM_SCREENS; i++)
{ {
TimeScreen::epdContent[i] = timeString[i]; TimeScreen::epdContent[i] = timeString[i];
} }
@ -30,7 +28,7 @@ void TimeScreen::onActivate() {
TimeScreen::showScreen(); TimeScreen::showScreen();
} }
std::array<String, 7> TimeScreen::getEpdContent() { std::array<String, NUM_SCREENS> TimeScreen::getEpdContent() {
return TimeScreen::epdContent; return TimeScreen::epdContent;
} }

View file

@ -7,8 +7,6 @@
class TimeScreen { class TimeScreen {
protected: protected:
static String timeString;
static String dateString;
static std::array<String, 7> epdContent; static std::array<String, 7> epdContent;
static TimeScreen* instance_; static TimeScreen* instance_;
public: public:

View file

@ -2,7 +2,7 @@
#include <Arduino.h> #include <Arduino.h>
//##include <Crypto.h> //##include <Crypto.h>
#include <ArduinoJson.h>
#include <WiFi.h> #include <WiFi.h>
#include <map> #include <map>
@ -50,4 +50,16 @@ const PROGMEM int SCREEN_COUNTDOWN = 98;
const PROGMEM int SCREEN_CUSTOM = 99; const PROGMEM int SCREEN_CUSTOM = 99;
const PROGMEM int screens[5] = { SCREEN_BLOCK_HEIGHT, SCREEN_MSCW_TIME, SCREEN_BTC_TICKER, SCREEN_TIME, SCREEN_HALVING_COUNTDOWN }; const PROGMEM int screens[5] = { SCREEN_BLOCK_HEIGHT, SCREEN_MSCW_TIME, SCREEN_BTC_TICKER, SCREEN_TIME, SCREEN_HALVING_COUNTDOWN };
const uint screenCount = sizeof(screens) / sizeof(int); const uint screenCount = sizeof(screens) / sizeof(int);
struct SpiRamAllocator {
void* allocate(size_t size) {
return ps_malloc(size);
}
void deallocate(void* pointer) {
free(pointer);
}
};
using SpiRamJsonDocument = BasicJsonDocument<SpiRamAllocator>;

View file

@ -1,6 +1,6 @@
#include "blocknotify.hpp" #include "blocknotify.hpp"
int currentBlockHeight = 789000; uint currentBlockHeight = 789000;
QueueHandle_t bitcoinQueue; QueueHandle_t bitcoinQueue;
BitcoinEvent bitcoinEvent; BitcoinEvent bitcoinEvent;
const String NEW_BLOCK_MINED_EVENT = "new_block_mined"; const String NEW_BLOCK_MINED_EVENT = "new_block_mined";
@ -17,7 +17,7 @@ bool useBitcoind = true;
void checkBitcoinBlock(void *pvParameters) void checkBitcoinBlock(void *pvParameters)
{ {
int blockHeight = preferences.getUInt("blockHeight", currentBlockHeight); uint blockHeight = preferences.getUInt("blockHeight", currentBlockHeight);
useBitcoind = preferences.getBool("useNode", false) && wifiClientInsecure.connect(preferences.getString("rpcHost", BITCOIND_HOST).c_str(), preferences.getUInt("rpcPort", BITCOIND_PORT)); useBitcoind = preferences.getBool("useNode", false) && wifiClientInsecure.connect(preferences.getString("rpcHost", BITCOIND_HOST).c_str(), preferences.getUInt("rpcPort", BITCOIND_PORT));
@ -26,7 +26,14 @@ void checkBitcoinBlock(void *pvParameters)
else else
Serial.println("bitcoind node is not reachable, using mempool API instead."); Serial.println("bitcoind node is not reachable, using mempool API instead.");
IPAddress result;
int err = WiFi.hostByName(preferences.getString("mempoolInstance", DEFAULT_MEMPOOL_INSTANCE).c_str(), result) ;
if (err != 1) {
flashTemporaryLights(255, 0, 0);
}
for (;;) for (;;)
{ {
HTTPClient http; HTTPClient http;

View file

@ -6,6 +6,7 @@
#include <freertos/FreeRTOS.h> #include <freertos/FreeRTOS.h>
#include <freertos/task.h> #include <freertos/task.h>
#include "base64.h" #include "base64.h"
#include "lib/functions.hpp"
#include "shared.hpp" #include "shared.hpp"
#include "config.h" #include "config.h"

View file

@ -6,9 +6,9 @@
// const int EPD_BUSY[7] = {16, 18, 37, 9, 7, 5, 3}; // const int EPD_BUSY[7] = {16, 18, 37, 9, 7, 5, 3};
// const int EPD_RESET_MPD[7] = {14, 13, 12, 11, 10, 9, 8}; // const int EPD_RESET_MPD[7] = {14, 13, 12, 11, 10, 9, 8};
const int EPD_CS[7] = {2, 4, 6, 10, 33, 21, 17}; const int EPD_CS[NUM_SCREENS] = {2, 4, 6, 10, 33, 21, 17};
const int EPD_BUSY[7] = {3, 5, 7, 9, 37, 18, 16}; const int EPD_BUSY[NUM_SCREENS] = {3, 5, 7, 9, 37, 18, 16};
const int EPD_RESET_MPD[7] = {8, 9, 10, 11, 12, 13, 14}; const int EPD_RESET_MPD[NUM_SCREENS] = {8, 9, 10, 11, 12, 13, 14};
const int EPD_DC = 14; const int EPD_DC = 14;
const int RST_PIN = 15; const int RST_PIN = 15;
@ -45,7 +45,8 @@ const int RST_PIN = 2;
#endif #endif
#ifdef IS_BW #ifdef IS_BW
GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT> displays[7] = {
GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT> displays[NUM_SCREENS] = {
GxEPD2_213_B74(EPD_CS[0], EPD_DC, /*RST=*/-1, EPD_BUSY[0]), GxEPD2_213_B74(EPD_CS[0], EPD_DC, /*RST=*/-1, EPD_BUSY[0]),
GxEPD2_213_B74(EPD_CS[1], EPD_DC, /*RST=*/-1, EPD_BUSY[1]), GxEPD2_213_B74(EPD_CS[1], EPD_DC, /*RST=*/-1, EPD_BUSY[1]),
GxEPD2_213_B74(EPD_CS[2], EPD_DC, /*RST=*/-1, EPD_BUSY[2]), GxEPD2_213_B74(EPD_CS[2], EPD_DC, /*RST=*/-1, EPD_BUSY[2]),
@ -55,6 +56,8 @@ GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT> displays[7] = {
GxEPD2_213_B74(EPD_CS[6], EPD_DC, /*RST=*/-1, EPD_BUSY[6]), GxEPD2_213_B74(EPD_CS[6], EPD_DC, /*RST=*/-1, EPD_BUSY[6]),
}; };
//GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT> * displays2 = (GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT> *) ps_malloc(7 * sizeof (GxEPD2_BW<GxEPD2_213_B74, GxEPD2_213_B74::HEIGHT>));
const int SEM_WAIT_TIME = 10000; const int SEM_WAIT_TIME = 10000;
#else #else
@ -72,13 +75,12 @@ const int SEM_WAIT_TIME = 30000;
#endif #endif
const uint displaySize = 7; uint32_t lastFullRefresh[NUM_SCREENS];
uint32_t lastFullRefresh[displaySize];
std::array<String, 7> currentEpdContent; std::array<String, 7> currentEpdContent;
std::array<String, 7> epdContent; std::array<String, 7> epdContent;
TaskHandle_t tasks[displaySize]; TaskHandle_t tasks[NUM_SCREENS];
SemaphoreHandle_t epdUpdateSemaphore[displaySize]; SemaphoreHandle_t epdUpdateSemaphore[NUM_SCREENS];
uint8_t qrcode[qrcodegen_BUFFER_LEN_MAX]; uint8_t qrcode[qrcodegen_BUFFER_LEN_MAX];
void setupDisplays() void setupDisplays()
@ -98,7 +100,7 @@ void resetAllDisplays()
digitalWrite(RST_PIN, HIGH); digitalWrite(RST_PIN, HIGH);
delay(200); delay(200);
#else #else
for (int i = 0; i < displaySize; i++) { for (int i = 0; i < NUM_SCREENS; i++) {
resetSingleDisplay(i); resetSingleDisplay(i);
} }
#endif NO_MCP #endif NO_MCP
@ -118,7 +120,7 @@ void resetSingleDisplay(int i)
void initDisplays() void initDisplays()
{ {
for (uint i = 0; i < displaySize; i++) for (uint i = 0; i < NUM_SCREENS; i++)
{ {
#ifndef NO_MCP #ifndef NO_MCP
mcp.pinMode(EPD_RESET_MPD[i], OUTPUT); mcp.pinMode(EPD_RESET_MPD[i], OUTPUT);
@ -131,8 +133,7 @@ void initDisplays()
// displays[i].epd2.init(SW_SCK, SW_MOSI, 115200, true, 20, false); // displays[i].epd2.init(SW_SCK, SW_MOSI, 115200, true, 20, false);
} }
std::string text = "BTClock"; for (uint i = 0; i < NUM_SCREENS; i++)
for (uint i = 0; i < displaySize; i++)
{ {
epdUpdateSemaphore[i] = xSemaphoreCreateBinary(); epdUpdateSemaphore[i] = xSemaphoreCreateBinary();
xSemaphoreGive(epdUpdateSemaphore[i]); xSemaphoreGive(epdUpdateSemaphore[i]);
@ -145,7 +146,7 @@ void initDisplays()
// delay(1000); // delay(1000);
} }
epdContent = {"B", "T", "C", "L", "O", "C", "K"}; epdContent = {"B", "T", "C", "L", "O", "C", "K"};
for (uint i = 0; i < displaySize; i++) for (uint i = 0; i < NUM_SCREENS; i++)
{ {
xTaskNotifyGive(tasks[i]); xTaskNotifyGive(tasks[i]);
} }
@ -185,7 +186,7 @@ void taskEpd(void *pvParameters)
bool updatedThisCycle = false; bool updatedThisCycle = false;
for (uint i = 0; i < displaySize; i++) for (uint i = 0; i < NUM_SCREENS; i++)
{ {
if (epdContent[i].compareTo(currentEpdContent[i]) != 0) if (epdContent[i].compareTo(currentEpdContent[i]) != 0)
{ {
@ -234,7 +235,7 @@ void setEpdContent(std::array<String, 7> newEpdContent)
epdContent = newEpdContent; epdContent = newEpdContent;
} }
void splitText(uint dispNum, String top, String bottom, bool partial) void splitText(const uint dispNum, String top, String bottom, bool partial)
{ {
displays[dispNum].setRotation(2); displays[dispNum].setRotation(2);
displays[dispNum].setFont(&FONT_SMALL); displays[dispNum].setFont(&FONT_SMALL);
@ -270,7 +271,7 @@ void splitText(uint dispNum, String top, String bottom, bool partial)
displays[dispNum].print(bottom); displays[dispNum].print(bottom);
} }
void showDigit(uint dispNum, char chr, bool partial, const GFXfont *font) void showDigit(const uint dispNum, char chr, bool partial, const GFXfont *font)
{ {
String str(chr); String str(chr);
displays[dispNum].setRotation(2); displays[dispNum].setRotation(2);
@ -291,7 +292,7 @@ void fullRefresh(void *pvParameters)
{ {
resetAllDisplays(); resetAllDisplays();
for (uint i = 0; i < displaySize; i++) for (uint i = 0; i < NUM_SCREENS; i++)
{ {
lastFullRefresh[i] = NULL; lastFullRefresh[i] = NULL;
} }
@ -428,13 +429,13 @@ void showSetupQr(String ssid, String password)
displays[displayIndex].println("Welcome!"); displays[displayIndex].println("Welcome!");
} while (displays[displayIndex].nextPage()); } while (displays[displayIndex].nextPage());
for (int i = 1; i < displaySize; (i = i+2)) { for (int i = 1; i < NUM_SCREENS; (i = i+2)) {
displays[i].setPartialWindow(0, 0, displays[i].width(), displays[i].height()); displays[i].setPartialWindow(0, 0, displays[i].width(), displays[i].height());
displays[i].fillScreen(GxEPD_WHITE); displays[i].fillScreen(GxEPD_WHITE);
displays[i].display(true); displays[i].display(true);
} }
for (int i = 0; i < displaySize; i++) { for (int i = 0; i < NUM_SCREENS; i++) {
displays[i].hibernate(); displays[i].hibernate();
} }
} }

View file

@ -40,8 +40,8 @@ void resetSingleDisplay(int i);
std::array<String, 7> getCurrentEpdContent(); std::array<String, 7> getCurrentEpdContent();
void setEpdContent(std::array<String, 7> newEpdContent); void setEpdContent(std::array<String, 7> newEpdContent);
void splitText(uint dispNum, String top, String bottom, bool partial); void splitText(const uint dispNum, String top, String bottom, bool partial);
void showDigit(uint dispNum, char chr, bool partial, const GFXfont *font); void showDigit(const uint dispNum, char chr, bool partial, const GFXfont *font);
void refreshDisplay(void *pvParameters); void refreshDisplay(void *pvParameters);
void fullRefresh(void *pvParameters); void fullRefresh(void *pvParameters);

View file

@ -31,7 +31,7 @@ void taskGetPrice(void *pvParameters)
if (httpCode == 200) if (httpCode == 200)
{ {
String payload = http.getString(); String payload = http.getString();
StaticJsonDocument<768> doc; SpiRamJsonDocument doc(768);
deserializeJson(doc, payload); deserializeJson(doc, payload);
JsonObject bpi = doc["bitcoin"]; JsonObject bpi = doc["bitcoin"];
usdPrice = bpi["usd"]; usdPrice = bpi["usd"];
@ -61,7 +61,7 @@ void taskGetPrice(void *pvParameters)
if (httpCode == 200) if (httpCode == 200)
{ {
String payload = http.getString(); String payload = http.getString();
StaticJsonDocument<768> doc; SpiRamJsonDocument doc(768);
deserializeJson(doc, payload); deserializeJson(doc, payload);
JsonObject bpi = doc["bpi"]; JsonObject bpi = doc["bpi"];
usdPrice = bpi["USD"]["rate_float"]; usdPrice = bpi["USD"]["rate_float"];