Receiving DMX-512 Protocol with MicroPython
This guide provides the necessary MicroPython code and guidance to receive the DMX-512 lighting control protocol using a microcontroller running MicroPython. The provided solution leverages a dedicated MicroPython library for DMX reception, making the process straightforward.
Understanding the DMX-512 Protocol
The DMX-512 protocol is a standard for digital communication networks commonly used to control lighting and effects. Here are its key characteristics:
- Asynchronous Serial Protocol: DMX is transmitted as a stream of asynchronous serial data.
- Baud Rate: The data rate is fixed at 250,000 bits per second.
- Data Format: The data is sent as 8-bit data, with one start bit, and two stop bits (8N2).
- Physical Layer: DMX uses RS-485 differential signaling for its physical layer, which allows for robust communication over long distances.
- Packet Structure: A DMX packet consists of a “break” condition, a “mark-after-break,” a start code, and up to 512 bytes of channel data. Each byte represents a single DMX channel, with a value from 0 to 255.
Hardware Requirements
To receive DMX signals with a MicroPython-enabled microcontroller, you will need the following hardware:
- MicroPython-compatible board: A board like the Raspberry Pi Pico is an excellent choice due to its PIO (Programmable I/O) capabilities, which are well-suited for handling the timing-critical nature of DMX.
- RS-485 Transceiver: Since DMX uses RS-485 signaling, a transceiver IC (like the MAX485 or similar) is required to convert the differential signals from the DMX bus to the single-ended logic levels (0V and 3.3V/5V) that the microcontroller’s UART can understand.
- XLR Connectors: DMX commonly uses 3-pin or 5-pin XLR connectors. You will need a female XLR connector to receive the DMX input.
- Termination Resistor: A 120-ohm resistor should be placed across the Data+ and Data- lines at the end of the DMX chain to prevent signal reflections.
MicroPython DMX Library
A readily available MicroPython library simplifies DMX reception significantly. A notable example is the micropython-dmx512 library, specifically designed for the Raspberry Pi Pico. This library utilizes the Pico’s PIO to accurately capture the DMX signal without heavily burdening the main processor.
Installation
To use this library, you will need to copy the dmx512_rx.py file to your MicroPython board.
MicroPython Code for DMX Reception
Below is a complete MicroPython script demonstrating how to receive DMX data on a Raspberry Pi Pico. This example reads the values of the first three DMX channels (typically Red, Green, and Blue for an RGB fixture) and prints them to the console.
# main.py
from machine import Pin
from time import sleep
from dmx512_rx import DMX512_RX
import _thread
# --- Configuration ---
# GPIO Pin connected to the RO (Receiver Output) of the RS485 transceiver
DMX_PIN = 0
# --- Global Variables ---
dmx_in = None
dmx_data = bytearray(513) # DMX data buffer (including start code at index 0)
# --- DMX Reception Task (runs in a separate thread) ---
def dmx_reception_task():
global dmx_in
while True:
# The wait_for_new_packet() function will block until a new DMX packet is received
# It automatically handles the break, mark-after-break, and start code.
dmx_in.wait_for_new_packet()
new_data = dmx_in.get_data()
for i in range(len(new_data)):
dmx_data[i] = new_data[i]
# --- Main Program ---
if __name__ == '__main__':
# Initialize the DMX receiver on a PIO state machine
# The pin number for the DMX input and the PIO state machine number are specified here.
dmx_in = DMX512_RX(Pin(DMX_PIN))
# Start the DMX reception in a new thread
_thread.start_new_thread(dmx_reception_task, ())
# Main loop to process the received DMX data
while True:
try:
# DMX data for channels 1, 2, and 3 are at indices 1, 2, and 3 of the dmx_data bytearray
# (index 0 is the start code)
red_value = dmx_data[1]
green_value = dmx_data[2]
blue_value = dmx_data[3]
print(f"Received DMX - R: {red_value}, G: {green_value}, B: {blue_value}")
# Add your code here to control LEDs, motors, or other devices based on the DMX data
sleep(0.5) # Update every half a second
except KeyboardInterrupt:
# Stop the DMX reception task (optional, for clean exit)
break
print("DMX reception stopped.")
Note: The dmx512_rx.py library from the steven-geo/micropython-dmx512 GitHub repository must be present on your MicroPython board for this code to work.
This example demonstrates a basic but effective way to start receiving and utilizing DMX data in your MicroPython projects. The use of a dedicated library and threading allows for reliable DMX reception while keeping the main loop of your program free to handle other tasks.
