From 99ece2f7d39077b0af3eecbbb108232e2a2261a6 Mon Sep 17 00:00:00 2001 From: tyeth Date: Wed, 27 Nov 2024 16:36:52 +0000 Subject: [PATCH 1/7] Add RPi Pico2W build --- platformio.ini | 82 +- src/Wippersnapper_Boards.h | 2 +- .../statusLED/Wippersnapper_StatusLED.cpp | 820 +++++++++--------- src/provisioning/tinyusb/Wippersnapper_FS.cpp | 2 +- 4 files changed, 491 insertions(+), 415 deletions(-) diff --git a/platformio.ini b/platformio.ini index dd4acafc2..427a7ea94 100644 --- a/platformio.ini +++ b/platformio.ini @@ -71,7 +71,7 @@ lib_deps = adafruit/Adafruit TouchScreen adafruit/Adafruit MQTT Library bblanchon/ArduinoJson - https://github.com/pstolarz/OneWireNg.git + https://github.com/tyeth/pstolarz_OneWireNg.git#pico2w https://github.com/milesburton/Arduino-Temperature-Control-Library.git https://github.com/Sensirion/arduino-sht.git https://github.com/Sensirion/arduino-i2c-scd4x.git @@ -112,9 +112,9 @@ lib_archive = no ; debug timer issues see https://community.platformio.org/t/cho lib_ignore = OneWire [common:rp2040] -platform = https://github.com/maxgerhardt/platform-raspberrypi.git +platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop ; platform_packages = -; framework-arduinopico @ symlink:///Users/tyeth/Projects/arduino-pico +; ; framework-arduinopico @ symlink:///Users/tyeth/Projects/arduino-pico ; framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git#master board = rpipicow framework = arduino @@ -511,3 +511,79 @@ build_flags = ; ; No USB stack ; build_flags = -DPIO_FRAMEWORK_ARDUINO_NO_USB ; -DPIO_FRAMEWORK_ARDUINO_ENABLE_IPV6 + + +[env:raspberypi_pico2w] +extends = common:rp2040 +platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w +; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop +platform_packages = + framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git +board = rpipico2w +build_flags = + -DWIFICC=CYW43_COUNTRY_UK + ; -DARDUINO_ARCH_RP2040 + ; -DUSBD_MAX_POWER_MA=500 + ; -DPICO_CYW43_SUPPORTED=1 + +[env:raspberypi_pico2w_debug] +extends = common:rp2040 +platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w +; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop +platform_packages = + framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git +; ; framework-arduinopico @ symlink:///Users/tyeth/Projects/arduino-pico +board = rpipico2w +build_type = debug +framework = arduino +debug_tool = cmsis-dap +upload_protocol = cmsis-dap +; board can use both Arduino cores -- we select Arduino-Pico here +board_build.core = earlephilhower +board_build.filesystem_size = 0.5m +debug_init_break = tbreak runNetFSM +build_flags = + ; -UARDUINO + ; -DPICO_BUILD + -DARDUINO_ARCH_RP2040 + -DUSBD_MAX_POWER_MA=500 + -DPICO_CYW43_SUPPORTED=1 + -DWIFICC=CYW43_COUNTRY_UK + ; -DDEBUG + ; -DDEBUG_RP2040_WIRE + ; -DDEBUG_RP2040_SPI + ; -DDEBUG_RP2040_CORE + ; -DDEBUG_RP2040_WIFI + ; -DNDEBUG + ; -DLWIP_DEBUG + ; -DDEBUG_RP2040_PORT=Serial1 + ; -DDEBUG_RP2040_UART_1 + ; -DDEBUG_RP2040_UART=1 + -Og + ; Enable debug stack protection + -fstack-protector + ; Enable Exceptions + -DPIO_FRAMEWORK_ARDUINO_ENABLE_EXCEPTIONS + ; Enable RTTI + -DPIO_FRAMEWORK_ARDUINO_ENABLE_RTTI + ; ; Enable default USB Stack of Pico SDK USB Stack with none of below usb options + ; Adafruit TinyUSB + -DUSE_TINYUSB + ; ; No USB stack + ; build_flags = -DPIO_FRAMEWORK_ARDUINO_NO_USB + ; -DPIO_FRAMEWORK_ARDUINO_ENABLE_IPV6 + + +[env:pimoroni_pico_plus_2w] +extends = common:rp2040 +platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w +; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop +platform_packages = + framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git +board = pimoroni_pico_plus_2w +build_flags = + -DWIFICC=CYW43_COUNTRY_UK + -DUSE_TINYUSB + ; -DARDUINO_ARCH_RP2040 + ; -DUSBD_MAX_POWER_MA=500 + ; -DPICO_CYW43_SUPPORTED=1 diff --git a/src/Wippersnapper_Boards.h b/src/Wippersnapper_Boards.h index 37e3db870..4e89862e0 100644 --- a/src/Wippersnapper_Boards.h +++ b/src/Wippersnapper_Boards.h @@ -185,7 +185,7 @@ #define BOARD_ID "mkrwifi1010" #define USE_STATUS_LED #define STATUS_LED_PIN 6 -#elif defined(ARDUINO_RASPBERRY_PI_PICO_W) +#elif defined(ARDUINO_RASPBERRY_PI_PICO_W) || defined(ARDUINO_ARCH_RP2040) #define BOARD_ID "rpi-pico-w" #define USE_TINYUSB #define USE_STATUS_LED diff --git a/src/components/statusLED/Wippersnapper_StatusLED.cpp b/src/components/statusLED/Wippersnapper_StatusLED.cpp index 47b170462..ba9061cb2 100644 --- a/src/components/statusLED/Wippersnapper_StatusLED.cpp +++ b/src/components/statusLED/Wippersnapper_StatusLED.cpp @@ -1,411 +1,411 @@ -/*! - * @file Wippersnapper_StatusLED.cpp - * - * Interfaces for the Wippersnapper status indicator LED/NeoPixel/Dotstar/RGB - * LED. - * - * Adafruit invests time and resources providing this open source code, - * please support Adafruit and open-source hardware by purchasing - * products from Adafruit! - * - * Copyright (c) Brent Rubell 2020-2022 for Adafruit Industries. - * - * BSD license, all text here must be included in any redistribution. - * - */ -#include "Wippersnapper_StatusLED.h" -#include "Wippersnapper.h" - -extern Wippersnapper WS; -#ifdef USE_STATUS_NEOPIXEL -Adafruit_NeoPixel *statusPixel = new Adafruit_NeoPixel( - STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); -#endif - -#ifdef USE_STATUS_DOTSTAR -Adafruit_DotStar *statusPixelDotStar = - new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, - STATUS_DOTSTAR_PIN_CLK, DOTSTAR_BRG); -#endif - -/****************************************************************************/ -/*! - @brief Initializes board-specific status LED pixel -*/ -/****************************************************************************/ -void initStatusLED() { -#ifdef USE_STATUS_NEOPIXEL - if (WS.lockStatusNeoPixel == false) { -#if defined(NEOPIXEL_I2C_POWER) - pinMode(NEOPIXEL_I2C_POWER, OUTPUT); - digitalWrite(NEOPIXEL_I2C_POWER, HIGH); -#elif defined(NEOPIXEL_POWER) - pinMode(NEOPIXEL_POWER, OUTPUT); -// turn NeoPixel power pin on -#ifndef ARDUINO_MAGTAG29_ESP32S2 - digitalWrite(NEOPIXEL_POWER, HIGH); -#else - digitalWrite(NEOPIXEL_POWER, LOW); -#endif -#endif - statusPixel = new Adafruit_NeoPixel( - STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); - statusPixel->begin(); - statusPixel->show(); // turn OFF all pixels - WS.lockStatusNeoPixel = true; - } -#endif - -#ifdef USE_STATUS_DOTSTAR - if (WS.lockStatusDotStar == false) { -#ifdef STATUS_DOTSTAR_COLOR_ORDER - // Board requires a non-default color order in the constructor - statusPixelDotStar = new Adafruit_DotStar( - STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, STATUS_DOTSTAR_PIN_CLK, - STATUS_DOTSTAR_COLOR_ORDER); -#else - statusPixelDotStar = - new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, - STATUS_DOTSTAR_PIN_CLK, STATUS_DOTSTAR_COLOR_ORDER) -#endif - statusPixelDotStar->begin(); - statusPixelDotStar->show(); // turn OFF all pixels - WS.lockStatusDotStar = true; - } -#endif - -#ifdef USE_STATUS_LED - pinMode(STATUS_LED_PIN, OUTPUT); - -// Turn off LED initially -#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - analogWrite(STATUS_LED_PIN, 255); -#elif defined(ARDUINO_ARCH_ESP32) - WS._pwmComponent->attach(STATUS_LED_PIN, LEDC_BASE_FREQ, LEDC_TIMER_12_BIT); - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); // turn OFF -#elif defined(ARDUINO_RASPBERRY_PI_PICO_W) - digitalWrite(STATUS_LED_PIN, 0); -#else - analogWrite(STATUS_LED_PIN, 0); -#endif - - WS.lockStatusLED = true; // set global pin "lock" flag -#endif -} - -/****************************************************************************/ -/*! - @brief De-initializes the status LED and releases pin. -*/ -/****************************************************************************/ -void releaseStatusLED() { -#ifdef USE_STATUS_NEOPIXEL - delete statusPixel; // Deallocate Adafruit_NeoPixel object, set data pin back - // to INPUT. - WS.lockStatusNeoPixel = false; // unlock -#endif - -#ifdef USE_STATUS_DOTSTAR - delete statusPixelDotStar; // Deallocate Adafruit_DotStar object, set data pin - // back to INPUT. - WS.lockStatusDotStar = false; // unlock -#endif - -#ifdef USE_STATUS_LED - digitalWrite(STATUS_LED_PIN, 0); // turn off - pinMode(STATUS_LED_PIN, - INPUT); // "release" for use by setting to input (hi-z) - WS.lockStatusLED = false; // un-set global pin "lock" flag -#endif -} - -/****************************************************************************/ -/*! - @brief Sets the status pixel's brightness - @param brightness - Desired pixel brightness, from 0.0 (0%) to 1.0 (100%). -*/ -/****************************************************************************/ -void setStatusLEDBrightness(float brightness) { - WS.status_pixel_brightness = brightness; -} - -/****************************************************************************/ -/*! - @brief Sets a status RGB LED's color - @param color - Desired RGB color. -*/ -/****************************************************************************/ -void setStatusLEDColor(uint32_t color) { -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // map() the WS.status_pixel_brightness - int brightness = WS.status_pixel_brightness * 255.0; - // flood all neopixels - for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { - statusPixel->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixel->show(); -#endif - -#ifdef USE_STATUS_DOTSTAR - if (!WS.lockStatusDotStar) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // map() the WS.status_pixel_brightness - int brightness = WS.status_pixel_brightness * 255.0; - // flood all dotstar pixels - for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { - statusPixelDotStar->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixelDotStar->show(); -#endif - -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; // status pixel is in-use elsewhere -#ifdef ARDUINO_RASPBERRY_PI_PICO_W - digitalWrite(STATUS_LED_PIN, color > 0); -#else - if (color != BLACK) - WS._pwmComponent->writeDutyCycle( - STATUS_LED_PIN, map(WS.status_pixel_brightness, 0.0, 1.0, 0, 1023)); - else - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); -#endif -#endif -} - -/****************************************************************************/ -/*! - @brief Sets a status RGB LED's color - @param color - Desired RGB color. - @param brightness - Brightness level, as an integer -*/ -/****************************************************************************/ -void setStatusLEDColor(uint32_t color, int brightness) { -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere - - // parse out the color elements - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // flood all neopixels - for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { - statusPixel->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixel->show(); -#endif - -#ifdef USE_STATUS_DOTSTAR - if (!WS.lockStatusDotStar) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // flood all dotstar pixels - for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { - statusPixelDotStar->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixelDotStar->show(); -#endif - -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; - -#ifdef ARDUINO_RASPBERRY_PI_PICO_W - digitalWrite(STATUS_LED_PIN, color > 0); -#else - if (color != BLACK) { - // re-map for pixel as a LED - int pulseWidth = map(brightness, 0, 255, 0, 1023); - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, pulseWidth); - } else { - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); - } -#endif -#endif -} - -/****************************************************************************/ -/*! - @brief Retrieve the pin number used for NeoPixel data output. - @return Arduino pin number (-2 if not set). -*/ -/****************************************************************************/ -int16_t getStatusNeoPixelPin() { -#ifdef USE_STATUS_NEOPIXEL - return statusPixel->getPin(); -#endif - return -2; -} - -/****************************************************************************/ -/*! - @brief Retrieve the pin number used for DotStar data output. - @return Arduino pin number (-2 if not set). -*/ -/****************************************************************************/ -int16_t getStatusDotStarDataPin() { -#ifdef USE_STATUS_DOTSTAR - return STATUS_DOTSTAR_PIN_DATA; -#endif - return -2; -} - -/****************************************************************************/ -/*! - @brief Fades the status LED. - @param color - The specific color to fade the status LED. - @param numFades - The amount of time to fade/pulse the status LED. -*/ -/****************************************************************************/ -void statusLEDFade(uint32_t color, int numFades = 3) { - // don't fade if our pixel is off - if (WS.status_pixel_brightness == 0.0) - return; - - // pulse `numFades` times - for (int i = 0; i < numFades; i++) { - // fade up - for (int i = 0; i <= 255; i += 5) { - setStatusLEDColor(color, i); - delay(10); - } - // fade down - for (int i = 0; i >= 255; i -= 5) { - setStatusLEDColor(color, i); - delay(10); - } - } - -// Turn status LED off -#if not defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - setStatusLEDColor(BLACK); -#else - // The Adafruit Feather ESP8266's built-in LED is reverse wired - setStatusLEDColor(BLACK ^ 1); -#endif -} - -/****************************************************************************/ -/*! - @brief Converts the a ws_led_status_t status state to color. - @param statusState - Hardware's status state. - @return Color as a uint32_t -*/ -/****************************************************************************/ -uint32_t ledStatusStateToColor(ws_led_status_t statusState) { - uint32_t ledColor; - switch (statusState) { - case WS_LED_STATUS_KAT: - ledColor = GREEN; - break; - case WS_LED_STATUS_ERROR_RUNTIME: - ledColor = RED; - break; - case WS_LED_STATUS_WIFI_CONNECTING: - ledColor = AMBER; - break; - case WS_LED_STATUS_MQTT_CONNECTING: - ledColor = BLUE; - break; - case WS_LED_STATUS_WAITING_FOR_REG_MSG: - ledColor = PINK; - break; - case WS_LED_STATUS_FS_WRITE: - ledColor = YELLOW; - break; - default: - ledColor = BLACK; - break; - } - return ledColor; -} - -/****************************************************************************/ -/*! - @brief Sets the status LED to a specific color depending on - the hardware's state. - @param statusState - Hardware's status state. -*/ -/****************************************************************************/ -void statusLEDSolid(ws_led_status_t statusState = WS_LED_STATUS_ERROR_RUNTIME) { -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; -#endif - -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere -#endif - - uint32_t ledColor = ledStatusStateToColor(statusState); - setStatusLEDColor(ledColor); -} - -/****************************************************************************/ -/*! - @brief Blinks a status LED a specific color depending on - the hardware's state. - @param statusState - Hardware's status state. -*/ -/****************************************************************************/ -void statusLEDBlink(ws_led_status_t statusState) { -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; -#endif - -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere -#endif - - // set number of times to blink - int blinkNum = 3; - // set blink color - uint32_t ledColor = ledStatusStateToColor(statusState); - - while (blinkNum > 0) { - setStatusLEDColor(ledColor); - delay(100); -#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - // The Adafruit Feather ESP8266's built-in LED is reverse wired - setStatusLEDColor(BLACK ^ 1); -#else - setStatusLEDColor(BLACK); -#endif - delay(100); - blinkNum--; - } +/*! + * @file Wippersnapper_StatusLED.cpp + * + * Interfaces for the Wippersnapper status indicator LED/NeoPixel/Dotstar/RGB + * LED. + * + * Adafruit invests time and resources providing this open source code, + * please support Adafruit and open-source hardware by purchasing + * products from Adafruit! + * + * Copyright (c) Brent Rubell 2020-2022 for Adafruit Industries. + * + * BSD license, all text here must be included in any redistribution. + * + */ +#include "Wippersnapper_StatusLED.h" +#include "Wippersnapper.h" + +extern Wippersnapper WS; +#ifdef USE_STATUS_NEOPIXEL +Adafruit_NeoPixel *statusPixel = new Adafruit_NeoPixel( + STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); +#endif + +#ifdef USE_STATUS_DOTSTAR +Adafruit_DotStar *statusPixelDotStar = + new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, + STATUS_DOTSTAR_PIN_CLK, DOTSTAR_BRG); +#endif + +/****************************************************************************/ +/*! + @brief Initializes board-specific status LED pixel +*/ +/****************************************************************************/ +void initStatusLED() { +#ifdef USE_STATUS_NEOPIXEL + if (WS.lockStatusNeoPixel == false) { +#if defined(NEOPIXEL_I2C_POWER) + pinMode(NEOPIXEL_I2C_POWER, OUTPUT); + digitalWrite(NEOPIXEL_I2C_POWER, HIGH); +#elif defined(NEOPIXEL_POWER) + pinMode(NEOPIXEL_POWER, OUTPUT); +// turn NeoPixel power pin on +#ifndef ARDUINO_MAGTAG29_ESP32S2 + digitalWrite(NEOPIXEL_POWER, HIGH); +#else + digitalWrite(NEOPIXEL_POWER, LOW); +#endif +#endif + statusPixel = new Adafruit_NeoPixel( + STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); + statusPixel->begin(); + statusPixel->show(); // turn OFF all pixels + WS.lockStatusNeoPixel = true; + } +#endif + +#ifdef USE_STATUS_DOTSTAR + if (WS.lockStatusDotStar == false) { +#ifdef STATUS_DOTSTAR_COLOR_ORDER + // Board requires a non-default color order in the constructor + statusPixelDotStar = new Adafruit_DotStar( + STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, STATUS_DOTSTAR_PIN_CLK, + STATUS_DOTSTAR_COLOR_ORDER); +#else + statusPixelDotStar = + new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, + STATUS_DOTSTAR_PIN_CLK, STATUS_DOTSTAR_COLOR_ORDER) +#endif + statusPixelDotStar->begin(); + statusPixelDotStar->show(); // turn OFF all pixels + WS.lockStatusDotStar = true; + } +#endif + +#ifdef USE_STATUS_LED + pinMode(STATUS_LED_PIN, OUTPUT); + +// Turn off LED initially +#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + analogWrite(STATUS_LED_PIN, 255); +#elif defined(ARDUINO_ARCH_ESP32) + WS._pwmComponent->attach(STATUS_LED_PIN, LEDC_BASE_FREQ, LEDC_TIMER_12_BIT); + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); // turn OFF +#elif defined(ARDUINO_ARCH_RP2040) + digitalWrite(STATUS_LED_PIN, 0); +#else + analogWrite(STATUS_LED_PIN, 0); +#endif + + WS.lockStatusLED = true; // set global pin "lock" flag +#endif +} + +/****************************************************************************/ +/*! + @brief De-initializes the status LED and releases pin. +*/ +/****************************************************************************/ +void releaseStatusLED() { +#ifdef USE_STATUS_NEOPIXEL + delete statusPixel; // Deallocate Adafruit_NeoPixel object, set data pin back + // to INPUT. + WS.lockStatusNeoPixel = false; // unlock +#endif + +#ifdef USE_STATUS_DOTSTAR + delete statusPixelDotStar; // Deallocate Adafruit_DotStar object, set data pin + // back to INPUT. + WS.lockStatusDotStar = false; // unlock +#endif + +#ifdef USE_STATUS_LED + digitalWrite(STATUS_LED_PIN, 0); // turn off + pinMode(STATUS_LED_PIN, + INPUT); // "release" for use by setting to input (hi-z) + WS.lockStatusLED = false; // un-set global pin "lock" flag +#endif +} + +/****************************************************************************/ +/*! + @brief Sets the status pixel's brightness + @param brightness + Desired pixel brightness, from 0.0 (0%) to 1.0 (100%). +*/ +/****************************************************************************/ +void setStatusLEDBrightness(float brightness) { + WS.status_pixel_brightness = brightness; +} + +/****************************************************************************/ +/*! + @brief Sets a status RGB LED's color + @param color + Desired RGB color. +*/ +/****************************************************************************/ +void setStatusLEDColor(uint32_t color) { +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // map() the WS.status_pixel_brightness + int brightness = WS.status_pixel_brightness * 255.0; + // flood all neopixels + for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { + statusPixel->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixel->show(); +#endif + +#ifdef USE_STATUS_DOTSTAR + if (!WS.lockStatusDotStar) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // map() the WS.status_pixel_brightness + int brightness = WS.status_pixel_brightness * 255.0; + // flood all dotstar pixels + for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { + statusPixelDotStar->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixelDotStar->show(); +#endif + +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; // status pixel is in-use elsewhere +#ifdef ARDUINO_ARCH_RP2040 + digitalWrite(STATUS_LED_PIN, color > 0); +#else + if (color != BLACK) + WS._pwmComponent->writeDutyCycle( + STATUS_LED_PIN, map(WS.status_pixel_brightness, 0.0, 1.0, 0, 1023)); + else + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); +#endif +#endif +} + +/****************************************************************************/ +/*! + @brief Sets a status RGB LED's color + @param color + Desired RGB color. + @param brightness + Brightness level, as an integer +*/ +/****************************************************************************/ +void setStatusLEDColor(uint32_t color, int brightness) { +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere + + // parse out the color elements + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // flood all neopixels + for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { + statusPixel->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixel->show(); +#endif + +#ifdef USE_STATUS_DOTSTAR + if (!WS.lockStatusDotStar) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // flood all dotstar pixels + for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { + statusPixelDotStar->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixelDotStar->show(); +#endif + +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; + +#ifdef ARDUINO_ARCH_RP2040 + digitalWrite(STATUS_LED_PIN, color > 0); +#else + if (color != BLACK) { + // re-map for pixel as a LED + int pulseWidth = map(brightness, 0, 255, 0, 1023); + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, pulseWidth); + } else { + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); + } +#endif +#endif +} + +/****************************************************************************/ +/*! + @brief Retrieve the pin number used for NeoPixel data output. + @return Arduino pin number (-2 if not set). +*/ +/****************************************************************************/ +int16_t getStatusNeoPixelPin() { +#ifdef USE_STATUS_NEOPIXEL + return statusPixel->getPin(); +#endif + return -2; +} + +/****************************************************************************/ +/*! + @brief Retrieve the pin number used for DotStar data output. + @return Arduino pin number (-2 if not set). +*/ +/****************************************************************************/ +int16_t getStatusDotStarDataPin() { +#ifdef USE_STATUS_DOTSTAR + return STATUS_DOTSTAR_PIN_DATA; +#endif + return -2; +} + +/****************************************************************************/ +/*! + @brief Fades the status LED. + @param color + The specific color to fade the status LED. + @param numFades + The amount of time to fade/pulse the status LED. +*/ +/****************************************************************************/ +void statusLEDFade(uint32_t color, int numFades = 3) { + // don't fade if our pixel is off + if (WS.status_pixel_brightness == 0.0) + return; + + // pulse `numFades` times + for (int i = 0; i < numFades; i++) { + // fade up + for (int i = 0; i <= 255; i += 5) { + setStatusLEDColor(color, i); + delay(10); + } + // fade down + for (int i = 0; i >= 255; i -= 5) { + setStatusLEDColor(color, i); + delay(10); + } + } + +// Turn status LED off +#if not defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + setStatusLEDColor(BLACK); +#else + // The Adafruit Feather ESP8266's built-in LED is reverse wired + setStatusLEDColor(BLACK ^ 1); +#endif +} + +/****************************************************************************/ +/*! + @brief Converts the a ws_led_status_t status state to color. + @param statusState + Hardware's status state. + @return Color as a uint32_t +*/ +/****************************************************************************/ +uint32_t ledStatusStateToColor(ws_led_status_t statusState) { + uint32_t ledColor; + switch (statusState) { + case WS_LED_STATUS_KAT: + ledColor = GREEN; + break; + case WS_LED_STATUS_ERROR_RUNTIME: + ledColor = RED; + break; + case WS_LED_STATUS_WIFI_CONNECTING: + ledColor = AMBER; + break; + case WS_LED_STATUS_MQTT_CONNECTING: + ledColor = BLUE; + break; + case WS_LED_STATUS_WAITING_FOR_REG_MSG: + ledColor = PINK; + break; + case WS_LED_STATUS_FS_WRITE: + ledColor = YELLOW; + break; + default: + ledColor = BLACK; + break; + } + return ledColor; +} + +/****************************************************************************/ +/*! + @brief Sets the status LED to a specific color depending on + the hardware's state. + @param statusState + Hardware's status state. +*/ +/****************************************************************************/ +void statusLEDSolid(ws_led_status_t statusState = WS_LED_STATUS_ERROR_RUNTIME) { +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; +#endif + +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere +#endif + + uint32_t ledColor = ledStatusStateToColor(statusState); + setStatusLEDColor(ledColor); +} + +/****************************************************************************/ +/*! + @brief Blinks a status LED a specific color depending on + the hardware's state. + @param statusState + Hardware's status state. +*/ +/****************************************************************************/ +void statusLEDBlink(ws_led_status_t statusState) { +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; +#endif + +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere +#endif + + // set number of times to blink + int blinkNum = 3; + // set blink color + uint32_t ledColor = ledStatusStateToColor(statusState); + + while (blinkNum > 0) { + setStatusLEDColor(ledColor); + delay(100); +#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + // The Adafruit Feather ESP8266's built-in LED is reverse wired + setStatusLEDColor(BLACK ^ 1); +#else + setStatusLEDColor(BLACK); +#endif + delay(100); + blinkNum--; + } } \ No newline at end of file diff --git a/src/provisioning/tinyusb/Wippersnapper_FS.cpp b/src/provisioning/tinyusb/Wippersnapper_FS.cpp index d99c6098b..74e58a90f 100644 --- a/src/provisioning/tinyusb/Wippersnapper_FS.cpp +++ b/src/provisioning/tinyusb/Wippersnapper_FS.cpp @@ -24,7 +24,7 @@ defined(ARDUINO_ADAFRUIT_QTPY_ESP32S3_NOPSRAM) || \ defined(ARDUINO_ADAFRUIT_FEATHER_ESP32S3) || \ defined(ARDUINO_ADAFRUIT_FEATHER_ESP32S3_TFT) || \ - defined(ARDUINO_RASPBERRY_PI_PICO_W) || \ + defined(ARDUINO_ARCH_RP2040) || \ defined(ARDUINO_ADAFRUIT_FEATHER_ESP32S3_REVTFT) || \ defined(ARDUINO_ADAFRUIT_FEATHER_ESP32S2_REVTFT) || \ defined(ARDUINO_ADAFRUIT_QTPY_ESP32S3_N4R2) From 8ea03941be6784d7c24df6809e698a5814d1d862 Mon Sep 17 00:00:00 2001 From: tyeth Date: Wed, 27 Nov 2024 18:05:21 +0000 Subject: [PATCH 2/7] Add tinyusb to pico2w non debug target --- platformio.ini | 1 + 1 file changed, 1 insertion(+) diff --git a/platformio.ini b/platformio.ini index 427a7ea94..149c92bae 100644 --- a/platformio.ini +++ b/platformio.ini @@ -522,6 +522,7 @@ platform_packages = board = rpipico2w build_flags = -DWIFICC=CYW43_COUNTRY_UK + -DUSE_TINYUSB ; -DARDUINO_ARCH_RP2040 ; -DUSBD_MAX_POWER_MA=500 ; -DPICO_CYW43_SUPPORTED=1 From 9b8479425cc95a6dc2603af570e77c38f3a62486 Mon Sep 17 00:00:00 2001 From: tyeth Date: Thu, 28 Nov 2024 15:29:55 +0000 Subject: [PATCH 3/7] Add .test.skip/.generate and CI test --- .github/workflows/build-clang-doxy.yml | 4 ++-- examples/Wippersnapper_NoFS/.picow_rp2350_tinyusb.test.skip | 1 + examples/Wippersnapper_demo/.picow_rp2350_tinyusb.generate | 1 + examples/wippersnapper_debug/.picow_rp2350_tinyusb.test.skip | 1 + 4 files changed, 5 insertions(+), 2 deletions(-) create mode 100644 examples/Wippersnapper_NoFS/.picow_rp2350_tinyusb.test.skip create mode 100644 examples/Wippersnapper_demo/.picow_rp2350_tinyusb.generate create mode 100644 examples/wippersnapper_debug/.picow_rp2350_tinyusb.test.skip diff --git a/.github/workflows/build-clang-doxy.yml b/.github/workflows/build-clang-doxy.yml index 084aca223..b35ab4792 100644 --- a/.github/workflows/build-clang-doxy.yml +++ b/.github/workflows/build-clang-doxy.yml @@ -494,7 +494,7 @@ jobs: strategy: fail-fast: false matrix: - arduino-platform: ["picow_rp2040_tinyusb"] + arduino-platform: ["picow_rp2040_tinyusb", "picow_rp2350_tinyusb"] steps: - uses: actions/setup-python@v5 with: @@ -508,7 +508,7 @@ jobs: - uses: actions/checkout@v4 with: repository: adafruit/ci-arduino - ref: ci-wippersnapper + ref: ci-wippersnapper-rp2040 path: ci - name: Install CI-Arduino run: bash ci/actions_install.sh diff --git a/examples/Wippersnapper_NoFS/.picow_rp2350_tinyusb.test.skip b/examples/Wippersnapper_NoFS/.picow_rp2350_tinyusb.test.skip new file mode 100644 index 000000000..d3f5a12fa --- /dev/null +++ b/examples/Wippersnapper_NoFS/.picow_rp2350_tinyusb.test.skip @@ -0,0 +1 @@ + diff --git a/examples/Wippersnapper_demo/.picow_rp2350_tinyusb.generate b/examples/Wippersnapper_demo/.picow_rp2350_tinyusb.generate new file mode 100644 index 000000000..d3f5a12fa --- /dev/null +++ b/examples/Wippersnapper_demo/.picow_rp2350_tinyusb.generate @@ -0,0 +1 @@ + diff --git a/examples/wippersnapper_debug/.picow_rp2350_tinyusb.test.skip b/examples/wippersnapper_debug/.picow_rp2350_tinyusb.test.skip new file mode 100644 index 000000000..d3f5a12fa --- /dev/null +++ b/examples/wippersnapper_debug/.picow_rp2350_tinyusb.test.skip @@ -0,0 +1 @@ + From 0f91cb9cfbabe8267479522b7a8495ff83bd470c Mon Sep 17 00:00:00 2001 From: tyeth Date: Fri, 29 Nov 2024 14:42:04 +0000 Subject: [PATCH 4/7] Swap back to official repos since upstreaming --- platformio.ini | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/platformio.ini b/platformio.ini index 149c92bae..d66126ff7 100644 --- a/platformio.ini +++ b/platformio.ini @@ -71,7 +71,7 @@ lib_deps = adafruit/Adafruit TouchScreen adafruit/Adafruit MQTT Library bblanchon/ArduinoJson - https://github.com/tyeth/pstolarz_OneWireNg.git#pico2w + https://github.com/pstolarz/OneWireNg.git https://github.com/milesburton/Arduino-Temperature-Control-Library.git https://github.com/Sensirion/arduino-sht.git https://github.com/Sensirion/arduino-i2c-scd4x.git @@ -473,7 +473,7 @@ extends = common:rp2040 [env:raspberypi_picow_debug] extends = common:rp2040 -platform = https://github.com/maxgerhardt/platform-raspberrypi.git +; platform = https://github.com/maxgerhardt/platform-raspberrypi.git ; platform_packages = ; framework-arduinopico @ symlink:///Users/tyeth/Projects/arduino-pico ; framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git#master @@ -515,8 +515,7 @@ build_flags = [env:raspberypi_pico2w] extends = common:rp2040 -platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w -; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop +platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop platform_packages = framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git board = rpipico2w @@ -529,8 +528,7 @@ build_flags = [env:raspberypi_pico2w_debug] extends = common:rp2040 -platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w -; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop +platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop platform_packages = framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git ; ; framework-arduinopico @ symlink:///Users/tyeth/Projects/arduino-pico From 1ceafabf7a1515686cdde50e6b7543bd2d03e3b3 Mon Sep 17 00:00:00 2001 From: tyeth Date: Fri, 29 Nov 2024 14:46:42 +0000 Subject: [PATCH 5/7] Swap RP2040 CI-Arduino branch back to ci-wippersnapper --- .github/workflows/build-clang-doxy.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/build-clang-doxy.yml b/.github/workflows/build-clang-doxy.yml index b35ab4792..7db6818c9 100644 --- a/.github/workflows/build-clang-doxy.yml +++ b/.github/workflows/build-clang-doxy.yml @@ -508,7 +508,7 @@ jobs: - uses: actions/checkout@v4 with: repository: adafruit/ci-arduino - ref: ci-wippersnapper-rp2040 + ref: ci-wippersnapper path: ci - name: Install CI-Arduino run: bash ci/actions_install.sh From e92cd181ec4befbff428882008fe6295d93f6e91 Mon Sep 17 00:00:00 2001 From: tyeth Date: Mon, 2 Dec 2024 19:54:59 +0000 Subject: [PATCH 6/7] Add Pico2W definition to boards list + fix LEDs --- platformio.ini | 19 ++----------------- src/Wippersnapper_Boards.h | 9 +++++++-- 2 files changed, 9 insertions(+), 19 deletions(-) diff --git a/platformio.ini b/platformio.ini index d66126ff7..3a65738be 100644 --- a/platformio.ini +++ b/platformio.ini @@ -523,7 +523,7 @@ build_flags = -DWIFICC=CYW43_COUNTRY_UK -DUSE_TINYUSB ; -DARDUINO_ARCH_RP2040 - ; -DUSBD_MAX_POWER_MA=500 + ; -DUSBD_MAX_POWER_MA=250 ; -DPICO_CYW43_SUPPORTED=1 [env:raspberypi_pico2w_debug] @@ -545,7 +545,7 @@ build_flags = ; -UARDUINO ; -DPICO_BUILD -DARDUINO_ARCH_RP2040 - -DUSBD_MAX_POWER_MA=500 + -DUSBD_MAX_POWER_MA=250 -DPICO_CYW43_SUPPORTED=1 -DWIFICC=CYW43_COUNTRY_UK ; -DDEBUG @@ -571,18 +571,3 @@ build_flags = ; ; No USB stack ; build_flags = -DPIO_FRAMEWORK_ARDUINO_NO_USB ; -DPIO_FRAMEWORK_ARDUINO_ENABLE_IPV6 - - -[env:pimoroni_pico_plus_2w] -extends = common:rp2040 -platform = https://github.com/tyeth/maxgerhardt_platform-raspberrypi.git#pico2w -; platform = https://github.com/maxgerhardt/platform-raspberrypi.git#develop -platform_packages = - framework-arduinopico@https://github.com/earlephilhower/arduino-pico.git -board = pimoroni_pico_plus_2w -build_flags = - -DWIFICC=CYW43_COUNTRY_UK - -DUSE_TINYUSB - ; -DARDUINO_ARCH_RP2040 - ; -DUSBD_MAX_POWER_MA=500 - ; -DPICO_CYW43_SUPPORTED=1 diff --git a/src/Wippersnapper_Boards.h b/src/Wippersnapper_Boards.h index 4e89862e0..f98acb4e5 100644 --- a/src/Wippersnapper_Boards.h +++ b/src/Wippersnapper_Boards.h @@ -185,11 +185,16 @@ #define BOARD_ID "mkrwifi1010" #define USE_STATUS_LED #define STATUS_LED_PIN 6 -#elif defined(ARDUINO_RASPBERRY_PI_PICO_W) || defined(ARDUINO_ARCH_RP2040) +#elif defined(ARDUINO_RASPBERRY_PI_PICO_W) #define BOARD_ID "rpi-pico-w" #define USE_TINYUSB #define USE_STATUS_LED -#define STATUS_LED_PIN 32 +#define STATUS_LED_PIN LED_BUILTIN +#elif defined(ARDUINO_RASPBERRY_PI_PICO_2W) +#define BOARD_ID "rpi-pico-2w" +#define USE_TINYUSB +#define USE_STATUS_LED +#define STATUS_LED_PIN LED_BUILTIN #else #warning "Board type not identified within Wippersnapper_Boards.h!" #endif From 45461242f2064fe8fbc08e2b612b5f663f63dd2a Mon Sep 17 00:00:00 2001 From: tyeth Date: Tue, 10 Dec 2024 18:42:38 +0000 Subject: [PATCH 7/7] Report BSSID's to help distinguish wifi networks --- platformio.ini | 2 +- .../statusLED/Wippersnapper_StatusLED.cpp | 820 +++++++++--------- src/network_interfaces/ws_networking_pico.h | 19 +- 3 files changed, 426 insertions(+), 415 deletions(-) diff --git a/platformio.ini b/platformio.ini index 3a65738be..6b8decfd5 100644 --- a/platformio.ini +++ b/platformio.ini @@ -494,7 +494,7 @@ build_flags = -DDEBUG_RP2040_CORE -DDEBUG_RP2040_WIFI -DNDEBUG - -DLWIP_DEBUG + -DLWIP_DEBUG=1 -DDEBUG_RP2040_PORT=Serial1 -DDEBUG_RP2040_UART_1 -DDEBUG_RP2040_UART=1 diff --git a/src/components/statusLED/Wippersnapper_StatusLED.cpp b/src/components/statusLED/Wippersnapper_StatusLED.cpp index ba9061cb2..464e0b8ba 100644 --- a/src/components/statusLED/Wippersnapper_StatusLED.cpp +++ b/src/components/statusLED/Wippersnapper_StatusLED.cpp @@ -1,411 +1,411 @@ -/*! - * @file Wippersnapper_StatusLED.cpp - * - * Interfaces for the Wippersnapper status indicator LED/NeoPixel/Dotstar/RGB - * LED. - * - * Adafruit invests time and resources providing this open source code, - * please support Adafruit and open-source hardware by purchasing - * products from Adafruit! - * - * Copyright (c) Brent Rubell 2020-2022 for Adafruit Industries. - * - * BSD license, all text here must be included in any redistribution. - * - */ -#include "Wippersnapper_StatusLED.h" -#include "Wippersnapper.h" - -extern Wippersnapper WS; -#ifdef USE_STATUS_NEOPIXEL -Adafruit_NeoPixel *statusPixel = new Adafruit_NeoPixel( - STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); -#endif - -#ifdef USE_STATUS_DOTSTAR -Adafruit_DotStar *statusPixelDotStar = - new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, - STATUS_DOTSTAR_PIN_CLK, DOTSTAR_BRG); -#endif - -/****************************************************************************/ -/*! - @brief Initializes board-specific status LED pixel -*/ -/****************************************************************************/ -void initStatusLED() { -#ifdef USE_STATUS_NEOPIXEL - if (WS.lockStatusNeoPixel == false) { -#if defined(NEOPIXEL_I2C_POWER) - pinMode(NEOPIXEL_I2C_POWER, OUTPUT); - digitalWrite(NEOPIXEL_I2C_POWER, HIGH); -#elif defined(NEOPIXEL_POWER) - pinMode(NEOPIXEL_POWER, OUTPUT); -// turn NeoPixel power pin on -#ifndef ARDUINO_MAGTAG29_ESP32S2 - digitalWrite(NEOPIXEL_POWER, HIGH); -#else - digitalWrite(NEOPIXEL_POWER, LOW); -#endif -#endif - statusPixel = new Adafruit_NeoPixel( - STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); - statusPixel->begin(); - statusPixel->show(); // turn OFF all pixels - WS.lockStatusNeoPixel = true; - } -#endif - -#ifdef USE_STATUS_DOTSTAR - if (WS.lockStatusDotStar == false) { -#ifdef STATUS_DOTSTAR_COLOR_ORDER - // Board requires a non-default color order in the constructor - statusPixelDotStar = new Adafruit_DotStar( - STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, STATUS_DOTSTAR_PIN_CLK, - STATUS_DOTSTAR_COLOR_ORDER); -#else - statusPixelDotStar = - new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, - STATUS_DOTSTAR_PIN_CLK, STATUS_DOTSTAR_COLOR_ORDER) -#endif - statusPixelDotStar->begin(); - statusPixelDotStar->show(); // turn OFF all pixels - WS.lockStatusDotStar = true; - } -#endif - -#ifdef USE_STATUS_LED - pinMode(STATUS_LED_PIN, OUTPUT); - -// Turn off LED initially -#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - analogWrite(STATUS_LED_PIN, 255); -#elif defined(ARDUINO_ARCH_ESP32) - WS._pwmComponent->attach(STATUS_LED_PIN, LEDC_BASE_FREQ, LEDC_TIMER_12_BIT); - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); // turn OFF -#elif defined(ARDUINO_ARCH_RP2040) - digitalWrite(STATUS_LED_PIN, 0); -#else - analogWrite(STATUS_LED_PIN, 0); -#endif - - WS.lockStatusLED = true; // set global pin "lock" flag -#endif -} - -/****************************************************************************/ -/*! - @brief De-initializes the status LED and releases pin. -*/ -/****************************************************************************/ -void releaseStatusLED() { -#ifdef USE_STATUS_NEOPIXEL - delete statusPixel; // Deallocate Adafruit_NeoPixel object, set data pin back - // to INPUT. - WS.lockStatusNeoPixel = false; // unlock -#endif - -#ifdef USE_STATUS_DOTSTAR - delete statusPixelDotStar; // Deallocate Adafruit_DotStar object, set data pin - // back to INPUT. - WS.lockStatusDotStar = false; // unlock -#endif - -#ifdef USE_STATUS_LED - digitalWrite(STATUS_LED_PIN, 0); // turn off - pinMode(STATUS_LED_PIN, - INPUT); // "release" for use by setting to input (hi-z) - WS.lockStatusLED = false; // un-set global pin "lock" flag -#endif -} - -/****************************************************************************/ -/*! - @brief Sets the status pixel's brightness - @param brightness - Desired pixel brightness, from 0.0 (0%) to 1.0 (100%). -*/ -/****************************************************************************/ -void setStatusLEDBrightness(float brightness) { - WS.status_pixel_brightness = brightness; -} - -/****************************************************************************/ -/*! - @brief Sets a status RGB LED's color - @param color - Desired RGB color. -*/ -/****************************************************************************/ -void setStatusLEDColor(uint32_t color) { -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // map() the WS.status_pixel_brightness - int brightness = WS.status_pixel_brightness * 255.0; - // flood all neopixels - for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { - statusPixel->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixel->show(); -#endif - -#ifdef USE_STATUS_DOTSTAR - if (!WS.lockStatusDotStar) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // map() the WS.status_pixel_brightness - int brightness = WS.status_pixel_brightness * 255.0; - // flood all dotstar pixels - for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { - statusPixelDotStar->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixelDotStar->show(); -#endif - -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; // status pixel is in-use elsewhere -#ifdef ARDUINO_ARCH_RP2040 - digitalWrite(STATUS_LED_PIN, color > 0); -#else - if (color != BLACK) - WS._pwmComponent->writeDutyCycle( - STATUS_LED_PIN, map(WS.status_pixel_brightness, 0.0, 1.0, 0, 1023)); - else - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); -#endif -#endif -} - -/****************************************************************************/ -/*! - @brief Sets a status RGB LED's color - @param color - Desired RGB color. - @param brightness - Brightness level, as an integer -*/ -/****************************************************************************/ -void setStatusLEDColor(uint32_t color, int brightness) { -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere - - // parse out the color elements - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // flood all neopixels - for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { - statusPixel->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixel->show(); -#endif - -#ifdef USE_STATUS_DOTSTAR - if (!WS.lockStatusDotStar) - return; // status pixel is in-use elsewhere - - uint8_t red = (color >> 16) & 0xff; // red - uint8_t green = (color >> 8) & 0xff; // green - uint8_t blue = color & 0xff; // blue - // flood all dotstar pixels - for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { - statusPixelDotStar->setPixelColor(i, brightness * red / 255, - brightness * green / 255, - brightness * blue / 255); - } - statusPixelDotStar->show(); -#endif - -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; - -#ifdef ARDUINO_ARCH_RP2040 - digitalWrite(STATUS_LED_PIN, color > 0); -#else - if (color != BLACK) { - // re-map for pixel as a LED - int pulseWidth = map(brightness, 0, 255, 0, 1023); - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, pulseWidth); - } else { - WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); - } -#endif -#endif -} - -/****************************************************************************/ -/*! - @brief Retrieve the pin number used for NeoPixel data output. - @return Arduino pin number (-2 if not set). -*/ -/****************************************************************************/ -int16_t getStatusNeoPixelPin() { -#ifdef USE_STATUS_NEOPIXEL - return statusPixel->getPin(); -#endif - return -2; -} - -/****************************************************************************/ -/*! - @brief Retrieve the pin number used for DotStar data output. - @return Arduino pin number (-2 if not set). -*/ -/****************************************************************************/ -int16_t getStatusDotStarDataPin() { -#ifdef USE_STATUS_DOTSTAR - return STATUS_DOTSTAR_PIN_DATA; -#endif - return -2; -} - -/****************************************************************************/ -/*! - @brief Fades the status LED. - @param color - The specific color to fade the status LED. - @param numFades - The amount of time to fade/pulse the status LED. -*/ -/****************************************************************************/ -void statusLEDFade(uint32_t color, int numFades = 3) { - // don't fade if our pixel is off - if (WS.status_pixel_brightness == 0.0) - return; - - // pulse `numFades` times - for (int i = 0; i < numFades; i++) { - // fade up - for (int i = 0; i <= 255; i += 5) { - setStatusLEDColor(color, i); - delay(10); - } - // fade down - for (int i = 0; i >= 255; i -= 5) { - setStatusLEDColor(color, i); - delay(10); - } - } - -// Turn status LED off -#if not defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - setStatusLEDColor(BLACK); -#else - // The Adafruit Feather ESP8266's built-in LED is reverse wired - setStatusLEDColor(BLACK ^ 1); -#endif -} - -/****************************************************************************/ -/*! - @brief Converts the a ws_led_status_t status state to color. - @param statusState - Hardware's status state. - @return Color as a uint32_t -*/ -/****************************************************************************/ -uint32_t ledStatusStateToColor(ws_led_status_t statusState) { - uint32_t ledColor; - switch (statusState) { - case WS_LED_STATUS_KAT: - ledColor = GREEN; - break; - case WS_LED_STATUS_ERROR_RUNTIME: - ledColor = RED; - break; - case WS_LED_STATUS_WIFI_CONNECTING: - ledColor = AMBER; - break; - case WS_LED_STATUS_MQTT_CONNECTING: - ledColor = BLUE; - break; - case WS_LED_STATUS_WAITING_FOR_REG_MSG: - ledColor = PINK; - break; - case WS_LED_STATUS_FS_WRITE: - ledColor = YELLOW; - break; - default: - ledColor = BLACK; - break; - } - return ledColor; -} - -/****************************************************************************/ -/*! - @brief Sets the status LED to a specific color depending on - the hardware's state. - @param statusState - Hardware's status state. -*/ -/****************************************************************************/ -void statusLEDSolid(ws_led_status_t statusState = WS_LED_STATUS_ERROR_RUNTIME) { -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; -#endif - -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere -#endif - - uint32_t ledColor = ledStatusStateToColor(statusState); - setStatusLEDColor(ledColor); -} - -/****************************************************************************/ -/*! - @brief Blinks a status LED a specific color depending on - the hardware's state. - @param statusState - Hardware's status state. -*/ -/****************************************************************************/ -void statusLEDBlink(ws_led_status_t statusState) { -#ifdef USE_STATUS_LED - if (!WS.lockStatusLED) - return; -#endif - -#ifdef USE_STATUS_NEOPIXEL - if (!WS.lockStatusNeoPixel) - return; // status pixel is in-use elsewhere -#endif - - // set number of times to blink - int blinkNum = 3; - // set blink color - uint32_t ledColor = ledStatusStateToColor(statusState); - - while (blinkNum > 0) { - setStatusLEDColor(ledColor); - delay(100); -#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) - // The Adafruit Feather ESP8266's built-in LED is reverse wired - setStatusLEDColor(BLACK ^ 1); -#else - setStatusLEDColor(BLACK); -#endif - delay(100); - blinkNum--; - } +/*! + * @file Wippersnapper_StatusLED.cpp + * + * Interfaces for the Wippersnapper status indicator LED/NeoPixel/Dotstar/RGB + * LED. + * + * Adafruit invests time and resources providing this open source code, + * please support Adafruit and open-source hardware by purchasing + * products from Adafruit! + * + * Copyright (c) Brent Rubell 2020-2022 for Adafruit Industries. + * + * BSD license, all text here must be included in any redistribution. + * + */ +#include "Wippersnapper_StatusLED.h" +#include "Wippersnapper.h" + +extern Wippersnapper WS; +#ifdef USE_STATUS_NEOPIXEL +Adafruit_NeoPixel *statusPixel = new Adafruit_NeoPixel( + STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); +#endif + +#ifdef USE_STATUS_DOTSTAR +Adafruit_DotStar *statusPixelDotStar = + new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, + STATUS_DOTSTAR_PIN_CLK, DOTSTAR_BRG); +#endif + +/****************************************************************************/ +/*! + @brief Initializes board-specific status LED pixel +*/ +/****************************************************************************/ +void initStatusLED() { +#ifdef USE_STATUS_NEOPIXEL + if (WS.lockStatusNeoPixel == false) { +#if defined(NEOPIXEL_I2C_POWER) + pinMode(NEOPIXEL_I2C_POWER, OUTPUT); + digitalWrite(NEOPIXEL_I2C_POWER, HIGH); +#elif defined(NEOPIXEL_POWER) + pinMode(NEOPIXEL_POWER, OUTPUT); +// turn NeoPixel power pin on +#ifndef ARDUINO_MAGTAG29_ESP32S2 + digitalWrite(NEOPIXEL_POWER, HIGH); +#else + digitalWrite(NEOPIXEL_POWER, LOW); +#endif +#endif + statusPixel = new Adafruit_NeoPixel( + STATUS_NEOPIXEL_NUM, STATUS_NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800); + statusPixel->begin(); + statusPixel->show(); // turn OFF all pixels + WS.lockStatusNeoPixel = true; + } +#endif + +#ifdef USE_STATUS_DOTSTAR + if (WS.lockStatusDotStar == false) { +#ifdef STATUS_DOTSTAR_COLOR_ORDER + // Board requires a non-default color order in the constructor + statusPixelDotStar = new Adafruit_DotStar( + STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, STATUS_DOTSTAR_PIN_CLK, + STATUS_DOTSTAR_COLOR_ORDER); +#else + statusPixelDotStar = + new Adafruit_DotStar(STATUS_DOTSTAR_NUM, STATUS_DOTSTAR_PIN_DATA, + STATUS_DOTSTAR_PIN_CLK, STATUS_DOTSTAR_COLOR_ORDER) +#endif + statusPixelDotStar->begin(); + statusPixelDotStar->show(); // turn OFF all pixels + WS.lockStatusDotStar = true; + } +#endif + +#ifdef USE_STATUS_LED + pinMode(STATUS_LED_PIN, OUTPUT); + +// Turn off LED initially +#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + analogWrite(STATUS_LED_PIN, 255); +#elif defined(ARDUINO_ARCH_ESP32) + WS._pwmComponent->attach(STATUS_LED_PIN, LEDC_BASE_FREQ, LEDC_TIMER_12_BIT); + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); // turn OFF +#elif defined(ARDUINO_ARCH_RP2040) + digitalWrite(STATUS_LED_PIN, 0); +#else + analogWrite(STATUS_LED_PIN, 0); +#endif + + WS.lockStatusLED = true; // set global pin "lock" flag +#endif +} + +/****************************************************************************/ +/*! + @brief De-initializes the status LED and releases pin. +*/ +/****************************************************************************/ +void releaseStatusLED() { +#ifdef USE_STATUS_NEOPIXEL + delete statusPixel; // Deallocate Adafruit_NeoPixel object, set data pin back + // to INPUT. + WS.lockStatusNeoPixel = false; // unlock +#endif + +#ifdef USE_STATUS_DOTSTAR + delete statusPixelDotStar; // Deallocate Adafruit_DotStar object, set data pin + // back to INPUT. + WS.lockStatusDotStar = false; // unlock +#endif + +#ifdef USE_STATUS_LED + digitalWrite(STATUS_LED_PIN, 0); // turn off + pinMode(STATUS_LED_PIN, + INPUT); // "release" for use by setting to input (hi-z) + WS.lockStatusLED = false; // un-set global pin "lock" flag +#endif +} + +/****************************************************************************/ +/*! + @brief Sets the status pixel's brightness + @param brightness + Desired pixel brightness, from 0.0 (0%) to 1.0 (100%). +*/ +/****************************************************************************/ +void setStatusLEDBrightness(float brightness) { + WS.status_pixel_brightness = brightness; +} + +/****************************************************************************/ +/*! + @brief Sets a status RGB LED's color + @param color + Desired RGB color. +*/ +/****************************************************************************/ +void setStatusLEDColor(uint32_t color) { +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // map() the WS.status_pixel_brightness + int brightness = WS.status_pixel_brightness * 255.0; + // flood all neopixels + for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { + statusPixel->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixel->show(); +#endif + +#ifdef USE_STATUS_DOTSTAR + if (!WS.lockStatusDotStar) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // map() the WS.status_pixel_brightness + int brightness = WS.status_pixel_brightness * 255.0; + // flood all dotstar pixels + for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { + statusPixelDotStar->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixelDotStar->show(); +#endif + +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; // status pixel is in-use elsewhere +#ifdef ARDUINO_ARCH_RP2040 + digitalWrite(STATUS_LED_PIN, color > 0); +#else + if (color != BLACK) + WS._pwmComponent->writeDutyCycle( + STATUS_LED_PIN, map(WS.status_pixel_brightness, 0.0, 1.0, 0, 1023)); + else + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); +#endif +#endif +} + +/****************************************************************************/ +/*! + @brief Sets a status RGB LED's color + @param color + Desired RGB color. + @param brightness + Brightness level, as an integer +*/ +/****************************************************************************/ +void setStatusLEDColor(uint32_t color, int brightness) { +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere + + // parse out the color elements + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // flood all neopixels + for (int i = 0; i < STATUS_NEOPIXEL_NUM; i++) { + statusPixel->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixel->show(); +#endif + +#ifdef USE_STATUS_DOTSTAR + if (!WS.lockStatusDotStar) + return; // status pixel is in-use elsewhere + + uint8_t red = (color >> 16) & 0xff; // red + uint8_t green = (color >> 8) & 0xff; // green + uint8_t blue = color & 0xff; // blue + // flood all dotstar pixels + for (int i = 0; i < STATUS_DOTSTAR_NUM; i++) { + statusPixelDotStar->setPixelColor(i, brightness * red / 255, + brightness * green / 255, + brightness * blue / 255); + } + statusPixelDotStar->show(); +#endif + +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; + +#ifdef ARDUINO_ARCH_RP2040 + digitalWrite(STATUS_LED_PIN, color > 0); +#else + if (color != BLACK) { + // re-map for pixel as a LED + int pulseWidth = map(brightness, 0, 255, 0, 1023); + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, pulseWidth); + } else { + WS._pwmComponent->writeDutyCycle(STATUS_LED_PIN, 0); + } +#endif +#endif +} + +/****************************************************************************/ +/*! + @brief Retrieve the pin number used for NeoPixel data output. + @return Arduino pin number (-2 if not set). +*/ +/****************************************************************************/ +int16_t getStatusNeoPixelPin() { +#ifdef USE_STATUS_NEOPIXEL + return statusPixel->getPin(); +#endif + return -2; +} + +/****************************************************************************/ +/*! + @brief Retrieve the pin number used for DotStar data output. + @return Arduino pin number (-2 if not set). +*/ +/****************************************************************************/ +int16_t getStatusDotStarDataPin() { +#ifdef USE_STATUS_DOTSTAR + return STATUS_DOTSTAR_PIN_DATA; +#endif + return -2; +} + +/****************************************************************************/ +/*! + @brief Fades the status LED. + @param color + The specific color to fade the status LED. + @param numFades + The amount of time to fade/pulse the status LED. +*/ +/****************************************************************************/ +void statusLEDFade(uint32_t color, int numFades = 3) { + // don't fade if our pixel is off + if (WS.status_pixel_brightness == 0.0) + return; + + // pulse `numFades` times + for (int i = 0; i < numFades; i++) { + // fade up + for (int i = 0; i <= 255; i += 5) { + setStatusLEDColor(color, i); + delay(10); + } + // fade down + for (int i = 0; i >= 255; i -= 5) { + setStatusLEDColor(color, i); + delay(10); + } + } + +// Turn status LED off +#if not defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + setStatusLEDColor(BLACK); +#else + // The Adafruit Feather ESP8266's built-in LED is reverse wired + setStatusLEDColor(BLACK ^ 1); +#endif +} + +/****************************************************************************/ +/*! + @brief Converts the a ws_led_status_t status state to color. + @param statusState + Hardware's status state. + @return Color as a uint32_t +*/ +/****************************************************************************/ +uint32_t ledStatusStateToColor(ws_led_status_t statusState) { + uint32_t ledColor; + switch (statusState) { + case WS_LED_STATUS_KAT: + ledColor = GREEN; + break; + case WS_LED_STATUS_ERROR_RUNTIME: + ledColor = RED; + break; + case WS_LED_STATUS_WIFI_CONNECTING: + ledColor = AMBER; + break; + case WS_LED_STATUS_MQTT_CONNECTING: + ledColor = BLUE; + break; + case WS_LED_STATUS_WAITING_FOR_REG_MSG: + ledColor = PINK; + break; + case WS_LED_STATUS_FS_WRITE: + ledColor = YELLOW; + break; + default: + ledColor = BLACK; + break; + } + return ledColor; +} + +/****************************************************************************/ +/*! + @brief Sets the status LED to a specific color depending on + the hardware's state. + @param statusState + Hardware's status state. +*/ +/****************************************************************************/ +void statusLEDSolid(ws_led_status_t statusState = WS_LED_STATUS_ERROR_RUNTIME) { +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; +#endif + +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere +#endif + + uint32_t ledColor = ledStatusStateToColor(statusState); + setStatusLEDColor(ledColor); +} + +/****************************************************************************/ +/*! + @brief Blinks a status LED a specific color depending on + the hardware's state. + @param statusState + Hardware's status state. +*/ +/****************************************************************************/ +void statusLEDBlink(ws_led_status_t statusState) { +#ifdef USE_STATUS_LED + if (!WS.lockStatusLED) + return; +#endif + +#ifdef USE_STATUS_NEOPIXEL + if (!WS.lockStatusNeoPixel) + return; // status pixel is in-use elsewhere +#endif + + // set number of times to blink + int blinkNum = 3; + // set blink color + uint32_t ledColor = ledStatusStateToColor(statusState); + + while (blinkNum > 0) { + setStatusLEDColor(ledColor); + delay(100); +#if defined(ARDUINO_ESP8266_ADAFRUIT_HUZZAH) + // The Adafruit Feather ESP8266's built-in LED is reverse wired + setStatusLEDColor(BLACK ^ 1); +#else + setStatusLEDColor(BLACK); +#endif + delay(100); + blinkNum--; + } } \ No newline at end of file diff --git a/src/network_interfaces/ws_networking_pico.h b/src/network_interfaces/ws_networking_pico.h index 25ce278b1..0ea955112 100644 --- a/src/network_interfaces/ws_networking_pico.h +++ b/src/network_interfaces/ws_networking_pico.h @@ -137,12 +137,23 @@ class ws_networking_pico : public Wippersnapper { // User-set network not found, print scan results to serial console WS_DEBUG_PRINTLN("ERROR: Your requested WiFi network was not found!"); - WS_DEBUG_PRINTLN("WipperSnapper found these WiFi networks: "); - for (int i = 0; i < n; ++i) { + WS_DEBUG_PRINTLN("WipperSnapper found these WiFi networks:"); + for (uint8_t i = 0; i < n; ++i) { WS_DEBUG_PRINT(WiFi.SSID(i)); - WS_DEBUG_PRINT(" "); + WS_DEBUG_PRINT(" ("); + uint8_t BSSID[WL_MAC_ADDR_LENGTH]; + WiFi.BSSID(i, BSSID); + for (int m = 0; m < WL_MAC_ADDR_LENGTH; ++m) { + if (m != 0) { + WS_DEBUG_PRINT(":"); + } + WS_DEBUG_PRINTHEX(BSSID[m]); + } + WS_DEBUG_PRINT(") "); WS_DEBUG_PRINT(WiFi.RSSI(i)); - WS_DEBUG_PRINTLN("dB"); + WS_DEBUG_PRINT("dB (ch"); + WS_DEBUG_PRINT(WiFi.channel(i)) + WS_DEBUG_PRINTLN(")"); } return false;