One of my favorite things about electronics is LEDs (Light Emitting Diode). LEDs have many uses from providing a simple output for your circuit or just creating vibrant beautiful colors to please your eye. With this love for the simple LED, I always enjoy building projects that involve some kind of LED output or display, even if it’s just some a blinking light!
Last winter, I decided to try messing around with RGB LEDs with integrated driver chips. These LEDs have some benefits over traditional RGB LEDs, making them very powerful in designs. In a traditional RGB LED, there is typically three separate LEDs, representing red, green, and blue, connected through a common anode or cathode. By controlling the currents of the three LED’s, you are able to create different colors based on your hardware. Traditionally in an Arduino you would use 3 8 bit PWM (Pulse Width Modulation) channels to vary the duty cycle, which would vary the voltage and current with 8 bit resolution. If you are interested in reading more on driving RGB LEDs with Arduino, Adafruit provides a good tutorial here. If you don’t have 3 spare PWM channels available or external hardware for your microcontroller, you will have an issue driving the traditional RGB led.
Another issue with traditional RGB LEDs is the hardware complexity of driving large quantities. If you would like to create an RGB LED array or cube, it would take 3 analog pins an LED if you would like to drive it the standard way! While nobody really drives LED arrays with 3 unique pins per LED, other methods like multiplexing still require a vast amount of pins and driving hardware.
While traditional RGB LEDs require analog driving to utilize the full potential of creating different colors and the use of many pins, these integrated driver ones do not. These LEDs package the required analog driving hardware for you, only requiring a single digital input! This is what makes them amazing!
Above, the diagram represents the pin out of the PL9823, which is the LED I decided to purchase. The PL9823 is considered a clone of the “WS2812” which is known as the original integrated driver RGB LED. The PL9823 like the other LEDs has 4 Pins: Ground, Power. Data In, and Data Out. So how does one send data?
It was stated earlier that these LEDs contain the RGB analog driving hardware, allowing you to avoid the headache of creating separate hardware. Additionally these LEDs also contain 24 bits of shift registers which run on an asynchronous clock, this is how the LED can send and receive it’s data. Typically in an embedded system circuit, peripherals that send and receive data are usually connected through synchronous buses like SPI or I2C. These standards require the master to send a data signal with an additionally clock signal so the slave can receive, read the data properly. In an asynchronous system, like UART, the master does not send a clock. In these systems, the master and slave device both generate a clock, timing system that runs internally for reading and transmitting data. A big issue with asynchronous systems is, if a device is slightly off the required timing, the data transmission can contain imperfections causing disastrous issues. Luckily for this application, the timing can allow for some errors.
Since the LEDs run on an asynchronous clock, the shift register system uses an interesting timing based protocol for determining if the bit sent is a 0 or 1. Below is an image of the timing and protocol used with these LEDs.
As you can see for both a logic ‘1’ and logic ‘0’, the master must send high and low pulses for the driver chip to properly read the data. For a logic ‘1’ the system must first send a long high pulse followed by a short low pulse, for a logic ‘0’ this is reversed where a short high pulse is sent followed by a long low pulse. Additionally when the data is held low for more than 50 us, the device is reset. When the device is reset, the device begins to read the 24 bits of data and then all bits after the first 24 are sent to the next LED through the Data out pin. Once the next reset is called, all data is read from the internal buff, where the previous data is stored, and sent to the PWM drivers (cpldcpu.com).
Overall, this protocol is pretty simple and can be implemented using any microcontroller through “bit banging”, as long as the main clock isn’t too slow.
While you can implement your own code for controlling these LEDs, people in the community have already created some working libraries for Arduino and AVR, both which I have used. Adafruit created for their Neopixel line a set of libraries which can be found here. Additionally Tim from cpldcpu.com created libraries for both AVR and Arduino, both which I used for all my projects involving PL9823 LEDs. His blog can be found here, where he goes into an interesting analyses of the timing of the ws2812 LEDs. He also has other posts on clone LEDs like the PL9823. This blog was a good reference in creating this post and for helping my understanding of the integrated driver RGB LEDs.
Hopefully this post has given you a good look into the PL9823 and other integrated driver RGB LEDs. I was originally going to post documentation for a project involving the PL9823 but ended up writing enough background information leading to the creation of this post. These LEDs are neat and I can’t wait to share some of my work with them! For now enjoy this demo running on an ATtiny85.