I'm a mechanical engineer by trade, I design and sell really big custom HVAC units, but for a hobby, I really enjoy playing around with microcontrollers. I am not a trained or schooled programmer, my style is a bit rough due to being self taught and picking up bad habits. I tend to take the long way when it comes to programming, so to many, my code may seem blocky and not as nice or efficient as others. I stumbled across the M5stack product and thought the product and presentation was very nice. I ended up purchasing a M5Stack fire and the obsession with the product has just grown. In this project, I make extensive use of their programming environment UIflow that is available both online and as a downloadable standalone program.
I really enjoy the Christmas time of year. Every year we decorate and I've seen some really nice LED and neopixel displays that really blow you away, so I thought I would have my hand at one this year. I wanted to start out small and see how much work it takes to have a good show. there are several programs out there for light control, one of the better ones is WLED, well thought out and works with a NODEMCU controller, but I am sure it could easily be used with an M5 stack ESP32 microcontroller. I just simply wanted to "roll my own" for the enjoyment of it all.
Maybe this project will be one that is good for beginners. The programming is fairly straight forward, but makes good use of variables, lists, and loops as well as bringing in slightly more advance topics such as using MQTT to pass information to and from microcontrollers. MQTT is a very useful tool and a fundamental building block of IOT related projects. One can remote control a pump, turn on lights, turn on motors, transmit environmental data quickly and easily.
As previously mentioned, many of the Christmas light displays can be controlled with an inexpensive NODEMCU microcontroller and the WLED application. This one however utilizes a M5StickC microcontroller that is only a dollar or two more expensive yet equipped with a Grove Port that makes connecting to the neopixel strips a breeze and it includes a display that can show pertinent information as to the brightness of the LEDs, the number of Neopixels in your display or even maybe what subroutine you are in. The sky is the limit with this controller. It along with the ease of programming in the UIFLow IDE make this project relatively simple. I hope you enjoy.
First a bit about the UIFlow IDE. The UIflow development interface is much like that of Blockly, Scratch, or Makecode, but what is really neat is that you can switch and see what the code looks like in Python/Micropython. While you cannot switch back and forth between programming in a CLI type interface and then back to the Blockly type interface, the Blockly type method of coding could help you code even the most arduous projects and just save the harder part to the CLI type programming allowing you to flesh out a project visually and finish it in at the CLI and load it. M5stack microcontrollers have several libraries loaded in their flash ram and the UIflow program makes use of those behind the scenes to aid in programming. These Microcontrollers can be just as easily programmed in the Arduino IDE, but I'm sticking with the UIFlow for this example.
A bit about the M5Stack and associated devices are a well thought out group or "ecosystem" of microcontrollers and peripherals that are easily connected using a grove port type connector. There are microcontrollers referred to M5Stack Fire, Core2, StickC and StickC plus, along with "Units" or "Hats" which are nicely packaged sensors that have groveport connectors and are color coded to match with their respective port on the microcontroller. In addition to the "Units" or "Hats" there are also Modules and Bases which also perform various functions and provide an extension of sort to the microcontroller whether it be a GPS device, a Stepper motor or DC motor driver module, a battery, or other device.
Now on to the project. From a hardware standpoint, this project is really basic. It consists of the M5StickC microcontroller, a 5 volt, 20 amp power supply, and 4 sets (can vary) of WS1228B addressable neopixel LED lights.
I was able to use the 5 volt in and ground connections on the StickC sensor found at the top rear of the microcontroller to power it from the 5 volt power supply. To make my power connections to the controller and from the supply to the lights, I used a roll of bell wire from home depot. Be sure to connect and waterproof any connections with shrink tubing or weatherproof electrical tape.
I started by writing the code and and testing the pattern on a 1 meter set of lights and then once I had it the way I wanted, I took the project outside to the front yard and expanded upon the setup.
The program consists of a list of RGB settings that you can choose from randomly, or if you choose, you could choose from the list by sending the program information via a MQTT broker.
For time being, I am using the MQTTHQ server that is actually a public MQTT server to subscribe and publish information to. The server settings are really easy and in this case you do not need a username or password to setup your MQTT broker..Do keep in mind that anyone can do a scan for topics and subscribe or publish to your topic, so you might want to use this for prototyping and projects that do not include sensitive information.
The program begins by initializing the number of lights. you can use an "RGB" Unit in UIFlow and setup the light count easily. The settings for the Neopixels are really easy to follow along with in UIFlow.
Once you include the RGB Led "Unit" in your application, you can make easy use of several commands anywhere from setting a single neopixel a RGB color that you can choose from a color pallet, or setting more than one to a color, or setting all to a particular color. To turn the neopixels off, you can set them all to Black, or 0, 0, 0 RGB. You can also control the brightness and set it programmatically.
A little about powering neopixels. A short 1 meter string can be powered from the M5StickC or Stack, as long as you keep the brightness to a minimum. This really allows you to easily test your setup inside before you take it outside. For larger strands, neopixels pull about 60 milliamps per pixel, so doing the math, you can size your power supply accordingly. Adafruit has a really nice tutorial on sizing power supplies for neopixels if you would like to check it out. In addition to having a large enough power supply, it is recommended to power the neopixel strands either at each end of the strand or at the beginning and ending of the strand to ensure enough power to all the neopixels. The resistant and voltage drop through the neopixel strand is fairly significant.
Brief overview of the code.
Setup
The first block can be found in the Advanced-MQTT dropdown, it sets up the mqtt broker/server. I have set mine to a public broker public.mqtthq.com with a port setting of 1883 and a keepalive setting of 3000. The next block prints a true or false to the M5Stack/StickC screen indicating that the wifi connection is indeed connected. Next wee initialize the brightness of the NEOPIXEL string and set it to 10 out of 100. Next is a series of variables that I used for setting or recording the brightness of the neopixel strings, variables I and k I use and initialize for counting, and then three lists I used for setting the R, G, and B settings of the neopixels. Instead of just picking random colors for my Christmas neopixels, I wanted to have colors that I associate with Chrismas. The bright red, the brilliant blue, purple, and green. So I found an online resource with a really good christmas RGB pallet to pull from. This is pretty much it for the setup.
Next is the Loop portion of the code. We start with a repeat block that you use to repeat or iterate throught he colors and neopixels, this is set to the number of lights in your neopixel string. In my case, I'm using 60 for my 1 meter test strip and 600 for my display in the front yard. I use k as the counting variable in this while loop.
I use "i" to increment to each pixel in the string. I make use of the lists of light colors I have created. First I pick a random number between 0 and 4 because the lists are 0 based lists. Once I choose my random number I use that to retrieve the "R", "G", and "B" setting and store those in variables "colorr", "colorg", and "colorb".
I use a switch case to see if I have received instructions from my mqttt subscribe function "kgslightshowx". If I have received text from that subscription that matches the string "RANDOM", "RED", "BLUE, or "WHITE" I decide what to set the pixel color at this point in the string. If one sends it something other than the above colors, or strings, it will default to a White setting and diplay all white neopixels.
To make it more interesting I nested one loop inside another so that it works its way through your whole neopixel string lighting up neopixels 0-10, then turns those off and then lights up neopixels 11-20, 21-30, 31-40 and so on until it reaches the number of pixels you have in your complete string of neopixels. This can be adjusted to as few or as many pixels as you like to make it interesting and can potentially be a variable that is changed via MQTT subscription. The fun thing about the program is that you can really build off the fundamentals in it and really make the light show your very own. Try it out, change the count, change the delays, or even the colors, using the colors that you associate with the holidays.
If you would like, say "Hi" by publishing your favorite light color to the "kgslightshowx" channel. You can choose from the colors above "RANDOM", "RED", "BLUE, or "WHITE". I thought about taking this a step further and using a M5Stack fire or the Grey controller with a SD card and allowing people to publish their location to my programs so I can see where everyone lived, but I was uncertain about the amount or type of data I would receive.
And here is the video of the end result.
I guess the presentation is a little lame. I'll work on it, but I just had to give these programmable neopixels a shot.
Happy Coding!
Comments