diff options
| author | Reiner Herrmann <reiner@reiner-h.de> | 2020-07-17 17:09:30 +0200 |
|---|---|---|
| committer | Reiner Herrmann <reiner@reiner-h.de> | 2020-07-17 17:09:30 +0200 |
| commit | 097db5fa9f57a77866be60ef8d8d39beef882639 (patch) | |
| tree | e70e1b5a49c948526784e0a6f6a428e1df8c797a /src | |
| parent | 2b73d32e1e32fa803a7a76bca7fc22dcf9e4c656 (diff) | |
draw qrcode for wlan connection
Diffstat (limited to 'src')
| -rw-r--r-- | src/draw_qrcode.cpp | 94 | ||||
| -rw-r--r-- | src/main.cpp | 2 |
2 files changed, 96 insertions, 0 deletions
diff --git a/src/draw_qrcode.cpp b/src/draw_qrcode.cpp new file mode 100644 index 0000000..594e47c --- /dev/null +++ b/src/draw_qrcode.cpp @@ -0,0 +1,94 @@ +#include <GxEPD2_BW.h> +#include <Fonts/FreeSansBold9pt7b.h> +#include <Fonts/FreeSans9pt7b.h> +#include <qrcode.h> + +#define BLOCK_WIDTH 4 + +static uint16_t sizes[] = { + 17, 32, 53, 78, 106, 134, 154, 192, 230, +}; + +static void escape_strings(String &text) { + text.replace("\\", "\\\\"); + text.replace("\"", "\\\""); + text.replace(";", "\\;"); + text.replace(",", "\\,"); + text.replace(":", "\\:"); +} + +static int version_for_len(int length) { + /* assuming ECC_LOW byte qrcodes + sizes taken from table in https://github.com/ricmoo/QRCode/blob/master/README.md */ + + for (int i = 0; i < sizeof(sizes)/sizeof(uint16_t); i++) { + if (length <= sizes[i]) + return i + 1; + } + return -1; +} + +int draw_qrcode(GxEPD2_GFX_BASE_CLASS &display, int16_t x, int16_t y, String &text) { + QRCode qrcode; + int version = version_for_len(text.length()); + if (version <= 0) + return 0; + + uint8_t bytes[qrcode_getBufferSize(version)]; + qrcode_initText(&qrcode, bytes, version, ECC_LOW, text.c_str()); + + /* add quiet zone */ + x += 4 * BLOCK_WIDTH; + y += 4 * BLOCK_WIDTH; + + for (int row = 0; row < qrcode.size; row++) { + for (int col = 0; col < qrcode.size; col++) { + if (!qrcode_getModule(&qrcode, row, col)) { + continue; + } + display.fillRect(x + BLOCK_WIDTH * row, y + BLOCK_WIDTH * col, BLOCK_WIDTH, BLOCK_WIDTH, GxEPD_BLACK); + } + } + return qrcode.size * BLOCK_WIDTH + 8 * BLOCK_WIDTH; +} + +void draw_qrcode_wlan(GxEPD2_GFX_BASE_CLASS &display, int16_t x, int16_t y, const char *ssid, const char *psk) { + String ssid_str = String(ssid); + String psk_str = String(psk); + escape_strings(ssid_str); + escape_strings(psk_str); + + /* assuming WPA network; (H)idden attribute is kept at default */ + String wifi_str = "WIFI:S:" + ssid_str; + if (psk_str.length() == 0) { + /* open network */ + wifi_str += ";;;;"; + } else { + wifi_str += ";P:" + psk_str + ";T:WPA;;"; + } + + int size = draw_qrcode(display, x, y, wifi_str); + + /* draw text */ + int16_t x2, y2; + uint16_t w, h; + String text_ssid = String("SSID:"); + String text_psk = String("PSK:"); + + display.setFont(&FreeSansBold9pt7b); + display.getTextBounds(text_ssid, 0, 0, &x2, &y2, &w, &h); + display.setCursor(x, y + size + h); + display.print(text_ssid); + display.setFont(&FreeSans9pt7b); + display.setCursor(x + w, y + size + h); + display.print(" " + ssid_str); + + if (psk_str.length() > 0) { + display.setFont(&FreeSansBold9pt7b); + display.setCursor(x, y + size + 2 * h + 10); + display.print(text_psk); + display.setFont(&FreeSans9pt7b); + display.setCursor(x + w, y + size + 2 * h + 10); + display.print(" " + psk_str); + } +} diff --git a/src/main.cpp b/src/main.cpp index b8cb0c1..70f2559 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -4,6 +4,7 @@ #include <WiFi.h> #include "calendar.h" +#include "draw_qrcode.h" #include "secrets.h" /* @@ -42,6 +43,7 @@ void draw() { do { display.fillScreen(GxEPD_WHITE); draw_calendar(display, 30, 30); + draw_qrcode_wlan(display, 30, 200, wifi_ssid, wifi_psk); } while(display.nextPage()); } |
