The LCC Lighting Controller Board is an OpenLCB (LCC) node designed for controlling RGBW NeoPixel LED strips on model railroads. The system uses a controller/follower architecture where one controller board reads analog inputs (potentiometers) via an ADS1115 ADC and broadcasts RGBW values over the LCC bus, while multiple follower boards receive these events and synchronize their LED strips accordingly. You can also set up multiple follower boards with a different board as the controller, for example the LCC Lighting Touchscreen Controller
The end result would be to have strings of LEDs as fully-customizable overhead lighting integrated into your LCC system. This opens up opportunities for custom scenes, rolling weather systems, and accurate sunsets/sunrises timed with a fast clock.
- RGBW Control: Independent control of Red, Green, Blue, White channels plus overall brightness
- Controller/Follower Architecture: One controller can synchronize multiple follower boards
- Automatic Detection: Boards automatically detect if they have an ADS1115 ADC and configure as controller or follower
- Wide LED Compatibility: Uses the NeoPixelBus library, supporting a wide range of addressable LED chips including WS2812, WS2812B, WS2811, SK6812 RGBW, WS2814 RGBWW. This is superior to teh previously utilized Adafruit neopixel library as it uses DMA to drive the LEDs, significantly reducing glitching and timing constraints on the ESP32 hardware
- Configurable LED Count: Support for strips up to 1000 LEDs
- Startup Animation: Configurable fade-in animation with adjustable delay for LCC bus settling
- Periodic Sync: Controller periodically broadcasts state to keep followers synchronized
⚠️ Version Constraint: Currently limited to using Arduino ESP Core v3.2.1, as the NeoPixelBus library has a dependency on gpio_hal_iomux_func_sel which is not present in later versions. Will hopefully be resolved in later releases
The LCC Lighting Controller Board must be powered from an external power supply (12V) on the J1 connector, do not attempt to use the OpenLCB (LCC) Bus power via the RJ45 connector as it will not supply enough power for any reasonably long string of LEDs.
The external power supply should be rated for at least 12VDC 500mA to ensure sufficient current is available for the node to operate as intended. For longer LED strips, a higher current power supply may be required.
If the ESP32 detects a brownout condition it will attempt to produce event 01.00.00.00.00.00.FF.F1 soon after startup. This delivery is not guaranteed.
The LCC Lighting Controller Board PCB can be found under the PCB directory and is provided as both KiCad files and generated Gerber files.
The LCC Lighting Controller PCB has been shared via PCBWay:
TODO: Add PCBWay Project link
The LCC Lighting Controller Board components have been entered on Mouser for easy ordering via the following shared carts:
TODO: Add shared carts
Ordering in larger quantities can decrease the per-PCB cost considerably. In the case of resistors and capacitors it is recommended to order 100 of each as they are tiny and easily lost. Other parts can often be substituted as long as they have the same footprint and pinout.
You can find the Fusion 360 archive and 3MF files for a 3D-printable stand-off/spacer type mount in the Mount directory. This will allow for easy mounting of the Lighting Controller using self-tapping screws to the underside of any layout or a dedicated plywood electronics board. The Fusion 360 files can also be modified for your application, or used to create printable paper templates to transfer the mounting hole spacing of the board.
The Lighting Controller must be plugged into an active LCC bus in order to be configured. The boards have been tested with a TCS CS-105 base station connected to a Raspberry Pi running JMRI.
Upon plugging in the Lighting Controller, you should see the entry for that device's address appear in the OpenLCB Network list:
Clicking on the board in the OpenLCB Network list expands the entry to show an "Open Configuration Dialog" option. Clicking that opens a separate window where you can adjust:
- Description: User-friendly name for the light strip
- Red/Green/Blue/White Channel Events: Event ID bases for each color channel. Keep them at their default values for Controller boards. For Follower boards change them to match the events emitted by the Controller.
- Brightness Event: Event ID base for overall brightness control. Same guidelines apply here as the RGBW channel events.
- Duration Event: Event ID base for duration of the transition from current rgbw scene parameters to newly transmitted scene. Same guidelines apply her as with the RGBW channel events.
- LED Count: Number of LEDs in your NeoPixel strip (1-1000)
- Sync Interval: How often the controller broadcasts state to followers (0-60 seconds)
- Startup Delay: Delay before fade-in animation starts (0-30 seconds). This is helpful to allow the startup traffic on the LCC bus to die down before sending a block of lighting commands during the fade-on animation. Otherwise, receiving frequent external events on the Controller board can interrupt the neopixel commands, which may result in green glitching along the LED strip.
- Controller Board: Install the ADS1115 ADC and connect potentiometers to control RGBW values. The board automatically detects the ADC and operates as a controller.

- Follower Board: Do not install the ADS1115 ADC [U2 on the PCB]. The board will automatically operate as a follower, receiving RGBW events from the controller.

Ensure all boards sharing the same LED strip colors use matching Event ID bases for each channel.
Events are transmitted to control RGBW lighting nodes using a Duration-Triggered Fade Protocol. The Controller (or touchscreen) sends target values and transition duration; Follower boards perform local high-fidelity fading at ~60fps.
05.01.01.01.9F.60.0X.VV
│ └── Value (0-255)
└───── Parameter
| Parameter | X | Description |
|---|---|---|
| Red | 0 | Red channel target intensity |
| Green | 1 | Green channel target intensity |
| Blue | 2 | Blue channel target intensity |
| White | 3 | White channel target intensity |
| Brightness | 4 | Master brightness target |
| Duration | 5 | Fade time in seconds (0=instant) |
- Controller sends 6 events: R, G, B, W, Brightness, Duration
- Followers store R, G, B, W, Brightness as pending values
- Duration event triggers the fade from current to pending values
- Local interpolation runs at ~60fps on Followers
- Minimal bus traffic: Only 6 events per scene change
This project borrows heavily from Mike Dunston's ESP32 OpenLCB IO Board for the PCB design: https://github.com/atanisoft/Esp32OlcbIO
A lot of the code is based on Robert Heller's ESP32 LCC examples: https://github.com/RobertPHeller/ESP32-LCC
Directly uses OpenMRNLite which is maintained by Balazs Racz and Stewart Baker: https://github.com/openmrn/OpenMRNLite




