Skip to content

Commit 4de6656

Browse files
committed
new usermod hooks "onUdpPacket"
this new hooks will help you implement new and custom protocols in usermods. I've provided an example (see usermods/udp_name_sync). The example will help you share the main segment name across different WLED instances. The segment name can be useful to sync with some effects like GIF image or scrolling text. If you define new packet format in your usermod, make sure it will either not collide with already used version of wled udp packet : - 0 is for udp sync - 1 is for AudioReactive data - 2 is for udp_name_sync :) Also, the onUdpPacket will override "parseNotification" if it returns "true". Have fun!
1 parent 7285efe commit 4de6656

File tree

5 files changed

+93
-0
lines changed

5 files changed

+93
-0
lines changed
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
{
2+
"name": "udp_name_sync",
3+
"build": { "libArchive": false },
4+
"dependencies": {}
5+
}
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
#include "wled.h"
2+
3+
class UdpNameSync : public Usermod {
4+
5+
private:
6+
7+
bool enabled = false;
8+
bool initDone = false;
9+
unsigned long lastTime = 0;
10+
char segmentName[WLED_MAX_SEGNAME_LEN] = {0};
11+
static const char _name[];
12+
static const char _enabled[];
13+
14+
public:
15+
/**
16+
* Enable/Disable the usermod
17+
*/
18+
inline void enable(bool enable) { enabled = enable; }
19+
20+
/**
21+
* Get usermod enabled/disabled state
22+
*/
23+
inline bool isEnabled() { return enabled; }
24+
25+
void setup() override {
26+
initDone = true;
27+
}
28+
29+
void loop() override {
30+
if (!WLED_CONNECTED) return;
31+
if (!udpConnected) return;
32+
Segment& mainseg = strip.getMainSegment();
33+
if (!strlen(segmentName) && !mainseg.name) return; //name was never set, do nothing
34+
35+
IPAddress broadcastIp = ~uint32_t(Network.subnetMask()) | uint32_t(Network.gatewayIP());
36+
byte udpOut[WLED_MAX_SEGNAME_LEN + 2];
37+
udpOut[0] = 2; // 0: wled notifier protocol, 1: warls protocol, 2 is free
38+
39+
if (strlen(segmentName) && !mainseg.name) { //name is back to null
40+
notifierUdp.beginPacket(broadcastIp, udpPort);
41+
strcpy(segmentName,"");
42+
DEBUG_PRINTLN(F("UdpNameSync: sending Null name"));
43+
notifierUdp.write( udpOut , 2);
44+
notifierUdp.endPacket();
45+
return;
46+
}
47+
48+
if (0 == strcmp(mainseg.name, segmentName)) return; //same name, do nothing
49+
50+
notifierUdp.beginPacket(broadcastIp, udpPort);
51+
DEBUG_PRINT(F("UdpNameSync: saving segment name "));
52+
DEBUG_PRINTLN(mainseg.name);
53+
byte length = strlen(mainseg.name);
54+
strlcpy(segmentName, mainseg.name, length+1);
55+
strlcpy((char *)&udpOut[1], segmentName, length+1);
56+
notifierUdp.write(udpOut, length + 2);
57+
notifierUdp.endPacket();
58+
DEBUG_PRINT(F("UdpNameSync: Sent segment name : "));
59+
DEBUG_PRINTLN(segmentName);
60+
}
61+
62+
bool onUdpPacket(uint8_t * payload, uint8_t len) override {
63+
DEBUG_PRINT(F("UdpNameSync: Received packet"));
64+
if (payload[0] != 2) return false;
65+
//else
66+
Segment& mainseg = strip.getMainSegment();
67+
mainseg.setName((char *)&payload[1]);
68+
DEBUG_PRINT(F("UdpNameSync: set segment name"));
69+
return true;
70+
}
71+
};
72+
73+
74+
// add more strings here to reduce flash memory usage
75+
const char UdpNameSync::_name[] PROGMEM = "UdpNameSync";
76+
const char UdpNameSync::_enabled[] PROGMEM = "enabled";
77+
78+
static UdpNameSync udp_name_sync;
79+
REGISTER_USERMOD(udp_name_sync);

wled00/fcn_declare.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -442,6 +442,7 @@ class Usermod {
442442
virtual void onMqttConnect(bool sessionPresent) {} // fired when MQTT connection is established (so usermod can subscribe)
443443
virtual bool onMqttMessage(char* topic, char* payload) { return false; } // fired upon MQTT message received (wled topic)
444444
virtual bool onEspNowMessage(uint8_t* sender, uint8_t* payload, uint8_t len) { return false; } // fired upon ESP-NOW message received
445+
virtual bool onUdpPacket(uint8_t* payload, uint8_t len) { return false; } //fired upon UDP packet received
445446
virtual void onUpdateBegin(bool) {} // fired prior to and after unsuccessful firmware update
446447
virtual void onStateChange(uint8_t mode) {} // fired upon WLED state change
447448
virtual uint16_t getId() {return USERMOD_ID_UNSPECIFIED;}
@@ -481,6 +482,7 @@ namespace UsermodManager {
481482
#ifndef WLED_DISABLE_ESPNOW
482483
bool onEspNowMessage(uint8_t* sender, uint8_t* payload, uint8_t len);
483484
#endif
485+
bool onUdpPacket(uint8_t* payload, uint8_t len);
484486
void onUpdateBegin(bool);
485487
void onStateChange(uint8_t);
486488
Usermod* lookup(uint16_t mod_id);

wled00/udp.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -557,6 +557,9 @@ void handleNotifications()
557557
return;
558558
}
559559

560+
// usermods hook can override processing
561+
if (UsermodManager::onUdpPacket(udpIn, packetSize)) return;
562+
560563
//wled notifier, ignore if realtime packets active
561564
if (udpIn[0] == 0 && !realtimeMode && receiveGroups)
562565
{

wled00/um_manager.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,10 @@ bool UsermodManager::onEspNowMessage(uint8_t* sender, uint8_t* payload, uint8_t
6868
return false;
6969
}
7070
#endif
71+
bool UsermodManager::onUdpPacket(uint8_t* payload, uint8_t len) {
72+
for (auto mod = _usermod_table_begin; mod < _usermod_table_end; ++mod) if ((*mod)->onUdpPacket(payload, len)) return true;
73+
return false;
74+
}
7175
void UsermodManager::onUpdateBegin(bool init) { for (auto mod = _usermod_table_begin; mod < _usermod_table_end; ++mod) (*mod)->onUpdateBegin(init); } // notify usermods that update is to begin
7276
void UsermodManager::onStateChange(uint8_t mode) { for (auto mod = _usermod_table_begin; mod < _usermod_table_end; ++mod) (*mod)->onStateChange(mode); } // notify usermods that WLED state changed
7377

0 commit comments

Comments
 (0)