diff --git a/Makefile b/Makefile index 889aaa0..b409e64 100644 --- a/Makefile +++ b/Makefile @@ -1,3 +1,4 @@ +#BOARD := featheresp32 BOARD := sparkfun_esp32micromod FIRMWARE := .pioenvs/$(BOARD)/firmware.bin SOURCES := \ diff --git a/include/prefs.h b/include/Config.h similarity index 75% rename from include/prefs.h rename to include/Config.h index 36cb5c8..ae4b6e9 100644 --- a/include/prefs.h +++ b/include/Config.h @@ -2,7 +2,7 @@ #define KIMODEM_PREFS_H -namespace config { +namespace Config { // Networking @@ -14,6 +14,11 @@ void SetStartTryConnecting(bool opt); // Misc. +bool EnableMeter(); +void SetEnableMeter(bool opt); + + +// Misc. control void FactoryDefaults(); } diff --git a/include/Display.h b/include/Display.h index d8eff6c..917bb77 100644 --- a/include/Display.h +++ b/include/Display.h @@ -6,29 +6,20 @@ #define ANSI_CLEAR_SCREEN "\33[2J" -/* -class Display { -public: - Display(); +namespace Display { - void Clear(); - void Draw(); - bool HasDisplay(); +void Init(); +void Clear(); +void Clear(bool hint); +void Draw(); +bool HasDisplay(); + +void Print(const char *); +void Println(const char *); +void SetCursor(int16_t x, int16_t y); + + +} // namespace Display - void Print(const char *); - void Println(const char *); - void SetCursor(int16_t x, int16_t y); -}; -*/ -#if defined(ADAFRUIT_OLED) -#include "internal/DisplayAdafruitOLED.h" -#else -#include "internal/DisplayNone.h" #endif - - -static Display display; - - -#endif \ No newline at end of file diff --git a/include/WiFiMeter.h b/include/WiFiMeter.h new file mode 100644 index 0000000..11717b5 --- /dev/null +++ b/include/WiFiMeter.h @@ -0,0 +1,20 @@ +#ifndef KIMODEM_WIFI_METER_H +#define KIMODEM_WIFI_METER_H + +#include + + +namespace Meter { + + +void Begin(); +void Enable(); +void Disable(); +void Update(); + + +} + + + +#endif diff --git a/include/WiFiMgr.h b/include/WiFiMgr.h index 6b7289f..444ddce 100644 --- a/include/WiFiMgr.h +++ b/include/WiFiMgr.h @@ -10,6 +10,7 @@ bool SetupWiFi(); bool Autoconnect(Dictionary &pb); bool Autoconnect(Dictionary &pb, bool reset); bool TryConnect(Dictionary &pb); +void WiFiRefresh(Dictionary &pb); #endif diff --git a/include/internal/DisplayAdafruitOLED.h b/include/internal/DisplayAdafruitOLED.h deleted file mode 100644 index 365416f..0000000 --- a/include/internal/DisplayAdafruitOLED.h +++ /dev/null @@ -1,26 +0,0 @@ -#ifndef KIMODEM_ADAFRUIT_OLED_H -#define KIMODEM_ADAFRUIT_OLED_H - -#include -#include -#include -#include - -class Display { -public: - Display(); - - void Clear(); - void Draw(); - bool HasDisplay(); - - void Print(const char *); - void Println(const char *); - void SetCursor(int16_t x, int16_t y); -private: - Adafruit_SSD1306 oled; -}; - - - -#endif \ No newline at end of file diff --git a/include/internal/DisplayNone.h b/include/internal/DisplayNone.h deleted file mode 100644 index d6f12fd..0000000 --- a/include/internal/DisplayNone.h +++ /dev/null @@ -1,20 +0,0 @@ -#ifndef KIMODEM_DISPLAY_SERIAL -#define KIMODEM_DISPLAY_SERIAL - -#include - - -class Display { -public: - Display() {}; - - void Clear(); - void Draw(); - bool HasDisplay(); - - void Print(const char *); - void Println(const char *); - void SetCursor(int16_t x, int16_t y); -}; - -#endif \ No newline at end of file diff --git a/platformio.ini b/platformio.ini index 9deb2de..0f45acb 100644 --- a/platformio.ini +++ b/platformio.ini @@ -13,6 +13,8 @@ framework = arduino platform = espressif32 monitor_speed = 115200 extra_scripts = scripts/download_fs.py +monitor_filters = + esp32_exception_decoder [env:featheresp32] board = featheresp32 @@ -27,7 +29,13 @@ lib_deps = board = sparkfun_esp32micromod build_flags = -DSPARKFUN_HYPERDISPLAY - -DDISPLAY_NONE + -DAPA102_ENABLED + +lib_deps = + sparkfun/SparkFun HyperDisplay@^2.0.1 + sparkfun/SparkFun HyperDisplay ILI9341@^1.0.0 + sparkfun/SparkFun HyperDisplay 4DLCD-320240@^1.0.0 + pololu/APA102@^3.0.0 [env:d1mini] board = wemos_d1_mini32 diff --git a/src/prefs.cc b/src/Config.cc similarity index 79% rename from src/prefs.cc rename to src/Config.cc index 38e122c..96d4409 100644 --- a/src/prefs.cc +++ b/src/Config.cc @@ -1,8 +1,9 @@ #include -#include "prefs.h" + +#include "Config.h" -namespace config { +namespace Config { static bool isLoaded = false; @@ -61,6 +62,22 @@ SetStartTryConnecting(bool opt) } +bool +EnableMeter() +{ + checkReady(); + return preferences.getBool("WCM", true); +} + + +void +SetEnableMeter(bool opt) +{ + checkReady(); + preferences.putBool("WCM", opt); +} + + void FactoryDefaults() { diff --git a/src/DisplayAdafruitOLED.cc b/src/DisplayAdafruitOLED.cc index fe6661b..4d83df8 100644 --- a/src/DisplayAdafruitOLED.cc +++ b/src/DisplayAdafruitOLED.cc @@ -5,64 +5,84 @@ #include #include -#include "internal/DisplayAdafruitOLED.h" +#include "Display.h" -static Adafruit_SSD1306 oled(SSD1306_SWITCHCAPVCC, 0x3C); +namespace Display { + +static Adafruit_SSD1306 oled(SSD1306_SWITCHCAPVCC, 0x3C); - -Display::Display() - : oled(oled) +void +Init() { - Serial.println("initialized display"); + oled.begin(SSD1306_SWITCHCAPVCC, 0x3C); + oled.display(); + oled.clearDisplay(); oled.setTextSize(1); - oled.setTextColor(SSD1306_WHITE); + oled.setTextColor(WHITE); + oled.fillScreen(BLACK); + oled.display(); + Serial.println("DISP INIT"); +} + + +void +Clear() +{ + Clear(false); } void -Display::Clear() +Clear(bool hint) { - this->oled.clearDisplay(); - this->SetCursor(0, 0); - this->Draw(); + oled.clearDisplay(); + SetCursor(0, 0); + oled.display(); } void -Display::Draw() +Draw() { - this->oled.display(); + oled.display(); } bool -Display::HasDisplay() +HasDisplay() { return true; } void -Display::Print(const char *s) +Print(const char *s) { - this->oled.print(s); + oled.print(s); + Serial.print(s); + oled.display(); } void -Display::Println(const char *s) +Println(const char *s) { - this->oled.println(s); + oled.println(s); + Serial.println(s); + oled.display(); } void -Display::SetCursor(int16_t x, int16_t y) +SetCursor(int16_t x, int16_t y) { - this->oled.setCursor(x, y); + oled.setCursor(x, y); } -#endif \ No newline at end of file +} // namespace Display + + +#endif diff --git a/src/DisplaySFHyperdisplay.cc b/src/DisplaySFHyperdisplay.cc new file mode 100644 index 0000000..5dc90f1 --- /dev/null +++ b/src/DisplaySFHyperdisplay.cc @@ -0,0 +1,88 @@ +#if defined(SPARKFUN_HYPERDISPLAY) + +#include +#include +#include "Display.h" + + +namespace Display { + + +static LCD320240_4WSPI tft; +static ILI9341_color_18_t defaultColor; +static uint16_t line = 0; + + +void +Init() +{ + tft.begin(D1, D0, PWM0, SPI, 32000000); + tft.setInterfacePixelFormat(ILI9341_PXLFMT_18); + tft.clearDisplay(); + + defaultColor = tft.rgbTo18b(255, 255, 255); + tft.setCurrentWindowColorSequence((color_t)&defaultColor); +} + + +void +Clear() +{ + Clear(false); +} + + +void +Clear(bool hint) +{ + if (hint) { + return; + } + tft.clearDisplay(); + SetCursor(0, 0); + line = 0; +} + + +void +Draw() +{ + +} + + +bool +HasDisplay() +{ + return true; +} + + +void +Print(const char *s) +{ + tft.print(s); + Serial.print(s); +} + + +void +Println(const char *s) +{ + tft.println(s); + Serial.println(s); + line++; + SetCursor(0, line*10); +} + + +void +SetCursor(int16_t x, int16_t y) +{ + tft.setTextCursor(x, y); +} + + +} // namespace Display + +#endif diff --git a/src/WiFiMeter.cc b/src/WiFiMeter.cc new file mode 100644 index 0000000..cfdf049 --- /dev/null +++ b/src/WiFiMeter.cc @@ -0,0 +1,132 @@ +#include +#include + +#include "Config.h" +#include "WiFiMeter.h" + +namespace Meter { + +static bool enabled = false; + +#if defined(APA102_ENABLED) + +#include + +constexpr uint8_t APA102_DATA = 25; +constexpr uint8_t APA102_CLOCK = 15; +constexpr uint8_t APA102_COUNT = 6; +constexpr uint8_t APA102_BRIGHTNESS = 5; + + +APA102 ledBar; + + +static void +setLED(uint8_t brightness) +{ + brightness = brightness & 0x1f; + + ledBar.sendColor(0, 0, 255, brightness); +} + + +static void +clearBar() +{ + ledBar.startFrame(); + for (int i = 0; i < APA102_COUNT; i++) { + setLED(0); + } + ledBar.endFrame(APA102_COUNT); +} + + +static void +setLedCount(uint8_t on) +{ + ledBar.startFrame(); + + for (int i = 0; i < APA102_COUNT; i++) { + if (i >= on) { + setLED(0); + } else { + setLED(APA102_BRIGHTNESS); + } + } + + ledBar.endFrame(APA102_CLOCK); +} + + +void +Begin() +{ + enabled = Config::EnableMeter(); +} + + +void +Enable() +{ + enabled = true; + Config::SetEnableMeter(true); +} + + +void +Disable() +{ + enabled = false; + Config::SetEnableMeter(false); +} + + +void +Update() +{ + if (!enabled) { + return; + } + + int8_t rssi; + uint8_t count = 0; + + if (WiFi.status() != WL_CONNECTED) { + rssi = -127; + } else { + rssi = WiFi.RSSI(); + } + + + if (rssi >= -30) { + count = 6; + } else if (rssi >= -55) { + count = 5; + } else if (rssi >= -67) { + count = 4; + } else if (rssi >= -70) { + count = 3; + } else if (rssi >= -80) { + count = 2; + } else if (rssi >= -90) { + count = 1; + } else { + count = 0; + } + + setLedCount(count); +} + + + +#else + +void Begin() {} +void Enable() {} +void Disable() {} +void Update() {} + + +#endif + +} diff --git a/src/WiFiMgr.cc b/src/WiFiMgr.cc index daf4e8f..52d7c51 100644 --- a/src/WiFiMgr.cc +++ b/src/WiFiMgr.cc @@ -2,10 +2,11 @@ #include #include +#include "Config.h" #include "Dictionary.h" #include "Display.h" +#include "WiFiMeter.h" #include "TLV.h" -#include "prefs.h" #include "WiFiMgr.h" @@ -14,6 +15,10 @@ #define CONN_WAIT 250 +static TLV::Record ssidrec; +static TLV::Record wpakeyrec; + + bool SetupWiFi() { @@ -27,32 +32,30 @@ tryConnect(const char *ssid, const char *wpakey) { size_t waitedFor = 0; - Serial.print("CONNECT "); - Serial.println(ssid); + Display::Print("CONNECT "); + Display::Println(ssid); WiFi.begin(ssid, wpakey); while ((WiFi.status() != WL_CONNECTED) && (waitedFor < MAX_WAIT)) { waitedFor += CONN_WAIT; if ((waitedFor % 1000) == 0) { - Serial.print("."); + Display::Print("."); } delay(250); } if (WiFi.status() == WL_CONNECTED) { - Serial.print("MODEM ADDR "); - Serial.println(WiFi.localIP()); - - display.Clear(); - display.Print("SSID: "); - display.Println(ssid); - display.Print("IP: "); - display.Println(WiFi.localIP().toString().c_str()); - display.Draw(); + Display::Clear(true); + Display::Print("SSID: "); + Display::Println(ssid); + Display::Print("IP: "); + Display::Println(WiFi.localIP().toString().c_str()); + + Config::SetLastSSID(ssid); return true; } - Serial.println("CARRIER SIGNAL LOST"); + Display::Println("CARRIER SIGNAL LOST"); return false; } @@ -60,30 +63,28 @@ tryConnect(const char *ssid, const char *wpakey) bool TryConnect(Dictionary &pb) { - TLV::Record ssid; - TLV::Record wpakey; uint8_t *cursor; - if ((ssid.Len = config::LastSSID(ssid.Val, 32)) != 0) { - Serial.print("LAST SSID: "); - Serial.println(ssid.Val); - if (pb.Lookup(ssid.Val, ssid.Len, wpakey)) { - if (tryConnect((const char *)ssid.Val, (const char *)wpakey.Val)) { + if ((ssidrec.Len = Config::LastSSID(ssidrec.Val, 32)) != 0) { + Display::Print("LAST SSID: "); + Display::Println(ssidrec.Val); + if (pb.Lookup(ssidrec.Val, ssidrec.Len, wpakeyrec)) { + if (tryConnect((const char *)ssidrec.Val, (const char *)wpakeyrec.Val)) { return true; } } else { - Serial.println("WPAKEY NOT FOUND"); + Display::Println("WPAKEY NOT FOUND"); } } while ((cursor != NULL) && (cursor[0] != TAG_EMPTY)) { - TLV::ReadFromMemory(ssid, cursor); - TLV::SkipRecord(ssid, cursor); + TLV::ReadFromMemory(ssidrec, cursor); + TLV::SkipRecord(ssidrec, cursor); - TLV::ReadFromMemory(wpakey, cursor); - TLV::SkipRecord(ssid, cursor); + TLV::ReadFromMemory(wpakeyrec, cursor); + TLV::SkipRecord(wpakeyrec, cursor); - if (tryConnect(ssid.Val, wpakey.Val)) { + if (tryConnect(ssidrec.Val, wpakeyrec.Val)) { return true; } } @@ -103,16 +104,16 @@ tryConnect(Dictionary &pb, int network) return false; } - Serial.print("MODEM: CHECK "); - Serial.print(ssid); - Serial.print(": "); + Display::Print("MODEM: CHECK "); + Display::Print(ssid); + Display::Print(": "); if (!pb.Lookup(ssid, uint8_t(ssidLen), password)) { - Serial.println("NOT FOUND"); + Display::Println("NOT FOUND"); return false; } - Serial.println("CONNECTING"); + Display::Println("CONNECTING"); return tryConnect(ssid, password.Val); } @@ -129,15 +130,15 @@ Autoconnect(Dictionary &pb, bool reset) int networkCount = 0; int network = 0; - Serial.println("MODEM: TRY AUTOCONNECT"); + Display::Println("MODEM: TRY AUTOCONNECT"); if (reset) { - Serial.println("RADIO RESET"); + Display::Println("RADIO RESET"); SetupWiFi(); WiFi.disconnect(); delay(1000); } else { - Serial.println("NO RESET"); + Display::Println("NO RESET"); } networkCount = WiFi.scanNetworks(); @@ -147,7 +148,31 @@ Autoconnect(Dictionary &pb, bool reset) } } - Serial.println("NO CARRIER"); + Display::Println("NO CARRIER"); return false; } + +bool +Reconnect(Dictionary &pb) +{ + if (!tryConnect(ssidrec.Val, wpakeyrec.Val)) { + return TryConnect(pb); + } + + return true; +} + + +void +WiFiRefresh(Dictionary &pb) +{ + Meter::Update(); + + if (WiFi.status() == WL_CONNECTED) { + return; + } + + Display::Println("CARRIER SIGNAL LOST: ATC"); + Reconnect(pb); +} diff --git a/src/main.cc b/src/main.cc index 35065e2..e5d8f30 100644 --- a/src/main.cc +++ b/src/main.cc @@ -2,10 +2,11 @@ #include #include "Arena.h" +#include "Config.h" #include "Dictionary.h" #include "Display.h" #include "WiFiMgr.h" -#include "prefs.h" +#include "WiFiMeter.h" #include "homenet.h" @@ -23,31 +24,31 @@ setupPhonebook() size_t fileSize = pbFile.size(); bool ok = false; - Serial.print("DAT FILE "); - Serial.print(fileSize); - Serial.println("B"); + Display::Print("DAT FILE "); + Display::Print(String(fileSize).c_str()); + Display::Println("B"); if (fileSize == 0) { - Serial.println("INIT PHONEBOOK"); + Display::Println("INIT PHONEBOOK"); phonebook.Set(HOME_SSID, HOME_SSIDLEN, HOME_WPA, HOME_WPALEN); if (WriteArena(arena, pbFilePath) == 0) { ok = true; } pbFile.close(); - config::SetLastSSID(HOME_SSID); + Config::SetLastSSID(HOME_SSID); return ok; } fileSize = fileSize > PHONEBOOK_SIZE ? PHONEBOOK_SIZE : fileSize; - Serial.print("LOAD PHONEBOOK "); + Display::Print("LOAD PHONEBOOK "); if (fileSize != pbFile.read(phonebookBuffer, fileSize)) { - Serial.println("FAILED"); + Display::Println("FAILED"); pbFile.close(); return false; } - Serial.println("OK"); + Display::Println("OK"); pbFile.close(); phonebook.DumpKVPairs(); return true; @@ -56,32 +57,35 @@ setupPhonebook() void setup() { Serial.begin(115200); - while (!Serial) ; + Display::Init(); - display.Clear(); - - Serial.println("MODEM BOOT"); + Display::Println("MODEM BOOT"); + Display::Clear(); + Display::Println("MODEM BOOT"); InitializeArena(arena); NewStaticArena(arena, phonebookBuffer, PHONEBOOK_SIZE); + Meter::Begin(); + Meter::Enable(); - while (true); - + Display::Println("SPIFFS INIT"); if (!SPIFFS.begin(true) && !SPIFFS.begin(false)) { - Serial.println("SPIFFS BEGIN FAIL"); + Display::Println("SPIFFS BEGIN FAIL"); while (true) ; } setupPhonebook(); - if (config::StartTryConnecting()) { + if (Config::StartTryConnecting()) { + Display::Println("AUTO ATC"); if (!TryConnect(phonebook)) { Autoconnect(phonebook); } } - Serial.println("MODEM READY"); + Display::Println("MODEM READY"); } void loop() { - // put your main code here, to run repeatedly: + delay(1000); + Meter::Update(); }