SSH into your Christmas tree with Raspberry Pi

No readers like this yet.
LightShowPi Christmas tree

Anderson Silva. CC BY-SA 4.0.

Earlier this year, I wrote an article about how to use the Raspberry Pi to create a music light show using an open source project called LightShowPi. My little Christmas tree light show was popular enough that I was invited to demo it for a group of middle school kids in North Carolina.

Which brings me to this year's Christmas season. I was flirting with the idea of taking the light show outdoors, but due to the business of life I just ended up not having enough time (or motivation) to make that leap. I did, however, put a bit of time into improving last year's setup.

Instead of five channels running 500 lights, I have eight channels running 800 lights. I also modified the LightShowPi's configuration to customize the lights a bit more. I am running all songs in four channels and mirroring the other four channels. This makes the lights a little more fun with fewer blackouts from unused channels during certain songs.

My configuration is now headless as well (i.e., no monitor), and is running on a Raspberry Pi 2. The headless configuration is nice, as I don't need room under the tree for a monitor anymore. The Raspberry Pi 2 (instead of the B+) doesn't make much of a difference, as the performance of LightShowPi is great in either version. With the WiFi dongle, I just SSH into the Pi from my phone and start/stop the lights and music anytime I want.

Finally, this year I also put a bit more thought into the the song selection, trying to add a bit more variety and fun songs to the playlist.

Christmas playlist screenshot

Here's a sample of what the tree is looking like this year:

After getting the Christmas tree lights up and "dancing," one problem immediately became apparent: My wife and kids wanted a simple way to toggle between "solid" and "dancing" mode.

So, I went through my Raspberry Pi CanaKit and decided to try to use the push buttons that came with it to solve this interesting problem.

To help me set up the buttons, I used this nice video tutorial. Here's the result.

LightShowPi wiring

Then I had to write up some code to make this work. At first I based my code on the YouTube video I linked to above, but I didn't like that it had so many loops. So, I did some more reading and was able to come up with a better piece of code. Granted, I'm sure the code can be improved a lot, but it's good enough for a small personal project/proof of concept.


#!/usr/bin/env python

import RPi.GPIO as gpio
import os
import time

gpio.setmode(gpio.BCM)
gpio.setup(4, gpio.IN, pull_up_down=gpio.PUD_UP)
gpio.setup(17, gpio.IN, pull_up_down=gpio.PUD_UP)
lights = 0

while True:
    b1 = gpio.input(4)
    b2 = gpio.input(17)
    #button 1 (solid lights)
    if (b1 == False):
       if lights == 0:
           os.system("export SYNCHRONIZED_LIGHTS_HOME=/home/pi/lightshowpi; sudo python /home/pi/lightshowpi/py/hardware_controller.py --state=on")
           lights = 1
       elif lights == 1:
           os.system("export SYNCHRONIZED_LIGHTS_HOME=/home/pi/lightshowpi; sudo python /home/pi/lightshowpi/py/hardware_controller.py --state=off")
           lights = 0

    #button 2 (dancing mode)
    if (b2 == False):
       if lights == 0:
           os.system("export SYNCHRONIZED_LIGHTS_HOME=/home/pi/lightshowpi; sudo lightshowpi/bin/start_music_and_lights")
           lights = 1
       elif lights == 1:
           os.system("export SYNCHRONIZED_LIGHTS_HOME=/home/pi/lightshowpi; sudo lightshowpi/bin/stop_music_and_lights")
           lights = 0

    # trying not to waste cycles on the pi
    time.sleep(0.2)

The code above basically uses the python RPi python library to interact with the two GPIO pins I use for my buttons (pins 4 and 17), and if a button is pressed and the lights are already off, then turn it on, and vice versa.

Finally—and this took me a while to figure out—I had to modify the $SYNCHRONIZED_LIGHTS_HOME/bin/stop_music_and_lights script that comes with LightShowPi because it had a sudo killall python on it that would kill my Python script.

So, I modified that line to:

sudo kill $(ps aux | grep 'synchronized_lights.py' | awk '{print $2}')

That's it! Here's a look at the end result:

User profile image.
Anderson was introduced to Linux by his uncle back in 1996. In the early 2000s, he transitioned from being a developer to a system administrator. Today, Anderson leads the Red Hat Information Security Incident Response team. He is also an active Fedora package maintainer.

9 Comments

I love this article and I want to try to do what you did. I have a Raspberry Pi Canakit and thanks to your wonderful documentation I have a chance to do just that. :)

Ok. So is there a way to SSH from your phone to make the lights solid? Now I'm just learning about SSH so I'm not sure if my question is good or makes sense.

Yes. At least using LightShowPi, you will need a SSR board (like the Sainsmart) and you can ssh into the Pi, and run the command: export SYNCHRONIZED_LIGHTS_HOME=/home/pi/lightshowpi && sudo python /home/pi/lightshowpi/py/hardware_controller.py --state=on

You can read my previous article on how to get started.

In reply to by Rick Weinberg (not verified)

Great work and documentation on this Anderson. The switching from lights solid to dancing is something I haven't tried yet. I like the way yours is set up. Maybe I will have the time to make it ready for next year. Won't have time this year.

forgive the noobness, but are just turning the lights on and off with the relay via the rpi?

not sure I follow the question, but I am using lightshowpi to do the whole dancing lights thing, but within lightshowpi there is a way to turn the lights on and off... so I added that. but one could hook up the Christmas lights to a relay and they raspberry pi and just write some plain python code to do the same. Does that help?

In reply to by zenmaster (not verified)

Hi, Anderson. It rocks! Great article!!! Your name is typically portuguese. Are you brazilian or portuguese?

Creative Commons LicenseThis work is licensed under a Creative Commons Attribution-Share Alike 4.0 International License.