Add missing settings, webUI as submodule

This commit is contained in:
Djuri Baars 2024-03-17 18:47:26 +01:00
parent 6c3796c776
commit 585b50d0ba
12 changed files with 209 additions and 45 deletions

3
.gitmodules vendored Normal file
View file

@ -0,0 +1,3 @@
[submodule "data"]
path = data
url = https://github.com/btclock/oc-webui.git

1
data Submodule

@ -0,0 +1 @@
Subproject commit 9df3329847f3939dc1242136e19746613fb83c4b

View file

View file

@ -9,7 +9,7 @@
; https://docs.platformio.org/page/projectconf.html
[platformio]
data_dir = data/build
data_dir = data/build_gz
default_envs = lolin_s2_mini_213epd, lolin_s2_mini_29epd, lolin_s3_mini_213epd, lolin_s3_mini_29epd
[btclock_base]
@ -19,6 +19,7 @@ monitor_speed = 115200
monitor_filters = esp32_exception_decoder, colorize
board_build.filesystem = littlefs
board_build.partitions = partition.csv
extra_scripts = post:scripts/extra_script.py
build_flags =
!python scripts/git_rev.py
-DLAST_BUILD_TIME=$UNIX_TIME

38
scripts/extra_script.py Normal file
View file

@ -0,0 +1,38 @@
Import("env")
import os
import gzip
from shutil import copyfileobj, rmtree
from pathlib import Path
def gzip_file(input_file, output_file):
with open(input_file, 'rb') as f_in:
with gzip.open(output_file, 'wb') as f_out:
copyfileobj(f_in, f_out)
def process_directory(input_dir, output_dir):
if os.path.exists(output_dir):
rmtree(output_dir)
for root, dirs, files in os.walk(input_dir):
relative_path = os.path.relpath(root, input_dir)
output_root = os.path.join(output_dir, relative_path)
Path(output_root).mkdir(parents=True, exist_ok=True)
for file in files:
# if file.endswith(('.html', '.css', '.js')):
input_file_path = os.path.join(root, file)
output_file_path = os.path.join(output_root, file + '.gz')
gzip_file(input_file_path, output_file_path)
print(f'Compressed: {input_file_path} -> {output_file_path}')
# Build web interface before building FS
def before_buildfs(source, target, env):
env.Execute("cd data && yarn && yarn postinstall && yarn build")
input_directory = 'data/dist'
output_directory = 'data/build_gz'
process_directory(input_directory, output_directory)
os.environ["PUBLIC_BASE_URL"] = ""
env.AddPreAction("$BUILD_DIR/littlefs.bin", before_buildfs)

View file

@ -3,7 +3,7 @@
Preferences preferences;
const char *ntpServer = "pool.ntp.org";
const long gmtOffset_sec = 0;
// const long gmtOffset_sec = 0;
const int daylightOffset_sec = 3600;
TaskHandle_t OTAHandle = NULL;
@ -14,7 +14,7 @@ bool isUpdating = false;
void setupTime()
{
configTime(gmtOffset_sec, daylightOffset_sec, ntpServer);
configTime(preferences.getInt(SETTING_TIME_OFFSET_MIN), daylightOffset_sec, ntpServer);
}
void setupPreferences()
@ -48,10 +48,44 @@ void setupPreferences()
{
preferences.putString(SETTING_MEMPOOL_INSTANCE, "https://mempool.space");
}
if (!preferences.isKey(SETTING_TIME_FORMAT))
{
preferences.putString(SETTING_TIME_FORMAT, "%H:%M:%S");
}
if (!preferences.isKey(SETTING_DATE_FORMAT))
{
preferences.putString(SETTING_DATE_FORMAT, "%d-%m-%Y");
}
if (!preferences.isKey(SETTING_DECIMAL_SEPARATOR))
{
preferences.putChar(SETTING_DECIMAL_SEPARATOR, '.');
}
if (!preferences.isKey(SETTING_POWER_SAVE_MODE))
{
preferences.putBool(SETTING_POWER_SAVE_MODE, false);
}
if (!preferences.isKey(SETTING_TIME_OFFSET_MIN))
{
preferences.putInt(SETTING_TIME_OFFSET_MIN, 0);
}
}
void setupWifi()
{
uint8_t mac[6];
WiFi.macAddress(mac);
unsigned long seed = 0;
for (int i = 0; i < 6; i++)
{
seed += (unsigned long)mac[i] << ((i & 1) * 8);
}
randomSeed(seed);
// WiFi.begin(, ");
WiFi.setAutoConnect(true);
WiFi.setAutoReconnect(true);
@ -75,15 +109,10 @@ void setupWifi()
}
}
byte mac[6];
WiFi.macAddress(mac);
String softAP_SSID =
String("OrangeBTClock");
WiFi.setHostname(softAP_SSID.c_str());
String softAP_password =
base64::encode(String(mac[2], 16) + String(mac[4], 16) +
String(mac[5], 16) + String(mac[1], 16))
.substring(2, 10);
String softAP_password = getAPPassword();
// wm.setConfigPortalTimeout(preferences.getUInt("wpTimeout", 600));
wm.setWiFiAutoReconnect(false);
@ -214,31 +243,36 @@ void setupOTA()
ArduinoOTA.begin();
xTaskCreatePinnedToCore(
OTAUpdateTask, // Task function
"OTAUpdateTask", // Task name
4096, // Stack size
NULL, // Task parameters
1, // Priority (higher value means higher priority)
&OTAHandle, // Task handle
0 // Core to run the task (0 or 1)
OTAUpdateTask, // Task function
"OTAUpdateTask", // Task name
4096, // Stack size
NULL, // Task parameters
1, // Priority (higher value means higher priority)
&OTAHandle, // Task handle
0 // Core to run the task (0 or 1)
);
}
void OTAUpdateTask(void *pvParameters) {
for (;;) {
ArduinoOTA.handle(); // Handle OTA updates
void OTAUpdateTask(void *pvParameters)
{
for (;;)
{
ArduinoOTA.handle(); // Handle OTA updates
vTaskDelay(1000 / portTICK_PERIOD_MS); // Delay to avoid high CPU usage
}
}
char getCurrencyIcon() {
char getCurrencyIcon()
{
char ret;
const char* currency = preferences.getString(SETTING_CURRENCY).c_str();
if (strcmp(currency, CURRENCY_USD) == 0) {
ret = ICON_DOLLAR;
} else if(strcmp(currency, CURRENCY_EUR) == 0) {
ret = ICON_EURO;
const char *currency = preferences.getString(SETTING_CURRENCY).c_str();
if (strcmp(currency, CURRENCY_USD) == 0)
{
ret = ICON_DOLLAR;
}
else if (strcmp(currency, CURRENCY_EUR) == 0)
{
ret = ICON_EURO;
}
// break;
// case CURRENCY_GBP:

View file

@ -59,6 +59,7 @@ void loop()
{
if (isUpdating)
{
delay(1000);
return;
}
@ -135,22 +136,22 @@ void loop()
{
icon = getCurrencyIcon();
int64_t marketCap = static_cast<std::int64_t>(getSupplyAtBlock(getBlock()) * double(getPrice()));
rowContent = String(formatNumberWithSuffix(marketCap, 4));
rowContent = String(formatNumberWithSuffix(marketCap, 8));
break;
}
case LINE_TIME:
{
icon = ICON_GLOBE;
char dateString[10];
strftime(dateString, 10, "%H:%M:%S", &timeinfo);
char dateString[16];
strftime(dateString, sizeof(dateString), preferences.getString(SETTING_TIME_FORMAT).c_str(), &timeinfo);
rowContent = dateString;
break;
}
case LINE_DATE:
{
icon = ICON_GLOBE;
char dateString[10];
strftime(dateString, 10, "%x", &timeinfo);
char dateString[16];
strftime(dateString, sizeof(dateString), preferences.getString(SETTING_DATE_FORMAT).c_str(), &timeinfo);
rowContent = dateString;
break;
}

View file

@ -1,13 +1,2 @@
#include "shared.hpp"
String getMyHostname()
{
uint8_t mac[6];
// WiFi.macAddress(mac);
esp_efuse_mac_get_default(mac);
char hostname[15];
String hostnamePrefix = preferences.getString(SETTING_HOSTNAME_PREFIX);
snprintf(hostname, sizeof(hostname), "%s-%02x%02x%02x", hostnamePrefix,
mac[3], mac[4], mac[5]);
return hostname;
}

View file

@ -5,6 +5,7 @@
#include <Preferences.h>
#include <GxEPD2.h>
#include <GxEPD2_BW.h>
#include "utils.hpp"
#include "fonts/fonts.hpp"
#ifdef VERSION_EPD_2_13
@ -62,6 +63,12 @@
#define SETTING_CURRENCY "currency"
#define SETTING_HOSTNAME_PREFIX "hostnamePrefix"
#define SETTING_MEMPOOL_INSTANCE "mempoolInstance"
#define SETTING_POWER_SAVE_MODE "powerSaveMode"
#define SETTING_TIME_OFFSET_MIN "timeOffsetMin"
#define SETTING_DECIMAL_SEPARATOR "decSeparator"
#define SETTING_TIME_FORMAT "timeFormat"
#define SETTING_DATE_FORMAT "dateFormat"
const int LINE_BLOCKHEIGHT = 0;
const int LINE_MEMPOOL_FEES = 1;
@ -94,4 +101,3 @@ extern char currentIcon1;
extern char currentIcon2;
extern char currentIcon3;
String getMyHostname();

32
src/utils.cpp Normal file
View file

@ -0,0 +1,32 @@
#include "utils.hpp"
String getAPPassword()
{
byte mac[6];
WiFi.macAddress(mac);
const char charset[] = "abcdefghjkmnpqrstuvwxyzABCDEFGHJKMNPQRSTUVWXYZ23456789";
char password[9]; // 8 characters + null terminator
snprintf(password, sizeof(password), "%c%c%c%c%c%c%c%c",
charset[mac[0] % (sizeof(charset) - 1)],
charset[mac[1] % (sizeof(charset) - 1)],
charset[mac[2] % (sizeof(charset) - 1)],
charset[mac[3] % (sizeof(charset) - 1)],
charset[mac[4] % (sizeof(charset) - 1)],
charset[mac[5] % (sizeof(charset) - 1)],
charset[(mac[0] + mac[1] + mac[2] + mac[3] + mac[4] + mac[5]) % (sizeof(charset) - 1)],
charset[(mac[0] * mac[1] * mac[2] * mac[3] * mac[4] * mac[5]) % (sizeof(charset) - 1)]);
return password;
}
String getMyHostname()
{
uint8_t mac[6];
// WiFi.macAddress(mac);
esp_efuse_mac_get_default(mac);
char hostname[15];
String hostnamePrefix = preferences.getString(SETTING_HOSTNAME_PREFIX);
snprintf(hostname, sizeof(hostname), "%s-%02x%02x%02x", hostnamePrefix,
mac[3], mac[4], mac[5]);
return hostname;
}

27
src/utils.hpp Normal file
View file

@ -0,0 +1,27 @@
#pragma once
#include <WiFi.h>
#include <Arduino.h>
#include <ArduinoJson.hpp>
#include "shared.hpp"
namespace ArduinoJson {
template <>
struct Converter<char> {
static void toJson(char c, JsonVariant var) {
var.set(static_cast<signed char>(c));
}
static char fromJson(JsonVariantConst src) {
return static_cast<char>(src.as<signed char>());
}
static bool checkJson(JsonVariantConst src) {
return src.is<signed char>();
}
};
}
String getAPPassword();
String getMyHostname();

View file

@ -3,8 +3,10 @@
AsyncWebServer server(80);
const String uintSettings[] = {SETTING_ROW1_CONTENT, SETTING_ROW2_CONTENT, SETTING_ROW3_CONTENT};
const String stringSettings[] = {SETTING_CURRENCY,SETTING_MEMPOOL_INSTANCE};
const String boolSettings[] = {};
const String intSettings[] = {SETTING_TIME_OFFSET_MIN};
const String stringSettings[] = {SETTING_CURRENCY, SETTING_MEMPOOL_INSTANCE, SETTING_TIME_FORMAT, SETTING_DATE_FORMAT};
const String charSettings[] = {SETTING_DECIMAL_SEPARATOR};
const String boolSettings[] = {SETTING_POWER_SAVE_MODE};
void setupWebserver()
{
@ -68,11 +70,21 @@ void onApiSettingsGet(AsyncWebServerRequest *request)
root[setting] = preferences.getUInt(setting.c_str());
}
for (String setting : intSettings)
{
root[setting] = preferences.getInt(setting.c_str());
}
for (String setting : stringSettings)
{
root[setting] = preferences.getString(setting.c_str());
}
for (String setting : charSettings)
{
root[setting] = preferences.getChar(setting.c_str());
}
for (String setting : boolSettings)
{
root[setting] = preferences.getBool(setting.c_str());
@ -110,6 +122,16 @@ void onApiSettingsPatch(AsyncWebServerRequest *request, JsonVariant &json)
}
}
for (String setting : intSettings)
{
if (settings.containsKey(setting))
{
preferences.putInt(setting.c_str(), settings[setting].as<int>());
Serial.printf("Setting %s to %d\r\n", setting.c_str(),
settings[setting].as<uint>());
}
}
for (String setting : stringSettings)
{
if (settings.containsKey(setting))
@ -120,6 +142,16 @@ void onApiSettingsPatch(AsyncWebServerRequest *request, JsonVariant &json)
}
}
for (String setting : charSettings)
{
if (settings.containsKey(setting))
{
preferences.putChar(setting.c_str(), settings[setting].as<char>());
Serial.printf("Setting %s to %s\r\n", setting.c_str(),
settings[setting].as<String>());
}
}
for (String setting : boolSettings)
{
if (settings.containsKey(setting))