Microsoft's MakeCode editor is a great way to get your Circuit Playground Express to do things without having to muck about in actual code. It's a fun drag-and-drop editor that's easy to use and sneakily teaches you how to write code while you're making pretty things that light up.
The MakeCode project linked below has four different modes, one for each season of the year, plus a mode for "off". Each mode is triggered by a capacitive touch pad on the Circuit Playground Express. You can download the completed code and get up and running right away, or you can follow along and create your own code, adding your own customizations as you go.
Our code has four different color modes: a high-energy "party" mode for spring, a relaxing rainbow for summer, flickering candle light for autumn, and a rainstorm with lighting for winter. This will make our MakeCode project a bit complex, so if it's your first time using MakeCode, head over to the MakeCode Intro Guide and play around with a couple of the beginner projects to get a feel for how it all works. Once you're ready to go, head over to makecode.adafruit.com, roll up your sleeves and it's time to dive in.
Click the Circuit Playground Express and then New Project. You'll see your workspace, with a Circuit Playground on the left, some tabs in the middle and your workspace on the right. Click the LOOPS tab, and find
on_start. Drag it into your workspace.
Whatever you put into the
on_start loop will run once, when you first boot up your Circuit Playground Express. Whatever you put in the
forever loop will run over and over again, forever.
Let's tell the Circuit Playground Express that we attached some lights to pin A1. Click the LIGHT tab and another sub-tab will appear labeled NEOPIXEL. Anything in the LIGHT tab refers to the lights on the face of the Circuit Playground Express itself. Anything in the NEOPIXEL tab will refer to lights that you add. Find
set strip to create strip on A1 with 200 pixels (or whatever your total number of pixels in ALL bottles is, plus a couple extra) and drag it onto your workspace inside the
A variable is a placeholder or container for a number. We use them so we can change numbers willy-nilly, on the fly, or in multiple places at once. We'll set up all our variables now so we can use them later on in our code. Click the VARIABLES tab to create your variables.
I've created a variable for each of the four seasons:
winter, as well as one called
sleep (for "off" mode).
I've got one called
clock, which we'll use to time our lightning strikes in the winter animation.
There's one called
hue, which we'll use in the spring and autumn animations to randomize our colors.
I've also created
strip4. These will be used to break up our strip into arrays, or chunks of LEDs which we can call individually, to apply animations to part of our strip at a time. We'll use these in our autumn animation as well.
I've set up a separate function for each of the seasons and one for "off". Functions are a fancy way of creating a separate box for a bunch of code which we can call when we want it, but it'll stay out of our way the rest of the time. You can create them from the FUNCTIONS menu which is found under the ADVANCED tab.
Name your functions something other than "spring" or "summer" -- since we already have variables set up using those names, we'll need to call our functions something different.
Spring / "Party" Mode
For spring, I want a lively animated mode with lots of color and motion. I'm using the Photon feature in this mode. Photon lights an LED in white and moves it along your LED strip, trailing color behind it.
By setting the pen color to our
hue variable and changing our hue each time the photon moves, we're able to have the photon trail a rainbow behind it instead of just a solid color. Adding
strip rotate gives more interest, as each light will slowly animate through the rainbow while it's waiting for the photon to come by. You can play with the numbers until you get an effect you like.
The photon feature has a bit of a bug, in that the white photon light tends to stay stuck "on" when you change to a different color mode. To work around this, I added a line to all the other modes setting the photon to LED #199 (shown below).
In reality I have fewer LEDs than 199 -- my total number is probably somewhere around 195 (I lost count at some point!). So setting the white photon light to #199 means it's moved off my strip entirely and is happily stuck "on" someplace in Imagination Land where it won't interfere with my project.
Autumn / "Flicker" Mode
For autumn, I want a halloween-y candle flame effect in my bottles. This is very similar to the flame effect I wrote for my paper mache dragon project, and I go into more detail about it here. I've added a little more complexity to this animation for this project.
Looking at the function: I'm starting with the
photon bug fix described above. The next line creates the candle flicker. I'm choosing a random LED (the first
pick random), then setting its hue to something between 0 and 30, and its intensity (
val) to something between 0 and 200. This will make all the LEDs color in various shades of red and orange, with randomized brightness. Then, I pause for a random number of milliseconds to make the flicker.
Next, I randomized the brightness of the whole strip to add another dimension of flameyness. But when I tested this on the bottles, it looked fake -- all the bottles seemed to be flickering at the exact same time, which really wouldn't happen if there were actual candles in the bottles. How to make it look more natural? This is where the arrays come in.
I added three lines to the
on start loop, setting the variables I made earlier (
strip2, strip3, strip4) to each represent roughly 1/3 of the total strip. Then I was able to vary the brightness of 1/3 of the strip at a time by randomizing brightness to those arrays. This makes the whole animation look a lot more natural.
Had I wanted to be very thorough, I could have made an array for each of my 9 bottles, using just the number of lights in each bottle, then varied the brightness of each bottle individually. But because of the way the bottles are spaced pretty far apart and not sitting in a line, having 3 arrays was plenty for an illusion of randomness. If your bottles are all lined up on a shelf, you'll probably want separate arrays for each bottle so they don't flicker in "chunks."
This is my favorite mode, so I want it to be the default when the tree starts up. I added a line to my
on start code setting my
autumn variable to
true. I also set
0 to be sure I get a nice red color when the bottles start up.
Winter / "Rain" Mode
For winter time, I wanted the feel of raindrops dripping from the tree, punctuated by the occasional flash of lightning. The top half of the code makes the raindrops, and the bottom half makes the lightning. The
clock variable is used to count out the time between strikes.
This is based on the raindrop animation I wrote for the FloraBrella project, and I go into more detail about that here.
if/then statement (found under LOGIC tab) makes this possible. In English, this code says something like:
If we haven't counted to some random number between 200 and 1000 yet, fix the photon bug and then turn on a white raindrop somewhere, while turning off some other raindrops. Then count up.
Once we've counted to our random number, flash all the pixels three times for a short randomized amount of time, then turn them all off and set our counter back to 0.
It's easy to make the lightning more or less frequent by adjusting the values. This code looks really cool, and is also my favorite mode. (Yes, I'm allowed to have two favorites!)
Summer / Rainbow Mode
Summertime is lazy, so I kept this one simple and just used one of MakeCode's canned animations. This was so simple that I didn't bother to make a function for it, I just call it in the FOREVER loop, which we will get to shortly.
Off / "Sleep" Mode
Finally, our "sleep" mode fixes the photon bug, then turns all the LEDs to black / off, and stops any animations.
Calling the Functions
To make the animations play, we'll use an
if/then statement inside our FOREVER loop. For summer, I used the canned rainbow animation (using
show frame of animation gives you a bit more control over speed and seems to curtail bugs), and for each of the other modes I called the function written for that season. Using the functions makes the code so simple!
Lastly, we need to hook up the Circuit Playground Express' capacitive touch pads to trigger the different modes.
I'm using A2 for "off" mode. I grabbed
on button A click from the INPUT tab and selected
touch A2. First, I reset all the lights to off by calling the
off function, so the previous mode doesn't bleed into the new mode. Then, I set all modes to
false except the one I want active, which I set to
Finally, I copy/pasted this block a few times, setting each touch pad to trigger the desired season's animation.
I'm sure there's a fancier way to do this with math and less repetitive code, but this way makes intuitive sense to me and it works just fine.
Give your code a name (I called mine Fairy Bottles) and save it. Click the Download button and a file will download to your computer. Plug your Circuit Playground Express into your USB port and click the reset button. You should see all the lights on the face of your Circuit Playground Express turn green, and a drive will appear on your computer called CPLAYBOOT. If you see a drive called CIRCUITPY, press the reset button a second time to get to CPLAYBOOT.
Drag the downloaded file onto this drive to program the Circuit Playground Express.
Once you've got your lights hooked up, touch the pads and see the modes change!
If you're having trouble with the download process, head over to the Circuit Playground Express guide for some more detailed instructions and troubleshooting ideas.