mirror of
https://github.com/meshtastic/firmware.git
synced 2025-06-08 14:12:05 +00:00
Get rid of Arduino Strings
This commit is contained in:
parent
21404de7fc
commit
6749d9ffc5
@ -80,9 +80,6 @@ using graphics::numEmotes;
|
||||
|
||||
using namespace meshtastic; /** @todo remove */
|
||||
|
||||
String alertBannerMessage = "";
|
||||
uint32_t alertBannerUntil = 0;
|
||||
|
||||
namespace graphics
|
||||
{
|
||||
|
||||
@ -97,8 +94,12 @@ namespace graphics
|
||||
// A text message frame + debug frame + all the node infos
|
||||
FrameCallback *normalFrames;
|
||||
static uint32_t targetFramerate = IDLE_FRAMERATE;
|
||||
static String alertBannerMessage;
|
||||
static uint32_t alertBannerUntil = 0;
|
||||
// Global variables for alert banner - explicitly define with extern "C" linkage to prevent optimization
|
||||
extern "C" {
|
||||
static char alertBannerBuffer[256] = "";
|
||||
char *alertBannerMessage = alertBannerBuffer;
|
||||
uint32_t alertBannerUntil = 0;
|
||||
}
|
||||
|
||||
uint32_t logo_timeout = 5000; // 4 seconds for EACH logo
|
||||
|
||||
@ -146,10 +147,11 @@ extern bool hasUnreadMessage;
|
||||
// The banner appears in the center of the screen and disappears after the specified duration
|
||||
|
||||
// Called to trigger a banner with custom message and duration
|
||||
void Screen::showOverlayBanner(const String &message, uint32_t durationMs)
|
||||
void Screen::showOverlayBanner(const char *message, uint32_t durationMs)
|
||||
{
|
||||
// Store the message and set the expiration timestamp
|
||||
alertBannerMessage = message;
|
||||
strncpy(alertBannerMessage, message, 255);
|
||||
alertBannerMessage[255] = '\0'; // Ensure null termination
|
||||
alertBannerUntil = (durationMs == 0) ? 0 : millis() + durationMs;
|
||||
}
|
||||
|
||||
@ -225,7 +227,8 @@ void Screen::drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *sta
|
||||
drawBattery(display, x, y + 7, imgBattery, powerStatus);
|
||||
|
||||
if (powerStatus->getHasBattery()) {
|
||||
String batteryPercent = String(powerStatus->getBatteryChargePercent()) + "%";
|
||||
char batteryPercent[8];
|
||||
snprintf(batteryPercent, sizeof(batteryPercent), "%d%%", powerStatus->getBatteryChargePercent());
|
||||
|
||||
display->setFont(FONT_SMALL);
|
||||
|
||||
@ -255,16 +258,13 @@ void Screen::drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *sta
|
||||
hour = 12;
|
||||
}
|
||||
|
||||
// hours string
|
||||
String hourString = String(hour);
|
||||
// Format time string
|
||||
char timeString[16];
|
||||
snprintf(timeString, sizeof(timeString), "%d:%02d", hour, minute);
|
||||
|
||||
// minutes string
|
||||
String minuteString = minute < 10 ? "0" + String(minute) : String(minute);
|
||||
|
||||
String timeString = hourString + ":" + minuteString;
|
||||
|
||||
// seconds string
|
||||
String secondString = second < 10 ? "0" + String(second) : String(second);
|
||||
// Format seconds string
|
||||
char secondString[8];
|
||||
snprintf(secondString, sizeof(secondString), "%02d", second);
|
||||
|
||||
float scale = 1.5;
|
||||
|
||||
@ -272,12 +272,12 @@ void Screen::drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *sta
|
||||
uint16_t segmentHeight = SEGMENT_HEIGHT * scale;
|
||||
|
||||
// calculate hours:minutes string width
|
||||
uint16_t timeStringWidth = timeString.length() * 5;
|
||||
uint16_t timeStringWidth = strlen(timeString) * 5;
|
||||
|
||||
for (uint8_t i = 0; i < timeString.length(); i++) {
|
||||
String character = String(timeString[i]);
|
||||
for (uint8_t i = 0; i < strlen(timeString); i++) {
|
||||
char character = timeString[i];
|
||||
|
||||
if (character == ":") {
|
||||
if (character == ':') {
|
||||
timeStringWidth += segmentHeight;
|
||||
} else {
|
||||
timeStringWidth += segmentWidth + (segmentHeight * 2) + 4;
|
||||
@ -285,7 +285,7 @@ void Screen::drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *sta
|
||||
}
|
||||
|
||||
// calculate seconds string width
|
||||
uint16_t secondStringWidth = (secondString.length() * 12) + 4;
|
||||
uint16_t secondStringWidth = (strlen(secondString) * 12) + 4;
|
||||
|
||||
// sum these to get total string width
|
||||
uint16_t totalWidth = timeStringWidth + secondStringWidth;
|
||||
@ -297,15 +297,15 @@ void Screen::drawDigitalClockFrame(OLEDDisplay *display, OLEDDisplayUiState *sta
|
||||
uint16_t hourMinuteTextY = (display->getHeight() / 2) - (((segmentWidth * 2) + (segmentHeight * 3) + 8) / 2);
|
||||
|
||||
// iterate over characters in hours:minutes string and draw segmented characters
|
||||
for (uint8_t i = 0; i < timeString.length(); i++) {
|
||||
String character = String(timeString[i]);
|
||||
for (uint8_t i = 0; i < strlen(timeString); i++) {
|
||||
char character = timeString[i];
|
||||
|
||||
if (character == ":") {
|
||||
if (character == ':') {
|
||||
drawSegmentedDisplayColon(display, hourMinuteTextX, hourMinuteTextY, scale);
|
||||
|
||||
hourMinuteTextX += segmentHeight + 6;
|
||||
} else {
|
||||
drawSegmentedDisplayCharacter(display, hourMinuteTextX, hourMinuteTextY, character.toInt(), scale);
|
||||
drawSegmentedDisplayCharacter(display, hourMinuteTextX, hourMinuteTextY, character - '0', scale);
|
||||
|
||||
hourMinuteTextX += segmentWidth + (segmentHeight * 2) + 4;
|
||||
}
|
||||
@ -457,7 +457,8 @@ void Screen::drawAnalogClockFrame(OLEDDisplay *display, OLEDDisplayUiState *stat
|
||||
drawBattery(display, x, y + 7, imgBattery, powerStatus);
|
||||
|
||||
if (powerStatus->getHasBattery()) {
|
||||
String batteryPercent = String(powerStatus->getBatteryChargePercent()) + "%";
|
||||
char batteryPercent[8];
|
||||
snprintf(batteryPercent, sizeof(batteryPercent), "%d%%", powerStatus->getBatteryChargePercent());
|
||||
|
||||
display->setFont(FONT_SMALL);
|
||||
|
||||
@ -1711,21 +1712,30 @@ int Screen::handleTextMessage(const meshtastic_MeshPacket *packet)
|
||||
const char *longName = (node && node->has_user) ? node->user.long_name : nullptr;
|
||||
|
||||
const char *msgRaw = reinterpret_cast<const char *>(packet->decoded.payload.bytes);
|
||||
String msg = String(msgRaw);
|
||||
msg.trim(); // Remove leading/trailing whitespace/newlines
|
||||
|
||||
String banner;
|
||||
char banner[256];
|
||||
|
||||
// Match bell character or exact alert text
|
||||
if (msg.indexOf("\x07") != -1) {
|
||||
banner = "Alert Received";
|
||||
} else {
|
||||
banner = "New Message";
|
||||
// Check for bell character in message to determine alert type
|
||||
bool isAlert = false;
|
||||
for (size_t i = 0; i < packet->decoded.payload.size && i < 100; i++) {
|
||||
if (msgRaw[i] == '\x07') {
|
||||
isAlert = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (isAlert) {
|
||||
if (longName && longName[0]) {
|
||||
banner += "\nfrom ";
|
||||
banner += longName;
|
||||
snprintf(banner, sizeof(banner), "Alert Received\nfrom %s", longName);
|
||||
} else {
|
||||
strcpy(banner, "Alert Received");
|
||||
}
|
||||
} else {
|
||||
if (longName && longName[0]) {
|
||||
snprintf(banner, sizeof(banner), "New Message\nfrom %s", longName);
|
||||
} else {
|
||||
strcpy(banner, "New Message");
|
||||
}
|
||||
}
|
||||
|
||||
screen->showOverlayBanner(banner, 3000);
|
||||
|
@ -269,7 +269,7 @@ class Screen : public concurrency::OSThread
|
||||
enqueueCmd(cmd);
|
||||
}
|
||||
|
||||
void showOverlayBanner(const String &message, uint32_t durationMs = 3000);
|
||||
void showOverlayBanner(const char *message, uint32_t durationMs = 3000);
|
||||
|
||||
void startFirmwareUpdateScreen()
|
||||
{
|
||||
@ -688,8 +688,10 @@ class Screen : public concurrency::OSThread
|
||||
|
||||
} // namespace graphics
|
||||
|
||||
extern String alertBannerMessage;
|
||||
extern "C" {
|
||||
extern char *alertBannerMessage;
|
||||
extern uint32_t alertBannerUntil;
|
||||
}
|
||||
|
||||
// Extern declarations for function symbols used in UIRenderer
|
||||
extern std::vector<std::string> functionSymbol;
|
||||
|
@ -181,19 +181,19 @@ void drawFrameWiFi(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, i
|
||||
}
|
||||
|
||||
if (WiFi.status() != WL_CONNECTED) {
|
||||
display->drawString(x, y, String("WiFi: Not Connected"));
|
||||
display->drawString(x, y, "WiFi: Not Connected");
|
||||
if (config.display.heading_bold)
|
||||
display->drawString(x + 1, y, String("WiFi: Not Connected"));
|
||||
display->drawString(x + 1, y, "WiFi: Not Connected");
|
||||
} else {
|
||||
display->drawString(x, y, String("WiFi: Connected"));
|
||||
display->drawString(x, y, "WiFi: Connected");
|
||||
if (config.display.heading_bold)
|
||||
display->drawString(x + 1, y, String("WiFi: Connected"));
|
||||
display->drawString(x + 1, y, "WiFi: Connected");
|
||||
|
||||
display->drawString(x + SCREEN_WIDTH - display->getStringWidth("RSSI " + String(WiFi.RSSI())), y,
|
||||
"RSSI " + String(WiFi.RSSI()));
|
||||
char rssiStr[32];
|
||||
snprintf(rssiStr, sizeof(rssiStr), "RSSI %d", WiFi.RSSI());
|
||||
display->drawString(x + SCREEN_WIDTH - display->getStringWidth(rssiStr), y, rssiStr);
|
||||
if (config.display.heading_bold) {
|
||||
display->drawString(x + SCREEN_WIDTH - display->getStringWidth("RSSI " + String(WiFi.RSSI())) - 1, y,
|
||||
"RSSI " + String(WiFi.RSSI()));
|
||||
display->drawString(x + SCREEN_WIDTH - display->getStringWidth(rssiStr) - 1, y, rssiStr);
|
||||
}
|
||||
}
|
||||
|
||||
@ -212,7 +212,9 @@ void drawFrameWiFi(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, i
|
||||
|
||||
*/
|
||||
if (WiFi.status() == WL_CONNECTED) {
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 1, "IP: " + String(WiFi.localIP().toString().c_str()));
|
||||
char ipStr[64];
|
||||
snprintf(ipStr, sizeof(ipStr), "IP: %s", WiFi.localIP().toString().c_str());
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 1, ipStr);
|
||||
} else if (WiFi.status() == WL_NO_SSID_AVAIL) {
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 1, "SSID Not Found");
|
||||
} else if (WiFi.status() == WL_CONNECTION_LOST) {
|
||||
@ -231,11 +233,15 @@ void drawFrameWiFi(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, i
|
||||
}
|
||||
#else
|
||||
else {
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 1, "Unkown status: " + String(WiFi.status()));
|
||||
char statusStr[32];
|
||||
snprintf(statusStr, sizeof(statusStr), "Unknown status: %d", WiFi.status());
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 1, statusStr);
|
||||
}
|
||||
#endif
|
||||
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 2, "SSID: " + String(wifiName));
|
||||
char ssidStr[64];
|
||||
snprintf(ssidStr, sizeof(ssidStr), "SSID: %s", wifiName);
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 2, ssidStr);
|
||||
|
||||
display->drawString(x, y + FONT_HEIGHT_SMALL * 3, "http://meshtastic.local");
|
||||
|
||||
@ -274,9 +280,9 @@ void drawFrameSettings(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t
|
||||
display->drawString(x + 1, y, batStr);
|
||||
} else {
|
||||
// Line 1
|
||||
display->drawString(x, y, String("USB"));
|
||||
display->drawString(x, y, "USB");
|
||||
if (config.display.heading_bold)
|
||||
display->drawString(x + 1, y, String("USB"));
|
||||
display->drawString(x + 1, y, "USB");
|
||||
}
|
||||
|
||||
// auto mode = DisplayFormatters::getModemPresetDisplayName(config.lora.modem_preset, true);
|
||||
@ -416,7 +422,7 @@ void drawLoRaFocused(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x,
|
||||
display->setTextAlignment(TEXT_ALIGN_LEFT);
|
||||
|
||||
// === First Row: Region / BLE Name ===
|
||||
graphics::UIRenderer::drawNodes(display, x, compactFirstLine + 3, nodeStatus, 0, true);
|
||||
graphics::UIRenderer::drawNodes(display, x, compactFirstLine + 3, nodeStatus, 0, true, "");
|
||||
|
||||
uint8_t dmac[6];
|
||||
char shortnameble[35];
|
||||
|
@ -47,9 +47,9 @@ static int scrollIndex = 0;
|
||||
// Utility Functions
|
||||
// =============================
|
||||
|
||||
String getSafeNodeName(meshtastic_NodeInfoLite *node)
|
||||
const char *getSafeNodeName(meshtastic_NodeInfoLite *node)
|
||||
{
|
||||
String nodeName = "?";
|
||||
static char nodeName[16] = "?";
|
||||
if (node->has_user && strlen(node->user.short_name) > 0) {
|
||||
bool valid = true;
|
||||
const char *name = node->user.short_name;
|
||||
@ -61,12 +61,13 @@ String getSafeNodeName(meshtastic_NodeInfoLite *node)
|
||||
}
|
||||
}
|
||||
if (valid) {
|
||||
nodeName = name;
|
||||
strncpy(nodeName, name, sizeof(nodeName) - 1);
|
||||
nodeName[sizeof(nodeName) - 1] = '\0';
|
||||
} else {
|
||||
char idStr[6];
|
||||
snprintf(idStr, sizeof(idStr), "%04X", (uint16_t)(node->num & 0xFFFF));
|
||||
nodeName = String(idStr);
|
||||
snprintf(nodeName, sizeof(nodeName), "%04X", (uint16_t)(node->num & 0xFFFF));
|
||||
}
|
||||
} else {
|
||||
strcpy(nodeName, "?");
|
||||
}
|
||||
return nodeName;
|
||||
}
|
||||
@ -179,7 +180,7 @@ void drawEntryLastHeard(OLEDDisplay *display, meshtastic_NodeInfoLite *node, int
|
||||
bool isLeftCol = (x < SCREEN_WIDTH / 2);
|
||||
int timeOffset = (SCREEN_WIDTH > 128) ? (isLeftCol ? 7 : 10) : (isLeftCol ? 3 : 7);
|
||||
|
||||
String nodeName = getSafeNodeName(node);
|
||||
const char *nodeName = getSafeNodeName(node);
|
||||
|
||||
char timeStr[10];
|
||||
uint32_t seconds = sinceLastSeen(node);
|
||||
@ -222,7 +223,7 @@ void drawEntryHopSignal(OLEDDisplay *display, meshtastic_NodeInfoLite *node, int
|
||||
|
||||
int barsXOffset = columnWidth - barsOffset;
|
||||
|
||||
String nodeName = getSafeNodeName(node);
|
||||
const char *nodeName = getSafeNodeName(node);
|
||||
|
||||
display->setTextAlignment(TEXT_ALIGN_LEFT);
|
||||
display->setFont(FONT_SMALL);
|
||||
@ -266,7 +267,7 @@ void drawNodeDistance(OLEDDisplay *display, meshtastic_NodeInfoLite *node, int16
|
||||
bool isLeftCol = (x < SCREEN_WIDTH / 2);
|
||||
int nameMaxWidth = columnWidth - (SCREEN_WIDTH > 128 ? (isLeftCol ? 25 : 28) : (isLeftCol ? 20 : 22));
|
||||
|
||||
String nodeName = getSafeNodeName(node);
|
||||
const char *nodeName = getSafeNodeName(node);
|
||||
char distStr[10] = "";
|
||||
|
||||
meshtastic_NodeInfoLite *ourNode = nodeDB->getMeshNode(nodeDB->getNodeNum());
|
||||
@ -361,7 +362,7 @@ void drawEntryCompass(OLEDDisplay *display, meshtastic_NodeInfoLite *node, int16
|
||||
// Adjust max text width depending on column and screen width
|
||||
int nameMaxWidth = columnWidth - (SCREEN_WIDTH > 128 ? (isLeftCol ? 25 : 28) : (isLeftCol ? 20 : 22));
|
||||
|
||||
String nodeName = getSafeNodeName(node);
|
||||
const char *nodeName = getSafeNodeName(node);
|
||||
|
||||
display->setTextAlignment(TEXT_ALIGN_LEFT);
|
||||
display->setFont(FONT_SMALL);
|
||||
|
@ -59,7 +59,7 @@ void drawNodeInfo(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, in
|
||||
// Utility functions
|
||||
const char *getCurrentModeTitle(int screenWidth);
|
||||
void retrieveAndSortNodes(std::vector<NodeEntry> &nodeList);
|
||||
String getSafeNodeName(meshtastic_NodeInfoLite *node);
|
||||
const char *getSafeNodeName(meshtastic_NodeInfoLite *node);
|
||||
uint32_t sinceLastSeen(meshtastic_NodeInfoLite *node);
|
||||
void drawColumns(OLEDDisplay *display, int16_t x, int16_t y, const char **fields);
|
||||
|
||||
|
@ -2,6 +2,7 @@
|
||||
#include "DisplayFormatters.h"
|
||||
#include "NodeDB.h"
|
||||
#include "configuration.h"
|
||||
#include "graphics/Screen.h"
|
||||
#include "graphics/ScreenFonts.h"
|
||||
#include "graphics/SharedUIDisplay.h"
|
||||
#include "graphics/images.h"
|
||||
@ -17,8 +18,6 @@
|
||||
using namespace meshtastic;
|
||||
|
||||
// External references to global variables from Screen.cpp
|
||||
extern String alertBannerMessage;
|
||||
extern uint32_t alertBannerUntil;
|
||||
extern std::vector<std::string> functionSymbol;
|
||||
extern std::string functionSymbolString;
|
||||
extern bool hasUnreadMessage;
|
||||
@ -77,7 +76,7 @@ void NotificationRenderer::drawWelcomeScreen(OLEDDisplay *display, OLEDDisplayUi
|
||||
void NotificationRenderer::drawAlertBannerOverlay(OLEDDisplay *display, OLEDDisplayUiState *state)
|
||||
{
|
||||
// Exit if no message is active or duration has passed
|
||||
if (alertBannerMessage.length() == 0 || (alertBannerUntil != 0 && millis() > alertBannerUntil))
|
||||
if (strlen(alertBannerMessage) == 0 || (alertBannerUntil != 0 && millis() > alertBannerUntil))
|
||||
return;
|
||||
|
||||
// === Layout Configuration ===
|
||||
@ -85,28 +84,37 @@ void NotificationRenderer::drawAlertBannerOverlay(OLEDDisplay *display, OLEDDisp
|
||||
constexpr uint8_t lineSpacing = 1; // Extra space between lines
|
||||
|
||||
// Search the message to determine if we need the bell added
|
||||
bool needs_bell = (alertBannerMessage.indexOf("Alert Received") != -1);
|
||||
bool needs_bell = (strstr(alertBannerMessage, "Alert Received") != nullptr);
|
||||
|
||||
// Setup font and alignment
|
||||
display->setFont(FONT_SMALL);
|
||||
display->setTextAlignment(TEXT_ALIGN_LEFT); // We will manually center per line
|
||||
|
||||
// === Split the message into lines (supports multi-line banners) ===
|
||||
std::vector<String> lines;
|
||||
int start = 0, newlineIdx;
|
||||
while ((newlineIdx = alertBannerMessage.indexOf('\n', start)) != -1) {
|
||||
lines.push_back(alertBannerMessage.substring(start, newlineIdx));
|
||||
start = newlineIdx + 1;
|
||||
const int MAX_LINES = 10;
|
||||
char lines[MAX_LINES][256];
|
||||
int lineCount = 0;
|
||||
|
||||
// Create a working copy of the message to tokenize
|
||||
char messageCopy[256];
|
||||
strncpy(messageCopy, alertBannerMessage, sizeof(messageCopy) - 1);
|
||||
messageCopy[sizeof(messageCopy) - 1] = '\0';
|
||||
|
||||
char *line = strtok(messageCopy, "\n");
|
||||
while (line != nullptr && lineCount < MAX_LINES) {
|
||||
strncpy(lines[lineCount], line, sizeof(lines[lineCount]) - 1);
|
||||
lines[lineCount][sizeof(lines[lineCount]) - 1] = '\0';
|
||||
lineCount++;
|
||||
line = strtok(nullptr, "\n");
|
||||
}
|
||||
lines.push_back(alertBannerMessage.substring(start));
|
||||
|
||||
// === Measure text dimensions ===
|
||||
uint16_t minWidth = (SCREEN_WIDTH > 128) ? 106 : 78;
|
||||
uint16_t maxWidth = 0;
|
||||
std::vector<uint16_t> lineWidths;
|
||||
for (const auto &line : lines) {
|
||||
uint16_t w = display->getStringWidth(line.c_str(), line.length(), true);
|
||||
lineWidths.push_back(w);
|
||||
uint16_t lineWidths[MAX_LINES];
|
||||
for (int i = 0; i < lineCount; i++) {
|
||||
uint16_t w = display->getStringWidth(lines[i], strlen(lines[i]), true);
|
||||
lineWidths[i] = w;
|
||||
if (w > maxWidth)
|
||||
maxWidth = w;
|
||||
}
|
||||
@ -115,7 +123,7 @@ void NotificationRenderer::drawAlertBannerOverlay(OLEDDisplay *display, OLEDDisp
|
||||
if (needs_bell && boxWidth < minWidth)
|
||||
boxWidth += (SCREEN_WIDTH > 128) ? 26 : 20;
|
||||
|
||||
uint16_t boxHeight = padding * 2 + lines.size() * FONT_HEIGHT_SMALL + (lines.size() - 1) * lineSpacing;
|
||||
uint16_t boxHeight = padding * 2 + lineCount * FONT_HEIGHT_SMALL + (lineCount - 1) * lineSpacing;
|
||||
|
||||
int16_t boxLeft = (display->width() / 2) - (boxWidth / 2);
|
||||
int16_t boxTop = (display->height() / 2) - (boxHeight / 2);
|
||||
@ -128,9 +136,9 @@ void NotificationRenderer::drawAlertBannerOverlay(OLEDDisplay *display, OLEDDisp
|
||||
|
||||
// === Draw each line centered in the box ===
|
||||
int16_t lineY = boxTop + padding;
|
||||
for (size_t i = 0; i < lines.size(); ++i) {
|
||||
for (int i = 0; i < lineCount; i++) {
|
||||
int16_t textX = boxLeft + (boxWidth - lineWidths[i]) / 2;
|
||||
uint16_t line_width = display->getStringWidth(lines[i].c_str(), lines[i].length(), true);
|
||||
uint16_t line_width = display->getStringWidth(lines[i], strlen(lines[i]), true);
|
||||
|
||||
if (needs_bell && i == 0) {
|
||||
int bellY = lineY + (FONT_HEIGHT_SMALL - 8) / 2;
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "target_specific.h"
|
||||
#include <OLEDDisplay.h>
|
||||
#include <RTC.h>
|
||||
#include <cstring>
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_GPS
|
||||
|
||||
@ -102,7 +103,7 @@ void drawGps(OLEDDisplay *display, int16_t x, int16_t y, const meshtastic::GPSSt
|
||||
// Draw status when GPS is disabled or not present
|
||||
void drawGpsPowerStatus(OLEDDisplay *display, int16_t x, int16_t y, const meshtastic::GPSStatus *gps)
|
||||
{
|
||||
String displayLine;
|
||||
const char *displayLine;
|
||||
int pos;
|
||||
if (y < FONT_HEIGHT_SMALL) { // Line 1: use short string
|
||||
displayLine = config.position.gps_mode == meshtastic_Config_PositionConfig_GpsMode_NOT_PRESENT ? "No GPS" : "GPS off";
|
||||
@ -117,7 +118,7 @@ void drawGpsPowerStatus(OLEDDisplay *display, int16_t x, int16_t y, const meshta
|
||||
|
||||
void drawGpsAltitude(OLEDDisplay *display, int16_t x, int16_t y, const meshtastic::GPSStatus *gps)
|
||||
{
|
||||
String displayLine = "";
|
||||
char displayLine[32];
|
||||
if (!gps->getIsConnected() && !config.position.fixed_position) {
|
||||
// displayLine = "No GPS Module";
|
||||
// display->drawString(x + (SCREEN_WIDTH - (display->getStringWidth(displayLine))) / 2, y, displayLine);
|
||||
@ -126,9 +127,10 @@ void drawGpsAltitude(OLEDDisplay *display, int16_t x, int16_t y, const meshtasti
|
||||
// display->drawString(x + (SCREEN_WIDTH - (display->getStringWidth(displayLine))) / 2, y, displayLine);
|
||||
} else {
|
||||
geoCoord.updateCoords(int32_t(gps->getLatitude()), int32_t(gps->getLongitude()), int32_t(gps->getAltitude()));
|
||||
displayLine = "Altitude: " + String(geoCoord.getAltitude()) + "m";
|
||||
if (config.display.units == meshtastic_Config_DisplayConfig_DisplayUnits_IMPERIAL)
|
||||
displayLine = "Altitude: " + String(geoCoord.getAltitude() * METERS_TO_FEET) + "ft";
|
||||
snprintf(displayLine, sizeof(displayLine), "Altitude: %.0fft", geoCoord.getAltitude() * METERS_TO_FEET);
|
||||
else
|
||||
snprintf(displayLine, sizeof(displayLine), "Altitude: %.0fm", geoCoord.getAltitude());
|
||||
display->drawString(x + (display->getWidth() - (display->getStringWidth(displayLine))) / 2, y, displayLine);
|
||||
}
|
||||
}
|
||||
@ -137,13 +139,13 @@ void drawGpsAltitude(OLEDDisplay *display, int16_t x, int16_t y, const meshtasti
|
||||
void drawGpsCoordinates(OLEDDisplay *display, int16_t x, int16_t y, const meshtastic::GPSStatus *gps)
|
||||
{
|
||||
auto gpsFormat = config.display.gps_format;
|
||||
String displayLine = "";
|
||||
char displayLine[32];
|
||||
|
||||
if (!gps->getIsConnected() && !config.position.fixed_position) {
|
||||
displayLine = "No GPS present";
|
||||
strcpy(displayLine, "No GPS present");
|
||||
display->drawString(x + (display->getWidth() - (display->getStringWidth(displayLine))) / 2, y, displayLine);
|
||||
} else if (!gps->getHasLock() && !config.position.fixed_position) {
|
||||
displayLine = "No GPS Lock";
|
||||
strcpy(displayLine, "No GPS Lock");
|
||||
display->drawString(x + (display->getWidth() - (display->getStringWidth(displayLine))) / 2, y, displayLine);
|
||||
} else {
|
||||
|
||||
@ -219,10 +221,10 @@ void drawNodes(OLEDDisplay *display, int16_t x, int16_t y, const meshtastic::Nod
|
||||
#endif
|
||||
display->drawString(x + 10, y - 2, usersString);
|
||||
int string_offset = (SCREEN_WIDTH > 128) ? 2 : 1;
|
||||
if (additional_words != "") {
|
||||
display->drawString(x + 10 + display->getStringWidth(usersString) + string_offset, y - 2, additional_words);
|
||||
if (additional_words.length() > 0) {
|
||||
display->drawString(x + 10 + display->getStringWidth(usersString) + string_offset, y - 2, additional_words.c_str());
|
||||
if (config.display.heading_bold)
|
||||
display->drawString(x + 11 + display->getStringWidth(usersString) + string_offset, y - 2, additional_words);
|
||||
display->drawString(x + 11 + display->getStringWidth(usersString) + string_offset, y - 2, additional_words.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
@ -575,7 +577,7 @@ void drawDeviceFocused(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t
|
||||
|
||||
#if HAS_GPS
|
||||
if (config.position.gps_mode != meshtastic_Config_PositionConfig_GpsMode_ENABLED) {
|
||||
String displayLine = "";
|
||||
const char *displayLine;
|
||||
if (config.position.fixed_position) {
|
||||
displayLine = "Fixed GPS";
|
||||
} else {
|
||||
@ -603,8 +605,7 @@ void drawDeviceFocused(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t
|
||||
} else {
|
||||
display->drawString(
|
||||
x + SCREEN_WIDTH - display->getStringWidth("USB"),
|
||||
((rows == 4) ? compactSecondLine : ((SCREEN_HEIGHT > 64) ? compactSecondLine : moreCompactSecondLine)),
|
||||
String("USB"));
|
||||
((rows == 4) ? compactSecondLine : ((SCREEN_HEIGHT > 64) ? compactSecondLine : moreCompactSecondLine)), "USB");
|
||||
}
|
||||
|
||||
config.display.heading_bold = origBold;
|
||||
@ -934,9 +935,9 @@ void drawCompassAndLocationScreen(OLEDDisplay *display, OLEDDisplayUiState *stat
|
||||
bool origBold = config.display.heading_bold;
|
||||
config.display.heading_bold = false;
|
||||
|
||||
String Satelite_String = "Sat:";
|
||||
const char *Satelite_String = "Sat:";
|
||||
display->drawString(0, ((SCREEN_HEIGHT > 64) ? compactFirstLine : moreCompactFirstLine), Satelite_String);
|
||||
String displayLine = "";
|
||||
const char *displayLine = ""; // Initialize to empty string by default
|
||||
if (config.position.gps_mode != meshtastic_Config_PositionConfig_GpsMode_ENABLED) {
|
||||
if (config.position.fixed_position) {
|
||||
displayLine = "Fixed GPS";
|
||||
@ -946,6 +947,7 @@ void drawCompassAndLocationScreen(OLEDDisplay *display, OLEDDisplayUiState *stat
|
||||
display->drawString(display->getStringWidth(Satelite_String) + 3,
|
||||
((SCREEN_HEIGHT > 64) ? compactFirstLine : moreCompactFirstLine), displayLine);
|
||||
} else {
|
||||
displayLine = "GPS enabled"; // Set a value when GPS is enabled
|
||||
UIRenderer::drawGps(display, display->getStringWidth(Satelite_String) + 3,
|
||||
((SCREEN_HEIGHT > 64) ? compactFirstLine : moreCompactFirstLine) + 3, gpsStatus);
|
||||
}
|
||||
@ -969,13 +971,15 @@ void drawCompassAndLocationScreen(OLEDDisplay *display, OLEDDisplayUiState *stat
|
||||
}
|
||||
|
||||
// If GPS is off, no need to display these parts
|
||||
if (displayLine != "GPS off" && displayLine != "No GPS") {
|
||||
if (strcmp(displayLine, "GPS off") != 0 && strcmp(displayLine, "No GPS") != 0) {
|
||||
|
||||
// === Second Row: Altitude ===
|
||||
String displayLine;
|
||||
displayLine = " Alt: " + String(geoCoord.getAltitude()) + "m";
|
||||
if (config.display.units == meshtastic_Config_DisplayConfig_DisplayUnits_IMPERIAL)
|
||||
displayLine = " Alt: " + String(geoCoord.getAltitude() * METERS_TO_FEET) + "ft";
|
||||
char displayLine[32];
|
||||
if (config.display.units == meshtastic_Config_DisplayConfig_DisplayUnits_IMPERIAL) {
|
||||
snprintf(displayLine, sizeof(displayLine), " Alt: %.0fft", geoCoord.getAltitude() * METERS_TO_FEET);
|
||||
} else {
|
||||
snprintf(displayLine, sizeof(displayLine), " Alt: %.0fm", geoCoord.getAltitude());
|
||||
}
|
||||
display->drawString(x, ((SCREEN_HEIGHT > 64) ? compactSecondLine : moreCompactSecondLine), displayLine);
|
||||
|
||||
// === Third Row: Latitude ===
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include "PowerFSM.h" // needed for button bypass
|
||||
#include "SPILock.h"
|
||||
#include "detect/ScanI2C.h"
|
||||
#include "graphics/Screen.h"
|
||||
#include "graphics/SharedUIDisplay.h"
|
||||
#include "graphics/images.h"
|
||||
#include "input/ScanAndSelect.h"
|
||||
@ -732,9 +733,7 @@ bool CannedMessageModule::handleSystemCommandInput(const InputEvent *event)
|
||||
return false;
|
||||
|
||||
// Block ALL input if an alert banner is active
|
||||
extern String alertBannerMessage;
|
||||
extern uint32_t alertBannerUntil;
|
||||
if (alertBannerMessage.length() > 0 && (alertBannerUntil == 0 || millis() <= alertBannerUntil)) {
|
||||
if (strlen(alertBannerMessage) > 0 && (alertBannerUntil == 0 || millis() <= alertBannerUntil)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -1462,12 +1461,12 @@ void CannedMessageModule::drawFrame(OLEDDisplay *display, OLEDDisplayUiState *st
|
||||
|
||||
int xOffset = 0;
|
||||
int yOffset = row * (FONT_HEIGHT_SMALL - 4) + rowYOffset;
|
||||
String entryText;
|
||||
char entryText[64];
|
||||
|
||||
// Draw Channels First
|
||||
if (itemIndex < numActiveChannels) {
|
||||
uint8_t channelIndex = this->activeChannelIndices[itemIndex];
|
||||
entryText = String("@") + String(channels.getName(channelIndex));
|
||||
snprintf(entryText, sizeof(entryText), "@%s", channels.getName(channelIndex));
|
||||
}
|
||||
// Then Draw Nodes
|
||||
else {
|
||||
@ -1475,13 +1474,17 @@ void CannedMessageModule::drawFrame(OLEDDisplay *display, OLEDDisplayUiState *st
|
||||
if (nodeIndex >= 0 && nodeIndex < static_cast<int>(this->filteredNodes.size())) {
|
||||
meshtastic_NodeInfoLite *node = this->filteredNodes[nodeIndex].node;
|
||||
if (node) {
|
||||
entryText = node->is_favorite ? "* " + String(node->user.long_name) : String(node->user.long_name);
|
||||
if (node->is_favorite) {
|
||||
snprintf(entryText, sizeof(entryText), "* %s", node->user.long_name);
|
||||
} else {
|
||||
snprintf(entryText, sizeof(entryText), "%s", node->user.long_name);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (entryText.length() == 0 || entryText == "Unknown")
|
||||
entryText = "?";
|
||||
if (strlen(entryText) == 0 || strcmp(entryText, "Unknown") == 0)
|
||||
strcpy(entryText, "?");
|
||||
|
||||
// === Highlight background (if selected) ===
|
||||
if (itemIndex == destIndex) {
|
||||
|
@ -341,7 +341,7 @@ ProcessMessage SerialModuleRadio::handleReceived(const meshtastic_MeshPacket &mp
|
||||
serialPrint->write(p.payload.bytes, p.payload.size);
|
||||
} else if (moduleConfig.serial.mode == meshtastic_ModuleConfig_SerialConfig_Serial_Mode_TEXTMSG) {
|
||||
meshtastic_NodeInfoLite *node = nodeDB->getMeshNode(getFrom(&mp));
|
||||
String sender = (node && node->has_user) ? node->user.short_name : "???";
|
||||
const char *sender = (node && node->has_user) ? node->user.short_name : "???";
|
||||
serialPrint->println();
|
||||
serialPrint->printf("%s: %s", sender, p.payload.bytes);
|
||||
serialPrint->println();
|
||||
@ -410,8 +410,8 @@ uint32_t SerialModule::getBaudRate()
|
||||
|
||||
// Add this structure to help with parsing WindGust = 24.4 serial lines.
|
||||
struct ParsedLine {
|
||||
String name;
|
||||
String value;
|
||||
char name[64];
|
||||
char value[128];
|
||||
};
|
||||
|
||||
/**
|
||||
@ -438,16 +438,30 @@ ParsedLine parseLine(const char *line)
|
||||
strncpy(nameBuf, line, nameLen);
|
||||
nameBuf[nameLen] = '\0';
|
||||
|
||||
// Create trimmed name string
|
||||
String name = String(nameBuf);
|
||||
name.trim();
|
||||
// Trim whitespace from name
|
||||
char *nameStart = nameBuf;
|
||||
while (*nameStart && isspace(*nameStart))
|
||||
nameStart++;
|
||||
char *nameEnd = nameStart + strlen(nameStart) - 1;
|
||||
while (nameEnd > nameStart && isspace(*nameEnd))
|
||||
*nameEnd-- = '\0';
|
||||
|
||||
// Extract value after equals sign
|
||||
String value = String(equals + 1);
|
||||
value.trim();
|
||||
// Copy trimmed name
|
||||
strncpy(result.name, nameStart, sizeof(result.name) - 1);
|
||||
result.name[sizeof(result.name) - 1] = '\0';
|
||||
|
||||
// Extract value part (after equals)
|
||||
const char *valueStart = equals + 1;
|
||||
while (*valueStart && isspace(*valueStart))
|
||||
valueStart++;
|
||||
strncpy(result.value, valueStart, sizeof(result.value) - 1);
|
||||
result.value[sizeof(result.value) - 1] = '\0';
|
||||
|
||||
// Trim trailing whitespace from value
|
||||
char *valueEnd = result.value + strlen(result.value) - 1;
|
||||
while (valueEnd > result.value && isspace(*valueEnd))
|
||||
*valueEnd-- = '\0';
|
||||
|
||||
result.name = name;
|
||||
result.value = value;
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -517,16 +531,16 @@ void SerialModule::processWXSerial()
|
||||
memcpy(line, &serialBytes[lineStart], lineEnd - lineStart);
|
||||
|
||||
ParsedLine parsed = parseLine(line);
|
||||
if (parsed.name.length() > 0) {
|
||||
if (parsed.name == "WindDir") {
|
||||
strlcpy(windDir, parsed.value.c_str(), sizeof(windDir));
|
||||
if (strlen(parsed.name) > 0) {
|
||||
if (strcmp(parsed.name, "WindDir") == 0) {
|
||||
strlcpy(windDir, parsed.value, sizeof(windDir));
|
||||
double radians = GeoCoord::toRadians(strtof(windDir, nullptr));
|
||||
dir_sum_sin += sin(radians);
|
||||
dir_sum_cos += cos(radians);
|
||||
dirCount++;
|
||||
gotwind = true;
|
||||
} else if (parsed.name == "WindSpeed") {
|
||||
strlcpy(windVel, parsed.value.c_str(), sizeof(windVel));
|
||||
} else if (strcmp(parsed.name, "WindSpeed") == 0) {
|
||||
strlcpy(windVel, parsed.value, sizeof(windVel));
|
||||
float newv = strtof(windVel, nullptr);
|
||||
velSum += newv;
|
||||
velCount++;
|
||||
@ -534,28 +548,28 @@ void SerialModule::processWXSerial()
|
||||
lull = newv;
|
||||
}
|
||||
gotwind = true;
|
||||
} else if (parsed.name == "WindGust") {
|
||||
strlcpy(windGust, parsed.value.c_str(), sizeof(windGust));
|
||||
} else if (strcmp(parsed.name, "WindGust") == 0) {
|
||||
strlcpy(windGust, parsed.value, sizeof(windGust));
|
||||
float newg = strtof(windGust, nullptr);
|
||||
if (newg > gust) {
|
||||
gust = newg;
|
||||
}
|
||||
gotwind = true;
|
||||
} else if (parsed.name == "BatVoltage") {
|
||||
strlcpy(batVoltage, parsed.value.c_str(), sizeof(batVoltage));
|
||||
} else if (strcmp(parsed.name, "BatVoltage") == 0) {
|
||||
strlcpy(batVoltage, parsed.value, sizeof(batVoltage));
|
||||
batVoltageF = strtof(batVoltage, nullptr);
|
||||
break; // last possible data we want so break
|
||||
} else if (parsed.name == "CapVoltage") {
|
||||
strlcpy(capVoltage, parsed.value.c_str(), sizeof(capVoltage));
|
||||
} else if (strcmp(parsed.name, "CapVoltage") == 0) {
|
||||
strlcpy(capVoltage, parsed.value, sizeof(capVoltage));
|
||||
capVoltageF = strtof(capVoltage, nullptr);
|
||||
} else if (parsed.name == "GXTS04Temp" || parsed.name == "Temperature") {
|
||||
strlcpy(temperature, parsed.value.c_str(), sizeof(temperature));
|
||||
} else if (strcmp(parsed.name, "GXTS04Temp") == 0 || strcmp(parsed.name, "Temperature") == 0) {
|
||||
strlcpy(temperature, parsed.value, sizeof(temperature));
|
||||
temperatureF = strtof(temperature, nullptr);
|
||||
} else if (parsed.name == "RainIntSum") {
|
||||
strlcpy(rainStr, parsed.value.c_str(), sizeof(rainStr));
|
||||
} else if (strcmp(parsed.name, "RainIntSum") == 0) {
|
||||
strlcpy(rainStr, parsed.value, sizeof(rainStr));
|
||||
rainSum = int(strtof(rainStr, nullptr));
|
||||
} else if (parsed.name == "Rain") {
|
||||
strlcpy(rainStr, parsed.value.c_str(), sizeof(rainStr));
|
||||
} else if (strcmp(parsed.name, "Rain") == 0) {
|
||||
strlcpy(rainStr, parsed.value, sizeof(rainStr));
|
||||
rain = strtof(rainStr, nullptr);
|
||||
}
|
||||
}
|
||||
|
@ -118,22 +118,31 @@ void HealthTelemetryModule::drawFrame(OLEDDisplay *display, OLEDDisplayUiState *
|
||||
}
|
||||
|
||||
// Display "Health From: ..." on its own
|
||||
display->drawString(x, y, "Health From: " + String(lastSender) + "(" + String(agoSecs) + "s)");
|
||||
char headerStr[64];
|
||||
snprintf(headerStr, sizeof(headerStr), "Health From: %s(%ds)", lastSender, (int)agoSecs);
|
||||
display->drawString(x, y, headerStr);
|
||||
|
||||
String last_temp = String(lastMeasurement.variant.health_metrics.temperature, 0) + "°C";
|
||||
char last_temp[16];
|
||||
if (moduleConfig.telemetry.environment_display_fahrenheit) {
|
||||
last_temp = String(UnitConversions::CelsiusToFahrenheit(lastMeasurement.variant.health_metrics.temperature), 0) + "°F";
|
||||
snprintf(last_temp, sizeof(last_temp), "%.0f°F",
|
||||
UnitConversions::CelsiusToFahrenheit(lastMeasurement.variant.health_metrics.temperature));
|
||||
} else {
|
||||
snprintf(last_temp, sizeof(last_temp), "%.0f°C", lastMeasurement.variant.health_metrics.temperature);
|
||||
}
|
||||
|
||||
// Continue with the remaining details
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL), "Temp: " + last_temp);
|
||||
char tempStr[32];
|
||||
snprintf(tempStr, sizeof(tempStr), "Temp: %s", last_temp);
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL), tempStr);
|
||||
if (lastMeasurement.variant.health_metrics.has_heart_bpm) {
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL),
|
||||
"Heart Rate: " + String(lastMeasurement.variant.health_metrics.heart_bpm, 0) + " bpm");
|
||||
char heartStr[32];
|
||||
snprintf(heartStr, sizeof(heartStr), "Heart Rate: %.0f bpm", lastMeasurement.variant.health_metrics.heart_bpm);
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL), heartStr);
|
||||
}
|
||||
if (lastMeasurement.variant.health_metrics.has_spO2) {
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL),
|
||||
"spO2: " + String(lastMeasurement.variant.health_metrics.spO2, 0) + " %");
|
||||
char spo2Str[32];
|
||||
snprintf(spo2Str, sizeof(spo2Str), "spO2: %.0f %%", lastMeasurement.variant.health_metrics.spO2);
|
||||
display->drawString(x, y += _fontHeight(FONT_SMALL), spo2Str);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -152,14 +152,18 @@ void PowerTelemetryModule::drawFrame(OLEDDisplay *display, OLEDDisplayUiState *s
|
||||
}
|
||||
|
||||
// Display "Pow. From: ..."
|
||||
display->drawString(x, compactFirstLine, "Pow. From: " + String(lastSender) + " (" + String(agoSecs) + "s)");
|
||||
char fromStr[64];
|
||||
snprintf(fromStr, sizeof(fromStr), "Pow. From: %s (%ds)", lastSender, agoSecs);
|
||||
display->drawString(x, compactFirstLine, fromStr);
|
||||
|
||||
// Display current and voltage based on ...power_metrics.has_[channel/voltage/current]... flags
|
||||
const auto &m = lastMeasurement.variant.power_metrics;
|
||||
int lineY = compactSecondLine;
|
||||
|
||||
auto drawLine = [&](const char *label, float voltage, float current) {
|
||||
display->drawString(x, lineY, String(label) + ": " + String(voltage, 2) + "V " + String(current, 0) + "mA");
|
||||
char lineStr[64];
|
||||
snprintf(lineStr, sizeof(lineStr), "%s: %.2fV %.0fmA", label, voltage, current);
|
||||
display->drawString(x, lineY, lineStr);
|
||||
lineY += _fontHeight(FONT_SMALL);
|
||||
};
|
||||
|
||||
|
@ -137,17 +137,17 @@ void BME680Sensor::updateState()
|
||||
#endif
|
||||
}
|
||||
|
||||
void BME680Sensor::checkStatus(String functionName)
|
||||
void BME680Sensor::checkStatus(const char *functionName)
|
||||
{
|
||||
if (bme680.status < BSEC_OK)
|
||||
LOG_ERROR("%s BSEC2 code: %s", functionName.c_str(), String(bme680.status).c_str());
|
||||
LOG_ERROR("%s BSEC2 code: %d", functionName, bme680.status);
|
||||
else if (bme680.status > BSEC_OK)
|
||||
LOG_WARN("%s BSEC2 code: %s", functionName.c_str(), String(bme680.status).c_str());
|
||||
LOG_WARN("%s BSEC2 code: %d", functionName, bme680.status);
|
||||
|
||||
if (bme680.sensor.status < BME68X_OK)
|
||||
LOG_ERROR("%s BME68X code: %s", functionName.c_str(), String(bme680.sensor.status).c_str());
|
||||
LOG_ERROR("%s BME68X code: %d", functionName, bme680.sensor.status);
|
||||
else if (bme680.sensor.status > BME68X_OK)
|
||||
LOG_WARN("%s BME68X code: %s", functionName.c_str(), String(bme680.sensor.status).c_str());
|
||||
LOG_WARN("%s BME68X code: %d", functionName, bme680.sensor.status);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -34,7 +34,7 @@ class BME680Sensor : public TelemetrySensor
|
||||
BSEC_OUTPUT_SENSOR_HEAT_COMPENSATED_HUMIDITY};
|
||||
void loadState();
|
||||
void updateState();
|
||||
void checkStatus(String functionName);
|
||||
void checkStatus(const char *functionName);
|
||||
|
||||
public:
|
||||
BME680Sensor();
|
||||
|
@ -109,14 +109,14 @@ class NimbleBluetoothServerCallback : public NimBLEServerCallbacks
|
||||
display->drawString(x_offset + x, y_offset + y, "Enter this code");
|
||||
|
||||
display->setFont(FONT_LARGE);
|
||||
String displayPin(btPIN);
|
||||
String pin = displayPin.substring(0, 3) + " " + displayPin.substring(3, 6);
|
||||
char pin[8];
|
||||
snprintf(pin, sizeof(pin), "%.3s %.3s", btPIN, btPIN + 3);
|
||||
y_offset = display->height() == 64 ? y_offset + FONT_HEIGHT_SMALL - 5 : y_offset + FONT_HEIGHT_SMALL + 5;
|
||||
display->drawString(x_offset + x, y_offset + y, pin);
|
||||
|
||||
display->setFont(FONT_SMALL);
|
||||
String deviceName = "Name: ";
|
||||
deviceName.concat(getDeviceName());
|
||||
char deviceName[64];
|
||||
snprintf(deviceName, sizeof(deviceName), "Name: %s", getDeviceName());
|
||||
y_offset = display->height() == 64 ? y_offset + FONT_HEIGHT_LARGE - 6 : y_offset + FONT_HEIGHT_LARGE + 5;
|
||||
display->drawString(x_offset + x, y_offset + y, deviceName);
|
||||
});
|
||||
|
@ -80,13 +80,13 @@ bool trySwitchToOTA()
|
||||
return true;
|
||||
}
|
||||
|
||||
String getVersion()
|
||||
const char *getVersion()
|
||||
{
|
||||
const esp_partition_t *part = getAppPartition();
|
||||
esp_app_desc_t app_desc;
|
||||
static esp_app_desc_t app_desc;
|
||||
if (!getAppDesc(part, &app_desc))
|
||||
return String();
|
||||
return String(app_desc.version);
|
||||
return "";
|
||||
return app_desc.version;
|
||||
}
|
||||
|
||||
} // namespace WiFiOTA
|
||||
|
@ -12,7 +12,7 @@ bool isUpdated();
|
||||
void recoverConfig(meshtastic_Config_NetworkConfig *network);
|
||||
void saveConfig(meshtastic_Config_NetworkConfig *network);
|
||||
bool trySwitchToOTA();
|
||||
String getVersion();
|
||||
const char *getVersion();
|
||||
} // namespace WiFiOTA
|
||||
|
||||
#endif // WIFIOTA_H
|
||||
|
Loading…
Reference in New Issue
Block a user