Introduction: Make Your Own TV Ambilight Using Arduino

Picture of Make Your Own TV Ambilight Using Arduino

This is a very easy project.

I won't go into too much detail how each part works, because I have written some information on my blog.

But you should be able to make it work with the information given on this instructable.

Here is the result

Step 1: Prepare RGB LED Strip

Picture of Prepare RGB LED Strip

The RGB LEDs came as a strip, but I want them to be separated further, so I soldered wires in between. I also use hot glue to strengthen the soldering points.

you could buy led strips that have long cables, or you can just use this out of the box, it's up to you.

I am using 25 LEDs.

Step 2: Mount LED Strip on TV

Picture of Mount LED Strip on TV

My example is a bad one. you should be more accurate about the LED positions. and the should be facing outward with a angle, so the Lights can be seen brighter from the front.

The sketch is how the LEDs should be mounted on the TV.

Step 3: The Connection (Arduino, Power)

Picture of The Connection (Arduino, Power)

The good thing about these LED strip is, it only requires one data connection from the Arduino.

You have to use external power source. I am using a 5V 2A power adapter for this.

Note: GND of the power source should be connected to the Arduino GND.

Step 4: Finally the Source Code

Just copy these source code and you are good to go

I use Processing on the computer


Cramery (author)2016-12-20

Where did you get the code from? BC when I add it to the arduino, nothing happens. The last programm which was on the arduino just stops working

William K Rod (author)2016-04-07

Can you show me exacly how to mount my led strip to arduino?

snorkpants (author)2016-03-30

I had a lot of trouble getting the processing code to talk to the arduino until I checked the properties of the COM port and found that the speed was set to 9600. As soon as I changed it to 115200 it all started working..

Hope that helps someone :)

Oliviero3 (author)2016-03-11

I have the same problem

AnonT (author)2015-11-10

I know this post is a bit old but I'm trying to follow this and having some issues compiling the provided processing code.

When I try and compile the code (even bone stock) I get an error "Found one too many { characters without a } to match it."

I've been looking through the code and trying to figure out where the missing bracket goes but I'm not having any luck. Is anyone / everyone else having that same problem with the source code provided?

Can anyone help debug this and shed some light on where the elusive bracket needs to go?

I tried the code provided in the comments below and it seems to work until I activate the serial port to try it with my arduino. Then the window that should show the border color launches but ends up not responding.

Conradv1 (author)2015-05-09

The graphical representation works fine but the Neopixel stay off. Datapin is the right one. Seems like there is something wrong with the communication :(

TomažN (author)2015-04-07

I feel as though the program processing is not working properly. Does anyone have a matter that work? I would ask that we send this file. thank you

TomažN (author)2015-04-07

I use a macbook air. I have a problem that processing does not want to run a single LEDs. I always change the port between 0 and 3, and after 10 attempts, the LED lights light up but not always. What would cause this?

TomažN (author)2015-03-01


I have one problem. The red color is green and purple is light blue. how to fix this?

Mr.Yourself (author)TomažN2015-03-05

Just change this line:

Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LED, PIN, NEO_GRB + NEO_KHZ800);


Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LED, PIN, NEO_RGB + NEO_KHZ800);

Mr.Yourself (author)2015-02-24

Hi everybody,

thanks for good idea how to improve home entertainment. Everything works
well (for now only with 8pcs of 2812 for testing) I already ordered
strip with 150 pcs of these LEDs. As I know that to drive every LED
separatelly would take amount of PC capacity, I tried to change Arduino
code to send every incoming byte to 3 neighbouring LEDs. (in the
processing I would use just 50 rectangles) Is anybody able to check what
I have done wrong? I copied here only the part which I changed against original code. (With this program I can not light up more than 50
LEDs. Is the limit the line with “#define NUM_LED 50″ ? When I change it
to 150, Arduino expect bytes for 150 LEDs and receive only 50. Thanks.


for (int i = 0; i < (3 * NUM_LED); i++) {
int led_index = i * 3 + 2;
strip.setPixelColor(i, strip.Color(led_color[led_index], led_color[led_index + 1], led_color[led_index + 2]));
strip.setPixelColor(i, strip.Color(led_color[led_index], led_color[led_index + 1], led_color[led_index + 2]));
strip.setPixelColor(i, strip.Color(led_color[led_index], led_color[led_index + 1], led_color[led_index + 2]));


seb_168 made it! (author)2014-10-19

I made it and it works perfectly, thanks you. But i'm thinking about using c# instead of processing for better performances. If someone already test this ..?

jajunkie (author)seb_1682014-12-03

i can not figure out what i am doing wrong. i get the processing code to run and it changes colors as needed in the java window. i can also get the arduino code loaded and the ozy reply but i do not get any lights changing. all the leds just turn blue and thats it. i am running the apa104 60 led strip. if anyone can help that would be great.

jajunkie (author)jajunkie2014-12-04

when i look at the serial monitor it just says ozy and keeps repeating 'y'.

zootalaws (author)seb_1682014-10-22

Did you make it using the exact code here, or did you have to rewrite it?

seb168 (author)zootalaws2014-10-23

I used the code here, I just change values and 1 or 2 lines

zootalaws (author)seb_1682014-10-20

Seb, Do you want to post both bits of code that you used?

I get intermittent results, some times, but have never gotten it to work properly.

mat.tripp (author)2014-11-28

Hi i am struggling a little with processing.

how do specify which monitor to measure ?

and how to specify what com port to use?


mat.tripp (author)2014-11-28

Hi i am struggling a little with processing.

how do specify which monitor to measure ?

and how to specify what com port to use?


seb168 (author)2014-10-22

Sure :

zootalaws (author)seb1682014-10-22

i am lost - it loads without error, if I look at the serial monitor I get 'ozy', but when I launch Processing, it just sits there with a 'blank' screen.

I guess it might be because I am on a Mac.

seb168 (author)zootalaws2014-10-23

I had this problem too, check your java version etc..

On windows I used the 32bits version of processing to get it works

zootalaws (author)seb1682014-10-23

Brilliant suggestion!

It wasn't Java, but was some java libraries inside Processing. Copied the ones from Arduino to Processing and it worked first time!

Thanks for the code and your hint!

zootalaws (author)seb1682014-10-23

OK - that makes sense. I downgraded to Arduino 1.0.6 for another problem which was caused by a timing issue in the compiler.

Thanks Seb, I will investigate further.

zootalaws (author)seb1682014-10-22

Great, thanks.

reducingmyconsumption made it! (author)2014-06-27

I made this using WS2801 LEDs (pictured below) because they were much cheaper than WS2811/ WS2812, they came pre-wired (but this limits the size of your TV to around 32") and the performance is exactly the same.

The only thing that I would change in your build is the processing software. I used ambibox 2.1.4 instead of processing because it allows greater customisation and has a lot of extra features. It allows multiple profiles for different aspect ratios which is important when watching movies, it can react to sound instead of screen captures for when you're browsing the web (rather that projecting boring website colours onto your wall) plus you can change saturation and brightness which allows you to fine tune it to suit your rooms wall colour and it's much easier to use than processing!

Thanks for posting this, you inspired me to build my amblight build a few moths ago and I absolutely love it.

I didn't know you can get this type of LED, well done on your build! :-D

zootalaws (author)lacglzh2014-10-20

You can get 'xmas lights' of 50 WS2811 LEDs for about $12. Saves a lot of soldering!

I am trying to get your apps working without much luck. I'm not much of a programmer, but I can fumble through. I mapped out the LED layout in Excel but am confused about x and y numbers and 0,0.

In your code, you say you have (for 25 LEDs) 10 x 6. but for me, that makes 32 LEDs - 10 across the top, 6 on the sides x 2.

So top left is 0,0, left side is 0 column, is the top left LED counted in both top and left column?

Regardless - I can't get the two halves to fire. I am confident they are exactly as you had in your example, with the port setup for my comm port setup - I can see the oxy in the Arduino serial monitor if I use that, but the LEDs just all stay lit white. It's like it never gets past the basic initialisation.

bogdanbarnea (author)2014-10-18

Tanks for your helpful project i realised ambilight whit 120 led and some modifications and is work perfectly tnx again

maewert (author)2013-12-23

I think I understand what you are doing. You hook up your TV as a computer monitor and you execute a PROCESSING script running on the computer which monitors the edges of the video image and sends the color data to the Arduino over the serial port. The Arduino receives the color data from your computer and clocks them out to a Neopixel RBG LED strip which you have modified to fit your TV. Cool.

lacglzh (author)maewert2013-12-24

That's right, you are not bad! :-D

tkotnik (author)lacglzh2014-03-31


GREAT JOB i like it very much, but i have a litle problem with arduino code.

When i copy/paste arduino code to arduino software, he give me this errors:

strip_1m:15: error: Adafruit_NeoPixel does not name a type

strip_1m.ino: In function void setup():

strip_1m:23: error: strip was not declared in this scope

I real like to do this project for myself, i have allready all done , only this probem is left.

Maybe please someone send me Adruino code to mai email please :


azmeanistrator (author)tkotnik2014-09-17

Hi tkotnik / lacglzh,

I have the same issue with the Arduino Code. How did you solve this?

email me at

Thanks in advance

PiotrS (author)2014-08-15

Jacob_M (author)2013-12-30

Hey, its a very good tutorial but I didn't understand few things
which type of LEDs is it? I have a RGB led strip and it looks very different, I have 4 connections, 3 for red,green,blue and one for GND, and you have only 3
Please explain your self better I want to make this.
and How you wire this up? the picture isn't understandable.
Thank you,

crime4sin (author)Jacob_M2014-01-23


he use ws2811 chip led,

it have only 3 connections... (author)crime4sin2014-08-15

NOW ,APA102 come out ,it is new build in ,but have data ,clock ,GND 5V ,4 connection (author)2014-08-15

it is very great ,i will build my own project ,but use apa102 apa104 led strip to replace the led pixel

h3nkinstruct (author)2014-08-06

Ma cosa fa variare il colore e la luminosità del led rgb?
Un sensore luminosità?

bnasty94 (author)2014-07-10

i have a question and someone please help me this project is what made me want an arduino but i have everything i need but what is the aux adapter that goes to the ardiuno can someone please help me

bnasty94 (author)2014-07-10

yes i would really like some help yes i am a noob to the arduino but what is the aux cable with the adapter for i would love to do this project but i need some help please

craftclarity (author)2014-06-27

This is super cool! You should enter it in the Home Technology Contest....!!!!

lacglzh (author)craftclarity2014-06-27

thank you, I just did! :-D

lacglzh (author)lacglzh2014-07-01

no, i can't, because they said it's too old...

molovesdiy (author)2014-06-27

i think this would make my head hurt!!!

radicator (author)2014-04-27

Hi, first thank you for sharing your project, I've made all the passage and uploaded the fix code without errors, processing works good and a appear the window with the edge color of the monitor, but the led strip do not turn on...I've checked it with some library examples ant it works good, is there any test that I can do to learn how to fix the problem? I have an arduino Mega board and a ws2811 chip led strip, really thanks! Riccardo

tkotnik (author)2014-04-02

All work fine bud LED not turn ON,

I have this LED WS2812B 5050 RGB Stripe weiss mit WS2811 Chip (link:

And adapter output 5V 2A...

Is this ok

daykkin (author)2014-03-01

Hello! Nice instruction! Please give link to your LED strip (your blog not opening for me :/)

ps. is it her ?

MrSkuit (author)2014-01-06

First of all nicely done!
I'm trying to do the same thing here for a few days know. I got the arduino one and a dreamcolor led strip (with 3 wires). Tried your sources for arduino and processing.
No problems at the arduino source. But from the processing source, I get ArrayIndexOutOfBoundsException: 77, at this part:
serialData[data_index++] = (byte)ledColor[i][0];.
I'm new with this kind of software and have no idea how to solve this. If you could help me that would be great!

crime4sin (author)MrSkuit2014-01-23

Here is the fix :

import java.awt.*;

import java.awt.image.*;

import processing.serial.*;


// using 12 RGB LEDs

static final int led_num_x = 4;

static final int led_num_y = 4;

static final int leds[][] = new int[][] {

{1,3}, {0,3}, // Bottom edge, left half

{0,2}, {0,1}, // Left edge

{0,0}, {1,0}, {2,0}, {3,0}, // Top edge

{3,1}, {3,2}, // Right edge

{3,3}, {2,3}, // Bottom edge, right half



// using 25 RGB LEDs

static final int led_num_x = 10;

static final int led_num_y = 6;

static final int leds[][] = new int[][] {

{2,5}, {1,5}, {0,5}, // Bottom edge, left half

{0,4}, {0,3}, {0,2}, {0,1}, // Left edge

{0,0}, {1,0}, {2,0}, {3,0}, {4,0}, {5,0}, {6,0}, {7,0}, {8,0}, {9,0}, // Top edge

{9,1}, {9,2}, {9,3}, {9,4}, // Right edge

{9,5}, {8,5}, {7,5}, {6,5} // Bottom edge, right half


static final short fade = 70;

static final int minBrightness = 120;

// Preview windows

int window_width;

int window_height;

int preview_pixel_width;

int preview_pixel_height;

int[][] pixelOffset = new int[leds.length][256];

// RGB values for each LED

short[][] ledColor = new short[leds.length][3],

prevColor = new short[leds.length][3];

byte[][] gamma = new byte[256][3];

byte[] serialData = new byte[ leds.length * 3 + 2];

int data_index = 0;

//creates object from java library that lets us take screenshots

Robot bot;

// bounds area for screen capture

Rectangle dispBounds;

// Monitor Screen information

GraphicsEnvironment ge;

GraphicsConfiguration[] gc;

GraphicsDevice[] gd;

Serial port;

void setup() {

int[] x = new int[16];

int[] y = new int[16];

// ge - Grasphics Environment

ge = GraphicsEnvironment.getLocalGraphicsEnvironment();

// gd - Grasphics Device

gd = ge.getScreenDevices();

DisplayMode mode = gd[0].getDisplayMode();

dispBounds = new Rectangle(0, 0, mode.getWidth(), mode.getHeight());

// Preview windows

window_width = mode.getWidth()/5;

window_height = mode.getHeight()/5;

preview_pixel_width = window_width/led_num_x;

preview_pixel_height = window_height/led_num_y;

// Preview window size

size(window_width, window_height);

//standard Robot class error check

try {

bot = new Robot(gd[0]);


catch (AWTException e) {

println("Robot class not supported by your system!");



float range, step, start;

for (int i=0; i<leds.length; i++) { // For each LED...

// Precompute columns, rows of each sampled point for this LED

// --- for columns -----

range = (float)dispBounds.width / led_num_x;

// we only want 256 samples, and 16*16 = 256

step = range / 16.0;

start = range * (float)leds[i][0] + step * 0.5;

for (int col=0; col<16; col++) {

x[col] = (int)(start + step * (float)col);


// ----- for rows -----

range = (float)dispBounds.height / led_num_y;

step = range / 16.0;

start = range * (float)leds[i][1] + step * 0.5;

for (int row=0; row<16; row++) {

y[row] = (int)(start + step * (float)row);


// ---- Store sample locations -----

// Get offset to each pixel within full screen capture

for (int row=0; row<16; row++) {

for (int col=0; col<16; col++) {

pixelOffset[i][row * 16 + col] = y[row] * dispBounds.width + x[col];




// Open serial port. this assumes the Arduino is the

// first/only serial device on the system. If that's not the case,

// change "Serial.list()[0]" to the name of the port to be used:

// you can comment it out if you only want to test it without the Arduino

//port = new Serial(this, Serial.list()[0], 115200);

// A special header expected by the Arduino, to identify the beginning of a new bunch data.

serialData[0] = 'o';

serialData[1] = 'z';


void draw() {

//get screenshot into object "screenshot" of class BufferedImage

BufferedImage screenshot = bot.createScreenCapture(dispBounds);

// Pass all the ARGB values of every pixel into an array

int[] screenData = ((DataBufferInt)screenshot.getRaster().getDataBuffer()).getData();

data_index = 2; // 0, 1 are predefined header

for (int i=0; i<leds.length; i++) { // For each LED...

int r = 0;

int g = 0;

int b = 0;

for (int o=0; o<256; o++) { //ARGB variable with 32 int bytes where

int pixel = screenData[ pixelOffset[i][o] ];

r += pixel & 0x00ff0000;

g += pixel & 0x0000ff00;

b += pixel & 0x000000ff; }

// Blend new pixel value with the value from the prior frame

ledColor[i][0] = (short)(((( r >> 24) & 0xff) * (255 - fade) + prevColor[i][0] * fade) >> 8);

ledColor[i][1] = (short)(((( g >> 16) & 0xff) * (255 - fade) + prevColor[i][1] * fade) >> 8);

ledColor[i][2] = (short)(((( b >> 8) & 0xff) * (255 - fade) + prevColor[i][2] * fade) >> 8);

serialData[data_index++] = (byte)ledColor[i][0];

serialData[data_index++] = (byte)ledColor[i][1];

serialData[data_index++] = (byte)ledColor[i][2];

float preview_pixel_left = (float)dispBounds.width /5 / led_num_x * leds[i][0] ;

float preview_pixel_top = (float)dispBounds.height /5 / led_num_y * leds[i][1] ;

color rgb = color(ledColor[i][0], ledColor[i][1], ledColor[i][2]);


rect(preview_pixel_left, preview_pixel_top, preview_pixel_width, preview_pixel_height);


if (port != null) {

// wait for Arduino to send data

for (;;) {

if (port.available() > 0) {

int inByte =;

if (inByte == 'y')




port.write(serialData); // Issue data to Arduino


// Benchmark, how are we doing?


arraycopy(ledColor, 0, prevColor, 0, ledColor.length);


About This Instructable




More by lacglzh:Build a Robotic Remote ControllerDIY Camera GimbalMake your own TV ambilight using Arduino
Add instructable to: