Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
c0d662a
Swap DMX output to also use esp_dmx
netmindz Jan 10, 2026
37732ca
Temp enable DMX Output in all builds
netmindz Jan 10, 2026
96d4489
WLED_GLOBAL needed for dmx field to prevent linker errors
netmindz Jan 10, 2026
84ce66f
ass ifdef for 8266
netmindz Jan 10, 2026
d40f0f6
Set output pin during init
netmindz Jan 10, 2026
7d3a673
Remove lazy init
netmindz Jan 10, 2026
d336b97
set output pin
netmindz Jan 10, 2026
576b628
Allow runtime config of DMX output pin
netmindz Jan 10, 2026
2f874cf
remove redundant code
netmindz Jan 10, 2026
034e4f5
register pin with PinManager
netmindz Jan 10, 2026
834c285
default output pin to -1
netmindz Jan 10, 2026
22aff94
move dmx definition back to original location
netmindz Jan 10, 2026
585d174
minor cleanup
netmindz Jan 10, 2026
7a910c8
minor cleanup, code style
netmindz Jan 10, 2026
5cdca58
Fix naming
netmindz Jan 11, 2026
48168ed
write data
netmindz Jan 11, 2026
93ef454
Swap DMX output to also use esp_dmx
netmindz Jan 10, 2026
cd08d6f
Temp enable DMX Output in all builds
netmindz Jan 10, 2026
c8ff292
WLED_GLOBAL needed for dmx field to prevent linker errors
netmindz Jan 10, 2026
b11c7f7
ass ifdef for 8266
netmindz Jan 10, 2026
d5061ed
Set output pin during init
netmindz Jan 10, 2026
1ccef16
Remove lazy init
netmindz Jan 10, 2026
4a60207
set output pin
netmindz Jan 10, 2026
3b92b2d
Allow runtime config of DMX output pin
netmindz Jan 10, 2026
ec64355
remove redundant code
netmindz Jan 10, 2026
02274e1
register pin with PinManager
netmindz Jan 10, 2026
b8fcb1c
default output pin to -1
netmindz Jan 10, 2026
306ba83
move dmx definition back to original location
netmindz Jan 10, 2026
f5522e6
minor cleanup
netmindz Jan 10, 2026
38330b5
minor cleanup, code style
netmindz Jan 10, 2026
daa2223
Fix naming
netmindz Jan 11, 2026
e28774d
write data
netmindz Jan 11, 2026
c20f59d
DMXInput: try to assign pins before UART port and default back to 1 i…
netmindz Mar 20, 2026
ea3aba9
DMXInput: No need to swap default pin for LED when DMX not hard-coded
netmindz Mar 20, 2026
ab632e9
DMXInput: Move allocation of pin to initDMXOutput
netmindz Mar 20, 2026
cf1f236
Merge remote-tracking branch 'netmindz/dmx-output-esp_dmx' into dmx-o…
netmindz Mar 20, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions platformio.ini
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@ build_flags =
-D DECODE_LG=true
-DWLED_USE_MY_CONFIG
-D WLED_PS_DONT_REPLACE_FX ; PS replacement FX are purely a flash memory saving feature, do not replace classic FX until we run out of flash
-D WLED_ENABLE_DMX
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Todo: remove before merge


build_unflags =

Expand Down
6 changes: 6 additions & 0 deletions wled00/cfg.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -607,6 +607,9 @@ bool deserializeConfig(JsonObject doc, bool fromFS) {
tdd = if_live[F("timeout")] | -1;
if (tdd >= 0) realtimeTimeoutMs = tdd * 100;

#ifdef WLED_ENABLE_DMX
CJSON(dmxOutputPin, if_live_dmx[F("dmxOutputPin")]);
#endif
#ifdef WLED_ENABLE_DMX_INPUT
CJSON(dmxInputTransmitPin, if_live_dmx[F("inputRxPin")]);
CJSON(dmxInputReceivePin, if_live_dmx[F("inputTxPin")]);
Expand Down Expand Up @@ -1133,6 +1136,9 @@ void serializeConfig(JsonObject root) {
if_live_dmx[F("addr")] = DMXAddress;
if_live_dmx[F("dss")] = DMXSegmentSpacing;
if_live_dmx["mode"] = DMXMode;
#ifdef WLED_ENABLE_DMX
if_live_dmx[F("dmxOutputPin")] = dmxOutputPin;
#endif
#ifdef WLED_ENABLE_DMX_INPUT
if_live_dmx[F("inputRxPin")] = dmxInputTransmitPin;
if_live_dmx[F("inputTxPin")] = dmxInputReceivePin;
Expand Down
7 changes: 1 addition & 6 deletions wled00/const.h
Original file line number Diff line number Diff line change
Expand Up @@ -650,13 +650,8 @@ static_assert(WLED_MAX_BUSSES <= 32, "WLED_MAX_BUSSES exceeds hard limit");

// Defaults pins, type and counts to configure LED output
#if defined(ESP8266) || defined(CONFIG_IDF_TARGET_ESP32C3)
#ifdef WLED_ENABLE_DMX
#define DEFAULT_LED_PIN 1
#warning "Compiling with DMX. The default LED pin has been changed to pin 1."
#else
#define DEFAULT_LED_PIN 2 // GPIO2 (D4) on Wemos D1 mini compatible boards, safe to use on any board
#endif
#else
#else
#if defined(WLED_USE_ETHERNET)
#define DEFAULT_LED_PIN 4 // GPIO4 seems to be a "safe bet" for all known ethernet boards (issue #5155)
//#warning "Compiling with Ethernet support. The default LED pin has been changed to pin 4."
Expand Down
11 changes: 9 additions & 2 deletions wled00/data/settings_sync.htm
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,10 @@
}
function hideDMXInput(){gId("dmxInput").style.display="none";}
function hideNoDMXInput(){gId("dmxInputOff").style.display="none";}
function hideNoDMXOutput(){gId("dmxOnOffOutput").style.display="none";}
function hideNoDMXOutput(){
gId("dmxOnOffOutput").style.display="none";
gId("dmxOutput").style.display="inline";
}
</script>
</head>
<body>
Expand Down Expand Up @@ -179,7 +182,11 @@ <h4>Wired DMX Input Pins</h4>
DMX TX: <input name="IDMT" type="number" min="-1" max="99">DI<br/>
DMX Enable: <input name="IDME" type="number" min="-1" max="99">RE+DE<br/>
DMX Port: <input name="IDMP" type="number" min="1" max="2"><br/>
</div>
</div>
<div id="dmxOutput" style="display: none">
<h4>Wired DMX Output Pin</h4>
DMX TX: <input name="IDMO" type="number" min="-1" max="99"><br/>
</div>
<div id="dmxInputOff">
<br><i class="warn">This firmware build does not include DMX Input support. <br></i>
</div>
Expand Down
17 changes: 9 additions & 8 deletions wled00/dmx_input.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -134,14 +134,6 @@ void DMXInput::init(uint8_t rxPin, uint8_t txPin, uint8_t enPin, uint8_t inputPo
// }
#endif

if (inputPortNum <= (SOC_UART_NUM - 1) && inputPortNum > 0) {
this->inputPortNum = inputPortNum;
}
else {
DEBUG_PRINTF("DMXInput: Error: invalid inputPortNum: %d\n", inputPortNum);
return;
}

if (rxPin > 0 && enPin > 0 && txPin > 0) {

const managed_pin_type pins[] = {
Expand All @@ -156,6 +148,15 @@ void DMXInput::init(uint8_t rxPin, uint8_t txPin, uint8_t enPin, uint8_t inputPo
DEBUG_PRINTF("en in use by: %s\n", PinManager::getPinOwner(enPin));
return;
}
if (inputPortNum <= (SOC_UART_NUM - 1) && inputPortNum > 0) {
this->inputPortNum = inputPortNum;
}
else {
DEBUG_PRINTF("DMXInput: Error: invalid inputPortNum: %d, default to 1\n", inputPortNum);
this->inputPortNum = 1;
return;
}


this->rxPin = rxPin;
this->txPin = txPin;
Expand Down
49 changes: 38 additions & 11 deletions wled00/dmx_output.cpp
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
#include "wled.h"

#include "dmx_output.h"
/*
* Support for DMX output via serial (e.g. MAX485).
* Change the output pin in src/dependencies/ESPDMX.cpp, if needed (ESP8266)
* Change the output pin in src/dependencies/SparkFunDMX.cpp, if needed (ESP32)
* Support for DMX output via serial (e.g. MAX485).
* ESP8266 Library from:
* https://github.com/Rickgg/ESP-Dmx
* ESP32 Library from:
* https://github.com/sparkfun/SparkFunDMX
* https://github.com/someweisguy/esp_dmx
*/

#ifdef WLED_ENABLE_DMX
Expand Down Expand Up @@ -68,13 +66,42 @@ void handleDMXOutput()
dmx.update(); // update the DMX bus
}

void initDMXOutput() {
#if defined(ESP8266) || defined(CONFIG_IDF_TARGET_ESP32C3) || defined(CONFIG_IDF_TARGET_ESP32S2)
dmx.init(512); // initialize with bus length
#else
dmx.initWrite(512); // initialize with bus length
#endif
void initDMXOutput(int outputPin) {
if (outputPin < 1) return;
const bool pinAllocated = PinManager::allocatePin(outputPin, true, PinOwner::DMX);
if (!pinAllocated) {
DEBUG_PRINTF("DMXOutput: Error: Failed to allocate pin for DMX_OUTPUT. Pin already in use:\n");
DEBUG_PRINTF("In use by: %s\n", PinManager::getPinOwner(outputPin));
return;
}
DEBUG_PRINTF("DMXOutput: init: pin %d\n", outputPin);
dmx.init(outputPin); // set output pin and initialize DMX output
}

#if !defined(ESP8266)
void DMXOutput::init(uint8_t outputPin) {
dmx_config_t config = DMX_CONFIG_DEFAULT;
const bool installOk = dmx_driver_install(dmxPort, &config, DMX_INTR_FLAGS_DEFAULT);
if (!installOk) {
DEBUG_PRINTF("DMXOutput: Error: Failed to install dmx driver\n");
return;
}
const bool setPin = dmx_set_pin(dmxPort, outputPin, -1, -1);
if (!setPin) {
DEBUG_PRINTF("DMXOutput: Error: Failed to set DMX output pin\n");
return;
}
}
void DMXOutput::write(uint8_t channel, uint8_t value) {
dmxdata[channel] = value;
}
void DMXOutput::update() {
dmx_write(dmxPort, dmxdata, DMX_PACKET_SIZE);
dmx_send(dmxPort, DMX_PACKET_SIZE);
}
#endif


#else
void initDMXOutput(){}
void handleDMXOutput() {}
Expand Down
33 changes: 33 additions & 0 deletions wled00/dmx_output.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
//
// Created by will on 1/10/26.
//

#ifndef DMX_OUTPUT_H
#define DMX_OUTPUT_H

#if defined(ESP8266)
#include "src/dependencies/dmx/ESPDMX.h"
#else
#include <esp_dmx.h>
/**
* Support for DMX Output via serial (e.g. max485) on ESP32
* ESP32 Library from:
* https://github.com/someweisguy/esp_dmx
*/
class DMXOutput
{
public:
void init(uint8_t outputPin);
void write(uint8_t channel, uint8_t value);
void update();
private:
byte dmxdata[DMX_PACKET_SIZE];
/* Next, lets decide which DMX port to use. The ESP32 has either 2 or 3 ports.
Port 0 is typically used to transmit serial data back to your Serial Monitor,
so we shouldn't use that port. Lets use port 1! */
dmx_port_t dmxPort = 1;
};
#endif


#endif //DMX_OUTPUT_H
2 changes: 1 addition & 1 deletion wled00/fcn_declare.h
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ typedef struct WiFiConfig {
} wifi_config;

//dmx_output.cpp
void initDMXOutput();
void initDMXOutput(int outputPin);
void handleDMXOutput();

//dmx_input.cpp
Expand Down
3 changes: 2 additions & 1 deletion wled00/pin_manager.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,11 +43,12 @@ enum struct PinOwner : uint8_t {
Relay = 0x87, // 'Rly' == Relay pin from configuration
SPI_RAM = 0x88, // 'SpiR' == SPI RAM
DebugOut = 0x89, // 'Dbg' == debug output always IO1
DMX = 0x8A, // 'DMX' == hard-coded to IO2
DMX = 0x8A, // 'DMX' == DMX output via serial
HW_I2C = 0x8B, // 'I2C' == hardware I2C pins (4&5 on ESP8266, 21&22 on ESP32)
HW_SPI = 0x8C, // 'SPI' == hardware (V)SPI pins (13,14&15 on ESP8266, 5,18&23 on ESP32)
DMX_INPUT = 0x8D, // 'DMX_INPUT' == DMX input via serial
HUB75 = 0x8E, // 'Hub75' == Hub75 driver
DMX_OUTPUT = 0x8F, // 'DMX_OUTPUT' == DMX output via serial
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Todo: clean up

// Use UserMod IDs from const.h here
UM_Unspecified = USERMOD_ID_UNSPECIFIED, // 0x01
UM_Example = USERMOD_ID_EXAMPLE, // 0x02 // Usermod "usermod_v2_example.h"
Expand Down
4 changes: 3 additions & 1 deletion wled00/set.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -473,7 +473,9 @@ void handleSettingsSet(AsyncWebServerRequest *request, byte subPage)
arlsDisableGammaCorrection = request->hasArg(F("RG"));
t = request->arg(F("WO")).toInt();
if (t >= -255 && t <= 255) arlsOffset = t;

#ifdef WLED_ENABLE_DMX
dmxOutputPin = request->arg(F("IDMO")).toInt();
#endif
#ifdef WLED_ENABLE_DMX_INPUT
dmxInputTransmitPin = request->arg(F("IDMT")).toInt();
dmxInputReceivePin = request->arg(F("IDMR")).toInt();
Expand Down
49 changes: 2 additions & 47 deletions wled00/src/dependencies/dmx/ESPDMX.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,62 +18,19 @@
#include "ESPDMX.h"



#define dmxMaxChannel 512
#define defaultMax 32

#define DMXSPEED 250000
#define DMXFORMAT SERIAL_8N2
#define BREAKSPEED 83333
#define BREAKFORMAT SERIAL_8N1

bool dmxStarted = false;
int sendPin = 2; //default on ESP8266

//DMX value array and size. Entry 0 will hold startbyte, so we need 512+1 elements
uint8_t dmxDataStore[dmxMaxChannel+1] = {};
int channelSize;


void DMXESPSerial::init() {
void DMXESPSerial::init(int sendPin) {
this->sendPin = sendPin;
channelSize = defaultMax;

Serial1.begin(DMXSPEED);
pinMode(sendPin, OUTPUT);
dmxStarted = true;
}

// Set up the DMX-Protocol
void DMXESPSerial::init(int chanQuant) {

if (chanQuant > dmxMaxChannel || chanQuant <= 0) {
chanQuant = defaultMax;
}

channelSize = chanQuant;

Serial1.begin(DMXSPEED);
pinMode(sendPin, OUTPUT);
dmxStarted = true;
}

// Function to read DMX data
uint8_t DMXESPSerial::read(int Channel) {
if (dmxStarted == false) init();

if (Channel < 1) Channel = 1;
if (Channel > dmxMaxChannel) Channel = dmxMaxChannel;
return(dmxDataStore[Channel]);
}

// Function to send DMX data
void DMXESPSerial::write(int Channel, uint8_t value) {
if (dmxStarted == false) init();

if (Channel < 1) Channel = 1;
if (Channel > channelSize) Channel = channelSize;
if (value < 0) value = 0;
if (value > 255) value = 255;

dmxDataStore[Channel] = value;
}
Expand All @@ -85,8 +42,6 @@ void DMXESPSerial::end() {
}

void DMXESPSerial::update() {
if (dmxStarted == false) init();

//Send break
digitalWrite(sendPin, HIGH);
Serial1.begin(BREAKSPEED, BREAKFORMAT);
Expand Down
20 changes: 18 additions & 2 deletions wled00/src/dependencies/dmx/ESPDMX.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,16 +16,32 @@
#ifndef ESPDMX_h
#define ESPDMX_h


#define dmxMaxChannel 512
#define defaultMax 32

#define DMXSPEED 250000
#define DMXFORMAT SERIAL_8N2
#define BREAKSPEED 83333
#define BREAKFORMAT SERIAL_8N1

// ---- Methods ----

class DMXESPSerial {
public:
void init();
void init(int MaxChan);
void init(int sendPin);
uint8_t read(int Channel);
void write(int channel, uint8_t value);
void update();
void end();
private:
int sendPin;
bool dmxStarted = false;

//DMX value array and size. Entry 0 will hold startbyte, so we need 512+1 elements
uint8_t dmxDataStore[dmxMaxChannel+1] = {};
int channelSize;

};

#endif
Loading
Loading