mirror of
https://github.com/meshtastic/firmware.git
synced 2026-01-11 04:17:43 +00:00
Merge branch 'master' into nomad-gemini
This commit is contained in:
@@ -18,7 +18,7 @@
|
||||
#ifdef ARCH_PORTDUINO
|
||||
#include "unistd.h"
|
||||
#endif
|
||||
#include "../userPrefs.h"
|
||||
|
||||
#include "Default.h"
|
||||
#include "TypeConversions.h"
|
||||
|
||||
@@ -175,6 +175,12 @@ bool AdminModule::handleReceivedProtobuf(const meshtastic_MeshPacket &mp, meshta
|
||||
LOG_INFO("Client set ham mode");
|
||||
handleSetHamMode(r->set_ham_mode);
|
||||
break;
|
||||
case meshtastic_AdminMessage_get_ui_config_request_tag: {
|
||||
LOG_INFO("Client is getting device-ui config");
|
||||
handleGetDeviceUIConfig(mp);
|
||||
handled = true;
|
||||
break;
|
||||
}
|
||||
|
||||
/**
|
||||
* Other
|
||||
@@ -234,6 +240,12 @@ bool AdminModule::handleReceivedProtobuf(const meshtastic_MeshPacket &mp, meshta
|
||||
reboot(DEFAULT_REBOOT_SECONDS);
|
||||
break;
|
||||
}
|
||||
case meshtastic_AdminMessage_store_ui_config_tag: {
|
||||
LOG_INFO("Storing device-ui config");
|
||||
handleStoreDeviceUIConfig(r->store_ui_config);
|
||||
handled = true;
|
||||
break;
|
||||
}
|
||||
case meshtastic_AdminMessage_begin_edit_settings_tag: {
|
||||
LOG_INFO("Begin transaction for editing settings");
|
||||
hasOpenEditTransaction = true;
|
||||
@@ -358,7 +370,7 @@ bool AdminModule::handleReceivedProtobuf(const meshtastic_MeshPacket &mp, meshta
|
||||
#ifdef ARCH_PORTDUINO
|
||||
case meshtastic_AdminMessage_exit_simulator_tag:
|
||||
LOG_INFO("Exiting simulator");
|
||||
_exit(0);
|
||||
exit(0);
|
||||
break;
|
||||
#endif
|
||||
|
||||
@@ -477,7 +489,7 @@ void AdminModule::handleSetConfig(const meshtastic_Config &c)
|
||||
IS_ONE_OF(config.device.role, meshtastic_Config_DeviceConfig_Role_ROUTER,
|
||||
meshtastic_Config_DeviceConfig_Role_REPEATER)) {
|
||||
config.device.rebroadcast_mode = meshtastic_Config_DeviceConfig_RebroadcastMode_ALL;
|
||||
const char *warning = "Rebroadcast mode can't be set to NONE for a router or repeater\n";
|
||||
const char *warning = "Rebroadcast mode can't be set to NONE for a router or repeater";
|
||||
LOG_WARN(warning);
|
||||
sendWarning(warning);
|
||||
}
|
||||
@@ -629,6 +641,9 @@ void AdminModule::handleSetConfig(const meshtastic_Config &c)
|
||||
requiresReboot = false;
|
||||
|
||||
break;
|
||||
case meshtastic_Config_device_ui_tag:
|
||||
// NOOP! This is handled by handleStoreDeviceUIConfig
|
||||
break;
|
||||
}
|
||||
if (requiresReboot && !hasOpenEditTransaction) {
|
||||
disableBluetooth();
|
||||
@@ -791,6 +806,10 @@ void AdminModule::handleGetConfig(const meshtastic_MeshPacket &req, const uint32
|
||||
LOG_INFO("Get config: Sessionkey");
|
||||
res.get_config_response.which_payload_variant = meshtastic_Config_sessionkey_tag;
|
||||
break;
|
||||
case meshtastic_AdminMessage_ConfigType_DEVICEUI_CONFIG:
|
||||
// NOOP! This is handled by handleGetDeviceUIConfig
|
||||
res.get_config_response.which_payload_variant = meshtastic_Config_device_ui_tag;
|
||||
break;
|
||||
}
|
||||
// NOTE: The phone app needs to know the ls_secs value so it can properly expect sleep behavior.
|
||||
// So even if we internally use 0 to represent 'use default' we still need to send the value we are
|
||||
@@ -1003,6 +1022,14 @@ void AdminModule::handleGetChannel(const meshtastic_MeshPacket &req, uint32_t ch
|
||||
}
|
||||
}
|
||||
|
||||
void AdminModule::handleGetDeviceUIConfig(const meshtastic_MeshPacket &req)
|
||||
{
|
||||
meshtastic_AdminMessage r = meshtastic_AdminMessage_init_default;
|
||||
r.which_payload_variant = meshtastic_AdminMessage_get_ui_config_response_tag;
|
||||
r.get_ui_config_response = uiconfig;
|
||||
myReply = allocDataProtobuf(r);
|
||||
}
|
||||
|
||||
void AdminModule::reboot(int32_t seconds)
|
||||
{
|
||||
LOG_INFO("Reboot in %d seconds", seconds);
|
||||
@@ -1023,6 +1050,11 @@ void AdminModule::saveChanges(int saveWhat, bool shouldReboot)
|
||||
}
|
||||
}
|
||||
|
||||
void AdminModule::handleStoreDeviceUIConfig(const meshtastic_DeviceUIConfig &uicfg)
|
||||
{
|
||||
nodeDB->saveProto("/prefs/uiconfig.proto", meshtastic_DeviceUIConfig_size, &meshtastic_DeviceUIConfig_msg, &uicfg);
|
||||
}
|
||||
|
||||
void AdminModule::handleSetHamMode(const meshtastic_HamParameters &p)
|
||||
{
|
||||
// Set call sign and override lora limitations for licensed use
|
||||
@@ -1089,7 +1121,7 @@ bool AdminModule::messageIsResponse(const meshtastic_AdminMessage *r)
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_ringtone_response_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_device_connection_status_response_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_node_remote_hardware_pins_response_tag ||
|
||||
r->which_payload_variant == meshtastic_NodeRemoteHardwarePinsResponse_node_remote_hardware_pins_tag)
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_ui_config_response_tag)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
@@ -1105,7 +1137,8 @@ bool AdminModule::messageIsRequest(const meshtastic_AdminMessage *r)
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_device_metadata_request_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_ringtone_request_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_device_connection_status_request_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_node_remote_hardware_pins_request_tag)
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_node_remote_hardware_pins_request_tag ||
|
||||
r->which_payload_variant == meshtastic_AdminMessage_get_ui_config_request_tag)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
|
||||
@@ -43,6 +43,7 @@ class AdminModule : public ProtobufModule<meshtastic_AdminMessage>, public Obser
|
||||
void handleGetDeviceMetadata(const meshtastic_MeshPacket &req);
|
||||
void handleGetDeviceConnectionStatus(const meshtastic_MeshPacket &req);
|
||||
void handleGetNodeRemoteHardwarePins(const meshtastic_MeshPacket &req);
|
||||
void handleGetDeviceUIConfig(const meshtastic_MeshPacket &req);
|
||||
/**
|
||||
* Setters
|
||||
*/
|
||||
@@ -52,6 +53,7 @@ class AdminModule : public ProtobufModule<meshtastic_AdminMessage>, public Obser
|
||||
void handleSetModuleConfig(const meshtastic_ModuleConfig &c);
|
||||
void handleSetChannel();
|
||||
void handleSetHamMode(const meshtastic_HamParameters &req);
|
||||
void handleStoreDeviceUIConfig(const meshtastic_DeviceUIConfig &uicfg);
|
||||
void reboot(int32_t seconds);
|
||||
|
||||
void setPassKey(meshtastic_AdminMessage *res);
|
||||
|
||||
@@ -117,8 +117,10 @@ class CannedMessageModule : public SinglePortModule, public Observable<const UIF
|
||||
int handleInputEvent(const InputEvent *event);
|
||||
virtual bool wantUIFrame() override { return this->shouldDraw(); }
|
||||
virtual Observable<const UIFrameEvent *> *getUIFrameObservable() override { return this; }
|
||||
virtual void drawFrame(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, int16_t y) override;
|
||||
virtual bool interceptingKeyboardInput() override;
|
||||
#if !HAS_TFT
|
||||
virtual void drawFrame(OLEDDisplay *display, OLEDDisplayUiState *state, int16_t x, int16_t y) override;
|
||||
#endif
|
||||
virtual AdminMessageHandleResult handleAdminMessageForModule(const meshtastic_MeshPacket &mp,
|
||||
meshtastic_AdminMessage *request,
|
||||
meshtastic_AdminMessage *response) override;
|
||||
@@ -228,4 +230,4 @@ class CannedMessageModule : public SinglePortModule, public Observable<const UIF
|
||||
};
|
||||
|
||||
extern CannedMessageModule *cannedMessageModule;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -124,7 +124,8 @@ int32_t ExternalNotificationModule::runOnce()
|
||||
if (externalTurnedOn[2] + (moduleConfig.external_notification.output_ms ? moduleConfig.external_notification.output_ms
|
||||
: EXT_NOTIFICATION_MODULE_OUTPUT_MS) <
|
||||
millis()) {
|
||||
LOG_DEBUG("EXTERNAL 2 %d compared to %d", externalTurnedOn[2]+moduleConfig.external_notification.output_ms, millis());
|
||||
LOG_DEBUG("EXTERNAL 2 %d compared to %d", externalTurnedOn[2] + moduleConfig.external_notification.output_ms,
|
||||
millis());
|
||||
setExternalState(2, !getExternal(2));
|
||||
}
|
||||
#if defined(HAS_NCP5623) || defined(RGBLED_RED) || defined(HAS_NEOPIXEL) || defined(UNPHONE)
|
||||
|
||||
@@ -74,7 +74,7 @@
|
||||
#include "modules/StoreForwardModule.h"
|
||||
#endif
|
||||
#endif
|
||||
#if defined(ARCH_ESP32) || defined(ARCH_NRF52) || defined(ARCH_RP2040)
|
||||
#if defined(ARCH_ESP32) || defined(ARCH_NRF52) || defined(ARCH_RP2040) || defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_EXTERNALNOTIFICATION
|
||||
#include "modules/ExternalNotificationModule.h"
|
||||
#endif
|
||||
@@ -173,7 +173,7 @@ void setupModules()
|
||||
aSerialKeyboardImpl->init();
|
||||
#endif // INPUTBROKER_MATRIX_TYPE
|
||||
#endif // HAS_BUTTON
|
||||
#if ARCH_PORTDUINO
|
||||
#if ARCH_PORTDUINO && !HAS_TFT
|
||||
aLinuxInputImpl = new LinuxInputImpl();
|
||||
aLinuxInputImpl->init();
|
||||
#endif
|
||||
@@ -195,11 +195,13 @@ void setupModules()
|
||||
if (nodeTelemetrySensorsMap[meshtastic_TelemetrySensorType_PMSA003I].first > 0) {
|
||||
new AirQualityTelemetryModule();
|
||||
}
|
||||
#if !MESHTASTIC_EXCLUDE_HEALTH_TELEMETRY
|
||||
if (nodeTelemetrySensorsMap[meshtastic_TelemetrySensorType_MAX30102].first > 0 ||
|
||||
nodeTelemetrySensorsMap[meshtastic_TelemetrySensorType_MLX90614].first > 0) {
|
||||
new HealthTelemetryModule();
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
#if HAS_TELEMETRY && !MESHTASTIC_EXCLUDE_POWER_TELEMETRY && !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
new PowerTelemetryModule();
|
||||
#endif
|
||||
@@ -223,7 +225,7 @@ void setupModules()
|
||||
storeForwardModule = new StoreForwardModule();
|
||||
#endif
|
||||
#endif
|
||||
#if defined(ARCH_ESP32) || defined(ARCH_NRF52) || defined(ARCH_RP2040)
|
||||
#if defined(ARCH_ESP32) || defined(ARCH_NRF52) || defined(ARCH_RP2040) || defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_EXTERNALNOTIFICATION
|
||||
externalNotificationModule = new ExternalNotificationModule();
|
||||
#endif
|
||||
|
||||
@@ -389,7 +389,7 @@ int32_t PositionModule::runOnce()
|
||||
}
|
||||
|
||||
if (lastGpsSend == 0 || msSinceLastSend >= intervalMs) {
|
||||
if (hasValidPosition(node)) {
|
||||
if (nodeDB->hasValidPosition(node)) {
|
||||
lastGpsSend = now;
|
||||
|
||||
lastGpsLatitude = node->position.latitude_i;
|
||||
@@ -403,7 +403,7 @@ int32_t PositionModule::runOnce()
|
||||
} else if (config.position.position_broadcast_smart_enabled) {
|
||||
const meshtastic_NodeInfoLite *node2 = service->refreshLocalMeshNode(); // should guarantee there is now a position
|
||||
|
||||
if (hasValidPosition(node2)) {
|
||||
if (nodeDB->hasValidPosition(node2)) {
|
||||
// The minimum time (in seconds) that would pass before we are able to send a new position packet.
|
||||
|
||||
auto smartPosition = getDistanceTraveledSinceLastSend(node->position);
|
||||
@@ -464,7 +464,7 @@ void PositionModule::handleNewPosition()
|
||||
meshtastic_NodeInfoLite *node = nodeDB->getMeshNode(nodeDB->getNodeNum());
|
||||
const meshtastic_NodeInfoLite *node2 = service->refreshLocalMeshNode(); // should guarantee there is now a position
|
||||
// We limit our GPS broadcasts to a max rate
|
||||
if (hasValidPosition(node2)) {
|
||||
if (nodeDB->hasValidPosition(node2)) {
|
||||
auto smartPosition = getDistanceTraveledSinceLastSend(node->position);
|
||||
uint32_t msSinceLastSend = millis() - lastGpsSend;
|
||||
if (smartPosition.hasTraveledOverThreshold &&
|
||||
@@ -483,4 +483,4 @@ void PositionModule::handleNewPosition()
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -155,8 +155,6 @@ ProcessMessage RangeTestModuleRadio::handleReceived(const meshtastic_MeshPacket
|
||||
LOG_DEBUG("mp.from %d", mp.from);
|
||||
LOG_DEBUG("mp.rx_snr %f", mp.rx_snr);
|
||||
LOG_DEBUG("mp.hop_limit %d", mp.hop_limit);
|
||||
// LOG_DEBUG("mp.decoded.position.latitude_i %d", mp.decoded.position.latitude_i); // Deprecated
|
||||
// LOG_DEBUG("mp.decoded.position.longitude_i %d", mp.decoded.position.longitude_i); // Deprecated
|
||||
LOG_DEBUG("---- Node Information of Received Packet (mp.from):");
|
||||
LOG_DEBUG("n->user.long_name %s", n->user.long_name);
|
||||
LOG_DEBUG("n->user.short_name %s", n->user.short_name);
|
||||
@@ -194,8 +192,6 @@ bool RangeTestModuleRadio::appendFile(const meshtastic_MeshPacket &mp)
|
||||
LOG_DEBUG("mp.from %d", mp.from);
|
||||
LOG_DEBUG("mp.rx_snr %f", mp.rx_snr);
|
||||
LOG_DEBUG("mp.hop_limit %d", mp.hop_limit);
|
||||
// LOG_DEBUG("mp.decoded.position.latitude_i %d", mp.decoded.position.latitude_i); // Deprecated
|
||||
// LOG_DEBUG("mp.decoded.position.longitude_i %d", mp.decoded.position.longitude_i); // Deprecated
|
||||
LOG_DEBUG("---- Node Information of Received Packet (mp.from):");
|
||||
LOG_DEBUG("n->user.long_name %s", n->user.long_name);
|
||||
LOG_DEBUG("n->user.short_name %s", n->user.short_name);
|
||||
@@ -265,13 +261,21 @@ bool RangeTestModuleRadio::appendFile(const meshtastic_MeshPacket &mp)
|
||||
fileToAppend.printf("??:??:??,"); // Time
|
||||
}
|
||||
|
||||
fileToAppend.printf("%d,", getFrom(&mp)); // From
|
||||
fileToAppend.printf("%s,", n->user.long_name); // Long Name
|
||||
fileToAppend.printf("%f,", n->position.latitude_i * 1e-7); // Sender Lat
|
||||
fileToAppend.printf("%f,", n->position.longitude_i * 1e-7); // Sender Long
|
||||
fileToAppend.printf("%f,", gpsStatus->getLatitude() * 1e-7); // RX Lat
|
||||
fileToAppend.printf("%f,", gpsStatus->getLongitude() * 1e-7); // RX Long
|
||||
fileToAppend.printf("%d,", gpsStatus->getAltitude()); // RX Altitude
|
||||
fileToAppend.printf("%d,", getFrom(&mp)); // From
|
||||
fileToAppend.printf("%s,", n->user.long_name); // Long Name
|
||||
fileToAppend.printf("%f,", n->position.latitude_i * 1e-7); // Sender Lat
|
||||
fileToAppend.printf("%f,", n->position.longitude_i * 1e-7); // Sender Long
|
||||
if (gpsStatus->getIsConnected() || config.position.fixed_position) {
|
||||
fileToAppend.printf("%f,", gpsStatus->getLatitude() * 1e-7); // RX Lat
|
||||
fileToAppend.printf("%f,", gpsStatus->getLongitude() * 1e-7); // RX Long
|
||||
fileToAppend.printf("%d,", gpsStatus->getAltitude()); // RX Altitude
|
||||
} else {
|
||||
// When the phone API is in use, the node info will be updated with position
|
||||
meshtastic_NodeInfoLite *us = nodeDB->getMeshNode(nodeDB->getNodeNum());
|
||||
fileToAppend.printf("%f,", us->position.latitude_i * 1e-7); // RX Lat
|
||||
fileToAppend.printf("%f,", us->position.longitude_i * 1e-7); // RX Long
|
||||
fileToAppend.printf("%d,", us->position.altitude); // RX Altitude
|
||||
}
|
||||
|
||||
fileToAppend.printf("%f,", mp.rx_snr); // RX SNR
|
||||
|
||||
@@ -292,4 +296,4 @@ bool RangeTestModuleRadio::appendFile(const meshtastic_MeshPacket &mp)
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@@ -205,7 +205,7 @@ int32_t SerialModule::runOnce()
|
||||
uint32_t readIndex = 0;
|
||||
const meshtastic_NodeInfoLite *tempNodeInfo = nodeDB->readNextMeshNode(readIndex);
|
||||
while (tempNodeInfo != NULL) {
|
||||
if (tempNodeInfo->has_user && hasValidPosition(tempNodeInfo)) {
|
||||
if (tempNodeInfo->has_user && nodeDB->hasValidPosition(tempNodeInfo)) {
|
||||
printWPL(outbuf, sizeof(outbuf), tempNodeInfo->position, tempNodeInfo->user.long_name, true);
|
||||
serialPrint->printf("%s", outbuf);
|
||||
}
|
||||
@@ -474,7 +474,7 @@ void SerialModule::processWXSerial()
|
||||
if (windDirPos != NULL) {
|
||||
// Extract data after "=" for WindDir
|
||||
strcpy(windDir, windDirPos + 15); // Add 15 to skip "WindDir = "
|
||||
double radians = toRadians(strtof(windDir, nullptr));
|
||||
double radians = GeoCoord::toRadians(strtof(windDir, nullptr));
|
||||
dir_sum_sin += sin(radians);
|
||||
dir_sum_cos += cos(radians);
|
||||
dirCount++;
|
||||
@@ -541,7 +541,7 @@ void SerialModule::processWXSerial()
|
||||
double avgCos = dir_sum_cos / dirCount;
|
||||
|
||||
double avgRadians = atan2(avgSin, avgCos);
|
||||
float dirAvg = toDegrees(avgRadians);
|
||||
float dirAvg = GeoCoord::toDegrees(avgRadians);
|
||||
|
||||
if (dirAvg < 0) {
|
||||
dirAvg += 360.0;
|
||||
|
||||
@@ -73,11 +73,11 @@ void StoreForwardModule::populatePSRAM()
|
||||
LOG_DEBUG("Before PSRAM init: heap %d/%d PSRAM %d/%d", memGet.getFreeHeap(), memGet.getHeapSize(), memGet.getFreePsram(),
|
||||
memGet.getPsramSize());
|
||||
|
||||
/* Use a maximum of 2/3 the available PSRAM unless otherwise specified.
|
||||
/* Use a maximum of 3/4 the available PSRAM unless otherwise specified.
|
||||
Note: This needs to be done after every thing that would use PSRAM
|
||||
*/
|
||||
uint32_t numberOfPackets =
|
||||
(this->records ? this->records : (((memGet.getFreePsram() / 3) * 2) / sizeof(PacketHistoryStruct)));
|
||||
(this->records ? this->records : (((memGet.getFreePsram() / 4) * 3) / sizeof(PacketHistoryStruct)));
|
||||
this->records = numberOfPackets;
|
||||
#if defined(ARCH_ESP32)
|
||||
this->packetHistory = static_cast<PacketHistoryStruct *>(ps_calloc(numberOfPackets, sizeof(PacketHistoryStruct)));
|
||||
@@ -198,6 +198,9 @@ void StoreForwardModule::historyAdd(const meshtastic_MeshPacket &mp)
|
||||
this->packetHistory[this->packetHistoryTotalCount].to = mp.to;
|
||||
this->packetHistory[this->packetHistoryTotalCount].channel = mp.channel;
|
||||
this->packetHistory[this->packetHistoryTotalCount].from = getFrom(&mp);
|
||||
this->packetHistory[this->packetHistoryTotalCount].id = mp.id;
|
||||
this->packetHistory[this->packetHistoryTotalCount].reply_id = p.reply_id;
|
||||
this->packetHistory[this->packetHistoryTotalCount].emoji = (bool)p.emoji;
|
||||
this->packetHistory[this->packetHistoryTotalCount].payload_size = p.payload.size;
|
||||
memcpy(this->packetHistory[this->packetHistoryTotalCount].payload, p.payload.bytes, meshtastic_Constants_DATA_PAYLOAD_LEN);
|
||||
|
||||
@@ -244,8 +247,11 @@ meshtastic_MeshPacket *StoreForwardModule::preparePayload(NodeNum dest, uint32_t
|
||||
|
||||
p->to = local ? this->packetHistory[i].to : dest; // PhoneAPI can handle original `to`
|
||||
p->from = this->packetHistory[i].from;
|
||||
p->id = this->packetHistory[i].id;
|
||||
p->channel = this->packetHistory[i].channel;
|
||||
p->decoded.reply_id = this->packetHistory[i].reply_id;
|
||||
p->rx_time = this->packetHistory[i].time;
|
||||
p->decoded.emoji = (uint32_t)this->packetHistory[i].emoji;
|
||||
|
||||
// Let's assume that if the server received the S&F request that the client is in range.
|
||||
// TODO: Make this configurable.
|
||||
@@ -617,4 +623,4 @@ StoreForwardModule::StoreForwardModule()
|
||||
disable();
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -13,7 +13,10 @@ struct PacketHistoryStruct {
|
||||
uint32_t time;
|
||||
uint32_t to;
|
||||
uint32_t from;
|
||||
uint32_t id;
|
||||
uint8_t channel;
|
||||
uint32_t reply_id;
|
||||
bool emoji;
|
||||
uint8_t payload[meshtastic_Constants_DATA_PAYLOAD_LEN];
|
||||
pb_size_t payload_size;
|
||||
};
|
||||
|
||||
@@ -113,12 +113,18 @@ bool AirQualityTelemetryModule::getAirQualityTelemetry(meshtastic_Telemetry *m)
|
||||
|
||||
m->time = getTime();
|
||||
m->which_variant = meshtastic_Telemetry_air_quality_metrics_tag;
|
||||
m->variant.air_quality_metrics.has_pm10_standard = true;
|
||||
m->variant.air_quality_metrics.pm10_standard = data.pm10_standard;
|
||||
m->variant.air_quality_metrics.has_pm25_standard = true;
|
||||
m->variant.air_quality_metrics.pm25_standard = data.pm25_standard;
|
||||
m->variant.air_quality_metrics.has_pm100_standard = true;
|
||||
m->variant.air_quality_metrics.pm100_standard = data.pm100_standard;
|
||||
|
||||
m->variant.air_quality_metrics.has_pm10_environmental = true;
|
||||
m->variant.air_quality_metrics.pm10_environmental = data.pm10_env;
|
||||
m->variant.air_quality_metrics.has_pm25_environmental = true;
|
||||
m->variant.air_quality_metrics.pm25_environmental = data.pm25_env;
|
||||
m->variant.air_quality_metrics.has_pm100_environmental = true;
|
||||
m->variant.air_quality_metrics.pm100_environmental = data.pm100_env;
|
||||
|
||||
LOG_INFO("Send: PM1.0(Standard)=%i, PM2.5(Standard)=%i, PM10.0(Standard)=%i", m->variant.air_quality_metrics.pm10_standard,
|
||||
|
||||
@@ -130,6 +130,14 @@ meshtastic_Telemetry DeviceTelemetryModule::getLocalStatsTelemetry()
|
||||
telemetry.variant.local_stats.num_packets_rx_bad = RadioLibInterface::instance->rxBad;
|
||||
telemetry.variant.local_stats.num_tx_relay = RadioLibInterface::instance->txRelay;
|
||||
}
|
||||
#ifdef ARCH_PORTDUINO
|
||||
if (SimRadio::instance) {
|
||||
telemetry.variant.local_stats.num_packets_tx = SimRadio::instance->txGood;
|
||||
telemetry.variant.local_stats.num_packets_rx = SimRadio::instance->rxGood + SimRadio::instance->rxBad;
|
||||
telemetry.variant.local_stats.num_packets_rx_bad = SimRadio::instance->rxBad;
|
||||
telemetry.variant.local_stats.num_tx_relay = SimRadio::instance->txRelay;
|
||||
}
|
||||
#endif
|
||||
if (router) {
|
||||
telemetry.variant.local_stats.num_rx_dupe = router->rxDupe;
|
||||
telemetry.variant.local_stats.num_tx_relay_canceled = router->txRelayCanceled;
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
#include <OLEDDisplay.h>
|
||||
#include <OLEDDisplayUi.h>
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR_EXTERNAL
|
||||
// Sensors
|
||||
#include "Sensor/AHT10.h"
|
||||
#include "Sensor/BME280Sensor.h"
|
||||
@@ -36,7 +37,6 @@
|
||||
#include "Sensor/SHT31Sensor.h"
|
||||
#include "Sensor/SHT4XSensor.h"
|
||||
#include "Sensor/SHTC3Sensor.h"
|
||||
#include "Sensor/T1000xSensor.h"
|
||||
#include "Sensor/TSL2591Sensor.h"
|
||||
#include "Sensor/VEML7700Sensor.h"
|
||||
|
||||
@@ -58,11 +58,12 @@ MLX90632Sensor mlx90632Sensor;
|
||||
DFRobotLarkSensor dfRobotLarkSensor;
|
||||
NAU7802Sensor nau7802Sensor;
|
||||
BMP3XXSensor bmp3xxSensor;
|
||||
CGRadSensSensor cgRadSens;
|
||||
#endif
|
||||
#ifdef T1000X_SENSOR_EN
|
||||
#include "Sensor/T1000xSensor.h"
|
||||
T1000xSensor t1000xSensor;
|
||||
#endif
|
||||
CGRadSensSensor cgRadSens;
|
||||
|
||||
#define FAILED_STATE_SENSOR_READ_MULTIPLIER 10
|
||||
#define DISPLAY_RECEIVEID_MEASUREMENTS_ON_SCREEN true
|
||||
|
||||
@@ -104,7 +105,7 @@ int32_t EnvironmentTelemetryModule::runOnce()
|
||||
// therefore, we should only enable the sensor loop if measurement is also enabled
|
||||
#ifdef T1000X_SENSOR_EN
|
||||
result = t1000xSensor.runOnce();
|
||||
#else
|
||||
#elif !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR_EXTERNAL
|
||||
if (dfRobotLarkSensor.hasSensor())
|
||||
result = dfRobotLarkSensor.runOnce();
|
||||
if (bmp085Sensor.hasSensor())
|
||||
@@ -159,8 +160,10 @@ int32_t EnvironmentTelemetryModule::runOnce()
|
||||
if (!moduleConfig.telemetry.environment_measurement_enabled) {
|
||||
return disable();
|
||||
} else {
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR_EXTERNAL
|
||||
if (bme680Sensor.hasSensor())
|
||||
result = bme680Sensor.runTrigger();
|
||||
#endif
|
||||
}
|
||||
|
||||
if (((lastSentToMesh == 0) ||
|
||||
@@ -499,6 +502,7 @@ AdminMessageHandleResult EnvironmentTelemetryModule::handleAdminMessageForModule
|
||||
meshtastic_AdminMessage *response)
|
||||
{
|
||||
AdminMessageHandleResult result = AdminMessageHandleResult::NOT_HANDLED;
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR_EXTERNAL
|
||||
if (dfRobotLarkSensor.hasSensor()) {
|
||||
result = dfRobotLarkSensor.handleAdminMessage(mp, request, response);
|
||||
if (result != AdminMessageHandleResult::NOT_HANDLED)
|
||||
@@ -609,7 +613,8 @@ AdminMessageHandleResult EnvironmentTelemetryModule::handleAdminMessageForModule
|
||||
if (result != AdminMessageHandleResult::NOT_HANDLED)
|
||||
return result;
|
||||
}
|
||||
#endif
|
||||
return result;
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,6 +1,6 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !MESHTASTIC_EXCLUDE_HEALTH_TELEMETRY && !defined(ARCH_PORTDUINO)
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "Default.h"
|
||||
@@ -246,4 +246,4 @@ bool HealthTelemetryModule::sendTelemetry(NodeNum dest, bool phoneOnly)
|
||||
return false;
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,6 +1,6 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !MESHTASTIC_EXCLUDE_HEALTH_TELEMETRY && !defined(ARCH_PORTDUINO)
|
||||
|
||||
#pragma once
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
@@ -57,4 +57,4 @@ class HealthTelemetryModule : private concurrency::OSThread, public ProtobufModu
|
||||
uint32_t sensor_read_error_count = 0;
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -56,6 +56,8 @@ int32_t PowerTelemetryModule::runOnce()
|
||||
// therefore, we should only enable the sensor loop if measurement is also enabled
|
||||
if (ina219Sensor.hasSensor() && !ina219Sensor.isInitialized())
|
||||
result = ina219Sensor.runOnce();
|
||||
if (ina226Sensor.hasSensor() && !ina226Sensor.isInitialized())
|
||||
result = ina226Sensor.runOnce();
|
||||
if (ina260Sensor.hasSensor() && !ina260Sensor.isInitialized())
|
||||
result = ina260Sensor.runOnce();
|
||||
if (ina3221Sensor.hasSensor() && !ina3221Sensor.isInitialized())
|
||||
@@ -170,6 +172,8 @@ bool PowerTelemetryModule::getPowerTelemetry(meshtastic_Telemetry *m)
|
||||
#if HAS_TELEMETRY && !defined(ARCH_PORTDUINO)
|
||||
if (ina219Sensor.hasSensor())
|
||||
valid = ina219Sensor.getMetrics(m);
|
||||
if (ina226Sensor.hasSensor())
|
||||
valid = ina226Sensor.getMetrics(m);
|
||||
if (ina260Sensor.hasSensor())
|
||||
valid = ina260Sensor.getMetrics(m);
|
||||
if (ina3221Sensor.hasSensor())
|
||||
@@ -253,4 +257,4 @@ bool PowerTelemetryModule::sendTelemetry(NodeNum dest, bool phoneOnly)
|
||||
return false;
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
13
src/modules/Telemetry/Sensor/CurrentSensor.h
Normal file
13
src/modules/Telemetry/Sensor/CurrentSensor.h
Normal file
@@ -0,0 +1,13 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
|
||||
#pragma once
|
||||
|
||||
class CurrentSensor
|
||||
{
|
||||
public:
|
||||
virtual int16_t getCurrentMa() = 0;
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -45,4 +45,9 @@ uint16_t INA219Sensor::getBusVoltageMv()
|
||||
return lround(ina219.getBusVoltage_V() * 1000);
|
||||
}
|
||||
|
||||
int16_t INA219Sensor::getCurrentMa()
|
||||
{
|
||||
return lround(ina219.getCurrent_mA());
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -3,11 +3,12 @@
|
||||
#if HAS_TELEMETRY && !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "CurrentSensor.h"
|
||||
#include "TelemetrySensor.h"
|
||||
#include "VoltageSensor.h"
|
||||
#include <Adafruit_INA219.h>
|
||||
|
||||
class INA219Sensor : public TelemetrySensor, VoltageSensor
|
||||
class INA219Sensor : public TelemetrySensor, VoltageSensor, CurrentSensor
|
||||
{
|
||||
private:
|
||||
Adafruit_INA219 ina219;
|
||||
@@ -20,6 +21,7 @@ class INA219Sensor : public TelemetrySensor, VoltageSensor
|
||||
virtual int32_t runOnce() override;
|
||||
virtual bool getMetrics(meshtastic_Telemetry *measurement) override;
|
||||
virtual uint16_t getBusVoltageMv() override;
|
||||
virtual int16_t getCurrentMa() override;
|
||||
};
|
||||
|
||||
#endif
|
||||
58
src/modules/Telemetry/Sensor/INA226Sensor.cpp
Normal file
58
src/modules/Telemetry/Sensor/INA226Sensor.cpp
Normal file
@@ -0,0 +1,58 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if HAS_TELEMETRY && !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "INA226.h"
|
||||
#include "INA226Sensor.h"
|
||||
#include "TelemetrySensor.h"
|
||||
|
||||
INA226Sensor::INA226Sensor() : TelemetrySensor(meshtastic_TelemetrySensorType_INA226, "INA226") {}
|
||||
|
||||
int32_t INA226Sensor::runOnce()
|
||||
{
|
||||
LOG_INFO("Init sensor: %s", sensorName);
|
||||
if (!hasSensor()) {
|
||||
return DEFAULT_SENSOR_MINIMUM_WAIT_TIME_BETWEEN_READS;
|
||||
}
|
||||
|
||||
begin(nodeTelemetrySensorsMap[sensorType].second, nodeTelemetrySensorsMap[sensorType].first);
|
||||
|
||||
if (!status) {
|
||||
status = ina226.begin();
|
||||
}
|
||||
return initI2CSensor();
|
||||
}
|
||||
|
||||
void INA226Sensor::setup() {}
|
||||
|
||||
void INA226Sensor::begin(TwoWire *wire, uint8_t addr)
|
||||
{
|
||||
_wire = wire;
|
||||
_addr = addr;
|
||||
ina226 = INA226(_addr, _wire);
|
||||
_wire->begin();
|
||||
}
|
||||
|
||||
bool INA226Sensor::getMetrics(meshtastic_Telemetry *measurement)
|
||||
{
|
||||
measurement->variant.environment_metrics.has_voltage = true;
|
||||
measurement->variant.environment_metrics.has_current = true;
|
||||
|
||||
// mV conversion to V
|
||||
measurement->variant.environment_metrics.voltage = ina226.getBusVoltage() / 1000;
|
||||
measurement->variant.environment_metrics.current = ina226.getCurrent_mA();
|
||||
return true;
|
||||
}
|
||||
|
||||
uint16_t INA226Sensor::getBusVoltageMv()
|
||||
{
|
||||
return lround(ina226.getBusVoltage());
|
||||
}
|
||||
|
||||
int16_t INA226Sensor::getCurrentMa()
|
||||
{
|
||||
return lround(ina226.getCurrent_mA());
|
||||
}
|
||||
|
||||
#endif
|
||||
30
src/modules/Telemetry/Sensor/INA226Sensor.h
Normal file
30
src/modules/Telemetry/Sensor/INA226Sensor.h
Normal file
@@ -0,0 +1,30 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if HAS_TELEMETRY && !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "CurrentSensor.h"
|
||||
#include "TelemetrySensor.h"
|
||||
#include "VoltageSensor.h"
|
||||
#include <INA226.h>
|
||||
|
||||
class INA226Sensor : public TelemetrySensor, VoltageSensor, CurrentSensor
|
||||
{
|
||||
private:
|
||||
uint8_t _addr = INA_ADDR;
|
||||
TwoWire *_wire = &Wire;
|
||||
INA226 ina226 = INA226(_addr, _wire);
|
||||
|
||||
protected:
|
||||
virtual void setup() override;
|
||||
void begin(TwoWire *wire = &Wire, uint8_t addr = INA_ADDR);
|
||||
|
||||
public:
|
||||
INA226Sensor();
|
||||
virtual int32_t runOnce() override;
|
||||
virtual bool getMetrics(meshtastic_Telemetry *measurement) override;
|
||||
virtual uint16_t getBusVoltageMv() override;
|
||||
virtual int16_t getCurrentMa() override;
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -102,4 +102,9 @@ uint16_t INA3221Sensor::getBusVoltageMv()
|
||||
return lround(ina3221.getVoltage(BAT_CH) * 1000);
|
||||
}
|
||||
|
||||
int16_t INA3221Sensor::getCurrentMa()
|
||||
{
|
||||
return lround(ina3221.getCurrent(BAT_CH));
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -3,11 +3,12 @@
|
||||
#if HAS_TELEMETRY && !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "CurrentSensor.h"
|
||||
#include "TelemetrySensor.h"
|
||||
#include "VoltageSensor.h"
|
||||
#include <INA3221.h>
|
||||
|
||||
class INA3221Sensor : public TelemetrySensor, VoltageSensor
|
||||
class INA3221Sensor : public TelemetrySensor, VoltageSensor, CurrentSensor
|
||||
{
|
||||
private:
|
||||
INA3221 ina3221 = INA3221(INA3221_ADDR42_SDA);
|
||||
@@ -35,6 +36,7 @@ class INA3221Sensor : public TelemetrySensor, VoltageSensor
|
||||
int32_t runOnce() override;
|
||||
bool getMetrics(meshtastic_Telemetry *measurement) override;
|
||||
virtual uint16_t getBusVoltageMv() override;
|
||||
virtual int16_t getCurrentMa() override;
|
||||
};
|
||||
|
||||
struct _INA3221Measurement {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !MESHTASTIC_EXCLUDE_HEALTH_TELEMETRY && !defined(ARCH_PORTDUINO)
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "MAX30102Sensor.h"
|
||||
@@ -80,4 +80,4 @@ bool MAX30102Sensor::getMetrics(meshtastic_Telemetry *measurement)
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,6 +1,6 @@
|
||||
#include "configuration.h"
|
||||
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !defined(ARCH_PORTDUINO)
|
||||
#if !MESHTASTIC_EXCLUDE_ENVIRONMENTAL_SENSOR && !MESHTASTIC_EXCLUDE_HEALTH_TELEMETRY && !defined(ARCH_PORTDUINO)
|
||||
|
||||
#include "../mesh/generated/meshtastic/telemetry.pb.h"
|
||||
#include "TelemetrySensor.h"
|
||||
@@ -23,4 +23,4 @@ class MAX30102Sensor : public TelemetrySensor
|
||||
virtual bool getMetrics(meshtastic_Telemetry *measurement) override;
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -126,7 +126,7 @@ void WaypointModule::drawFrame(OLEDDisplay *display, OLEDDisplayUiState *state,
|
||||
}
|
||||
|
||||
// If our node has a position:
|
||||
if (ourNode && (hasValidPosition(ourNode) || screen->hasHeading())) {
|
||||
if (ourNode && (nodeDB->hasValidPosition(ourNode) || screen->hasHeading())) {
|
||||
const meshtastic_PositionLite &op = ourNode->position;
|
||||
float myHeading;
|
||||
if (screen->hasHeading())
|
||||
|
||||
Reference in New Issue
Block a user