I’ve been building a cube recently:
It’s built from 64 programmable LEDs (in a 4x4x4 lattice), that I can control with a serial signal from a 16MHz Arduino. More specifically, these are APA106 LEDs, which have a chip embedded inside them that decodes the signal and outputs the programmed colour levels to the LED. They take a 3-byte RGB signal, which in theory means 16,777,216 possible colours (although your eyes can only see around 10 million).
Each LED has four wires: Data out, GND, +5V, Data in (left to right in the picture above). The 5V supply and ground pins are the main power source, and the 64 LEDs in the cube are connected to the supply in parallel. The Data in and Data out pins, however, run in series through the whole string of LEDs – the first LED’s Data out pin connects to the second LED’s Data in, and so on. Only the first LED in the sequence gets a signal from the Arduino, and once it has received its colour it propagates the rest of the serial signal on to the LED after it. Because all of the LEDs work this way, you can just send a sequence like R1,G1,B1,R2,G2,B2,R3,G3,B3,… to update all of the LEDs at once.
In the video above, all 64 LEDs in the cube are being updated 20 times per second. For parts of it, you can see a rainbow pattern weaving its way through each of the LEDs in turn. The order in which the LEDs turn on/off there is the order in which the data pins of the LEDs are connected to each other.
At maximum brightness, each LED draws about 60mA of power at 5V, meaning that the whole cube draws 3.84A. Most USB ports and phone chargers only supply one or two amps, so here I’m using a separate 5V 10A power supply. The Arduino is still powered over USB, so to connect the data wire safely I had to also connect the two ground wires together, but not the 5V.
The timing on the signal needs to be fairly precise, according to the APA106 datasheet the smallest time between signal changes is 350ns with an error of up to ±150ns. Initially, I tried to do this from a Raspberry Pi’s GPIO pins, but my program would always get interrupted in the middle of sending the signal, so I had to use an Arduino instead. I adapted some signal sending code for a similar type of LED I found online, which disables interrupts and uses assembly code for instruction level timing based on the fact that the processor runs at 16MHz.
In order to write visualisations in a higher level language than Arduino C, I wrote a very simple Arduino program that listens for data on USB and forwards it to the LEDs with the correct timing. The USB signal has a maximum baud rate of 115200, meaning that I can send a maximum of 115200/(64x3x8)=75 updates per second to the whole set of 64 LEDs. In practise, I’m only sending 20 per second.
To send those signals and generate interesting patterns, I’ve written some Python programs that run on a Raspberry Pi, which the Arduino is plugged into. These programs generate one frame after another and send them to the Arduino at 0.05 second intervals.
You can find the code, including Python visualisations and the Arduino LED controller, on my GitHub here: https://github.com/abryant/LED-Cube
Some of the visualisations I’ve written so far are:
- A rainbow filling up the cube in LED order.
- Blocks of colour scrolling past in different directions.
- One face of the cube rotating to become another face and changing colour.
- A 3D game of snake.
- Tetris blocks falling in random places until they reach the top.
- Pulsing the whole cube in different colours.
- Falling green lights (matrix-style).
- A rotating 3D colour wheel.
- 3 different coloured snakes all avoiding each other.
You can see some more photos and videos here:
https://photos.app.goo.gl/b63fNjHddFoOuM0C2
Unfortunately, some of these don’t work very well because the cube is so small. 4x4x4 isn’t enough to display much detail, for example you can’t display text on it. To remedy that, I’ve started building an 8x8x8 cube with 512 LEDs. Hopefully I’ll put up some more detailed blog posts about the construction and soldering as I go.
Tim Jacobs would love this. He’s a tinkerer who did physics at Imperial. mitxela.com
Hello Anthony,
thanks again for your support by realising my 8x8x8 Cube.
Yesterday i finished it. Great, I´m excited.
Now im going to learn python and program some effects.
That’s awesome that you finished it! How was it to build? and have you written any more effects?
(I should check these comments more often…)