![](/assets/playground/adafruit_playground_1200x900-699010177a4a3fd6bac6bc31deae0bfa3eb9ea777ba62aaa5cbc1225bb45bfcc.jpg)
Adafruit Playground is a wonderful place to share what you find interesting. Have a cool project you are working on? Have a bit of code that you think others will find useful? Want to show off your electronics workbench? You have come to the right place.
Adafruit Playground is a safe place to share with the wonderful Adafruit community of makers and doers.
Click here to learn more about Adafruit Playground and how to get started.
-
Pinned by mrklingon
Meet MrKlingon - Joel Anderson
Joel, aka MrKlingon, is a lifelong SF enthusiast who has been playing with computers for about as long as he remembers. From a Think-a-Tron, to Digicomp, to science fair projects, he has always loved thinking of interesting computing projects.
Retired from work in network security for a Big Ten university at the beginning of the pandemic, he delighted in discovering all the great things Adafruit had to experiment with. Particularly interesting has been coming up with ways to squeeze all sorts of things out of the tiny Neo Trinkey.
-
Decison Maker!
An invention was patented in 1948 that has assisted millions in making decisions. Long before widespread access to computers, this device - completely mechanical gave instant answers to questions - no AI or LLM required.
I refer to ... the Magic 8 Ball.
It doesn't take much of a web search to find examples of programs to recreate the Magic 8 Ball. It's an easy exercise - for example, here's one at geeksforgeeks.org that made a fun starting point for me to adapt for some Adafruit fun.
It wasn't hard to adapt that code into CircuitPython for the NeoTrinkey. I put together Magic8.py. Load that on a NeoTrinkey - copied to code.py. When run, it will display a blinking idle pattern. Touch either touch pad and it will go to Green (yes), Yellow (maybe) or Red (no). If you are running it in an IDE like Mu or Thonny, the REPL will print an answer appropriate to the verdict. Touch the pad again to return to the idle pattern.
But, why not make a better, smarter tool - something that you can use to calculate the answer? And why not have it SPEAK the answer?
In my DecisionMaker repository you'll find all you need to do that.
Starting with MakeCode I created a two-mode DecisonMaker for Circuit Playground Express. With the switch to the right, press the "A" button and it will give you a Green/Yellow/Red verdict. In addition, IF it is plugged in to a computer with a usb cable, touching A4 will give you a verdict and TYPE the appropriate message text. (note: If the CPX is not connected to a computer, touching A4 will crash the program; also, if you copy DecisionMaker.js into MakeCode, you'll need to add the Keyboard Extension; it's already in the version at this link).
The other mode is what you get when you move the switch to the left. This lets you give more input for the program to evaluate your question. Essentially, break your question into factors (as many as you want) and give each factor a value good or bad, then ask the DecisionMaker to weigh in. With each factor press A from one to five times (for Good) and B from one to five times (for Bad). After scoring the factor, touch A1 to add it in.
For example, lets say your question is "Should I go see the new movie Super Space Blockbuster XIII?" and you break down the factors to:
- I love Super Space Blockbusters - read all the books and comics and have all the action figures
- I didn't like the last three that much
- I hear they added famous actor Kirk Handsome
- I think it will be streaming in a couple of months.
So, here's the steps in the evaluation:
-
Tricorders!
In 1968, I participated in my first Science Fair, and I saw a working Tricorder! It was another student's project, an assembly of different instruments for sensing things. I know it included radiation as well as temperature. It had a form of an electrical analog computer as well for calculations. It was all wrapped in a case modeled after the imaginary Tricorders on Star Trek. Pretty impressive for the time (the show was only in it's second season)!
Of course, that was a fun project that many have improved upon - there was an X Prize awarded for creating a mobile device that can "diagnose patients better than or equal to a panel of board certified physicians". And fans have constructed working props - even ones that can provide a variety of sensor readings. It's a great example of how the art of an SF program has inspired real-world engineering and development.
My own efforts are pretty modest, but it's fun to think about ways to craft a sort-of Tricorder device, given platforms like micro:bit or Circuit Playground Express with their multiple built in sensors. Early on I made a micro:bit version that displayed compass reading, light level and temperature, along with a small vocabulary of "alien" words; easy to do with the 5x5 LED matrix on the micro:bit (this was V1 micro:bit, so it didn't use the microphone). There was even an animated picture of the Enterprise.
Now, the Circuit Playground Express has good sensors but there is no graphic display, just the ring of ten neopixels - so how do you display readings? I wrote functions to display numbers by converting them to a string, and then, digit by digit, lighting up enough pixels to indicate the value. In addition, for the Circuit Python version I recorded the digits 0-9, and "point" and "minus" so I could have the device speak the number. I also think it's fun to use Morse code to display info, so for the Makecode version, I added the ability to display a number of sayings (maybe not too practical, but it was fun).
I've saved all this in a repository - here's the README
Tricorders
Code for Circuit Playground "tricorders"
- pycorder.py - "tricorder" program; toggle through idle/temp/light/gees with button A, get reading with B
- bach.py - provides musical notes, random music with touch A7, Star Wars Tune with A1
save .wav files in "digits/" directory 0.wav 1.wav 2.wav 3.wav 4.wav 5.wav 6.wav 7.wav 8.wav 9.wav gees.wav light.wav minus.wav point.wav temp.wav idle.wav
- Tricorder.js - Javascript version of CircuitPlayground Tricorder - toggle through idle/light/temp/gees/text modes with A+B, get reading with button A. when in "text" mode, tilt left/right to choose what phrase to display, press A to get morse code version
Tricorder.js
To use the Javascript code, open up https://makecode.adafruit.com start a new project, switch to Javascript mode and paste in the code. (You can also go directly to this link)
When you run the Makecode version, the program starts by blinking "hello" in Morse, then in "idle" mode, swirling a rainbow. Press A+B to jump to the next mode. Each mode shows a distinctive color:
- Light (yellow)
- Temperature (red) - note, switching the CPX switch left, gives Fahrenheit, right give Celsius
- Sound (green)
- Text (blue)
When in a sensing mode, you'll see a real time graphing of the current value - press "A" to read the current numeric value.
When you are in "text" mode, tilt left and right to choose the phrase:
0: spock = "live long and prosper"
1: yoda = "do or do not"
2: yoda2 = "size matters not"
3: yoda3 = "luminous beings are we"
4: kirk = "to boldly go"
5: picard = "engage"Press A to see the words displayed in Morse code.
CircuitPython version: pycorder.py
This requires you start with a Circuit Playground running Circuit Python (well, of course). Copy all the .wav files to a directory "digits/" and pycorder.py to code.py and bach.py on the CPX.
When it starts, it will flash a few colors, then announce "idle", going into swirling colors.
Advance modes by pressing "A" button. Again, a signal color announces the mode switch, along with a voiced "temp", "light", "gees", "idle". When in a sensing mode, press B to get the current reading.
- Temp (red) - note, switching the CPX switch left, gives Fahrenheit, right give Celsius
- Light (yellow)
- Gees (green) - note, "gees" willl announce THREE different values; the X, Y and the Z axis values
For fun, the A1 touch pad will render a Star Wars tune, and A7 will play a snatch of random tones.
-------------------------------------------------
So there you have it, my version of "Tricorder" - I'd love to see how others take that idea and make the imaginary real!
-
It's ALIVE! Cellular Automata on the NeoTrinkey!
When I was in High School
- People were walking on the moon,
- I was learning to program with BASIC and,
- I learned about Cellular Automata from Scientific American, and I thought it was really neat.
Now, no one is on the moon, I mostly don't program in BASIC... but I still think Cellular Automata is pretty neat. So much so, it's one of my go-to things to fool around with on different tiny devices - micro:bit, Circuit Playground, and, of course, my favorite NeoTrinkey!
I've got a repository with some of my experiments.
The first is lca.py . This lets you run a linear cellular automata on the Neo. Run it as "code.py" or, in Thonny, load it up and click the "run" icon. It's a simple program that will run 10 generations every time you touch pad #1. Touching pad #2 randomizes the universe. Output is printed to the REPL - but the four pixels of the Neo will show four of the cells with random colors.
Output looks like this:
-
Magicquest!
Revisiting some of my Neo Trinkey experiments, I've been modifying code that no longer works with CircuitPython 9.x. This is another story generator I created using names and items generated with fantasynamegenerators.com.
Like "Tell me a story, Neo Trinkey" you get random stories by touching tab #2. Tab #1 chooses the hero name, class and race.
The repository is here
and includes
- magicquest.py - program file, rename to code.py
- prt.py - helper file for prt("text",REPL) function. REPL=True to send output to REPL and False for keystroke output
Data files for story input :
- destination.mq
- enemy.mq
- forest.mq
- names.mq
- treasure.mq
- weapon.mq
Load these on your NeoTrinkey and you can get stories like this:
The dwarf burglar Polo Littlefoot
gets lost at
Corftey Fortress
discovering Black Magic Tome
Polo Littlefoot is surprised when The Black-Eyed Cinder Spider attacks from Jagged Covert
Stumbling badly, Polo Littlefoot somehow manages to find the Mournblade, Gift of Ancient Power and dispatch them!
No, not great literature, but I had fun creating it!
note: illustration above from
https://www.publicdomainpictures.net/pictures/190000/velka/medieval-fantasy-castle-2.jpg
-
Tell me a story, Neo Trinkey!
Once upon a time.....
..... I remember reading a story in "Summer Weekly Reader" (I think by Isaac Asimov) about a robot that told stories to the young boy who owned it. Mostly fairy tales, till one of the boy's friends loaded a tape with more modern info like spaceships (and robots!).
Now, I don't have that robot... but I have a Neo Trinkey and CircuitPython - that's more than enough.
My repository TellMeAStory has five files, CircuitPython code: scifi.py and prt.py, and text data: planets.sf, aliens.sf and ships.sf. Copy those to a Neo Trinkey, renaming scifi.py to code.py. When the program runs, touching "1" chooses a planet name, and touching "2" will generate a short story. In code.py, if REPL=True, you'll need to be in an editor like mu to see the text. IF you change REPL to be False, then it will use HID support to send the text as if typed on a keyboard! For example:
(touching 1)
Broria KBO6
(touching 2)
Black Sparrow
lifts off from
Broria KBO6
with ancient artifacts
and is damaged in an explosion
and tumbles out of control till emergency crews reach them
Suddenly a ship appears from Notania warning of imminent Bhisih attack.
Planets, Aliens, and Ship names were generated on fantasynamegenerators.com - you can edit the lists with your own choices. And you can rewrite the story elements to your own liking!
[Note: updated to work with CircuitPython 9.x. I moved the lists of aliens, ships and planets to external files to avoid memory allocation problems.]
-
Mandelbrot on a Neotrinkey? ... It's Complicated.
It's no secret that I keep trying to think of new things to do with the NeoTrinkey. One day, for some reason*, I wondered if it would be possible to render the Mandelbrot set in ascii... with a NeoTrinkey.
Since the NeoTrinkey runs CircuitPython and since many, many projects are shared online in Python... it seemed reasonable to assume I could find code that would help me do this. And I did - I found a github project by "LadyClaire" : https://github.com/claiire/python-mandelbrot - this seemed exactly like what I wanted.
Except... well, I said it was "complicated." The math to render the Mandelbrot set involves manipulating points on the complex number plane and Python easily does such math, CircuitPython doesn't.
Which meant I couldn't just run LadyClaire's code - I needed to write my own complex.py module that let me do the work. Import complex.py and you get:
- absC - returns absolute value of a complex number
- plsC - adds two complex numbers
- sqrC - squares two complex numbers
- mltC - multiplies a complex number by a number
- mltCC - multiplies two complex numbers.
- mltI - multiplies a complex number by i
With those functions, I could tweak the code into mandelbrotx.py - adding in some blinking lights (you need ncount.py). The mandelbrotx.py module (which you'll rename code.py) has a variable REPL - REPL=True directs the output to the REPL, REPL=False sends it out as keystrokes.
When you run the program you need to touch pad #2 to start the rendering - you'll see lights blink as each row is calculated. When it's done you'll see the image at the top - generated not by some supercomputer... but your friendly, NeoTrinkey!
*Note: I know the reason, it's because I follow a Mastodon account, [email protected], which posts random images from the Mandelbrot set.
-
Babel - Let's make some Alien words!!
Here's another silly NeoTrinkey project - let's make some alien words!
babel.py - generates "alien" words using a set of rules for Wookie, Klingon, Vulcan, Mando'a and Romulan.
ncount.py - blinks numbers
Touching pad #1 toggles between the five languages, and blinks the number (1..5) for the language choice. Each language defines a set of consonants, vowels and an array of word patterns (V for vowel, C for consonant, v 50% chance for a vowel, c 50% chance for consonant). When you touch pad #2, a list of words (random quantity, 1 to 10) is created following the rule sets. The rule sets were created using known words from those languages.
Change the variable REPL to direct the output: True means the program prints to the repl, False sends the output to the keyboard.
Example output:
Wookie: OUWA ROR HOH AROOAUW HOUW WOH ORAUW ORUUUUR WOR OWOUOOR
Klingon: laq noegh tSyIm DIyS mI Ho jaab
Vulcan: su tuai tiustoa het' tiy k' t
Mando'a: ary reara 'hr syc tmn cor khc
Romulan: ihf ki'vh ies lu'm m'ih ih eenh hieh uek
Note: These are generated words, and only by coincidence match vocabulary in any real lexicons.
For fun you can replace my rule sets for any other alien or fantasy language you wish to create.
There's a hoopy frood who really knows where his towel is. -
Spock on a Chip!
I love using the random library - it's a simple way to introduce variety into simple programs and here's one example, what I call "Spock on a Chip." Here's a link to the repository.
Copy the files to a NeoTrinkey, changing "spock.py" to "code.py" - when it runs, it occasionally blinks lights, but when you touch one of the pads, it will blink and then pick a random quote out of the "spock" file and print it. If REPL=True, you'll need to be in an editor like mu to see the text. IF you change REPL to be False, then it will use HID support to send the text as if typed on a keyboard! Just the way to jazz up your email! Edit the "spock" file to add your own favorite quotes from everyone's favorite Vulcan.
What's going on?
There are two functions that are used to deliver the quotes. len_file(filename),
def file_len(filename):
with open(filename) as f:
for i, _ in enumerate(f):
pass
return i + 1
and wisdom(file_name).
def wisdom(filename):
qs = open(filename)
for i in range(random.randrange(file_len(filename))+1):
quote = qs.readline()
quote = quote.rstrip()
cmpthink()
qs.close()
return (quote.rstrip())
Give a file name, wisdom() calls len_file() to determine how big the file is, then uses random.randrange() to select the text - that means you can add or subtract from the "spock" file without needing to update the program.
The fun thing with this code is, it can be reused for other purposes. I've already used it to put together a "story" program that uses multiple source files (aliens, suns, planets, etc.) that can be drawn from to generate story lines. It could be used for a diceware style passphrase generator. And, of course, it doesn't have to be Spock on a chip - you can fill the "spock" file with any quotes you choose.
Fascinating. Is this logical? -
How about.... a 4 Pixel Video Game??
Here's a project I had fun putting together using my NeoTrinkey toolkit to make a tiny little video game.
I call it "Galaga" - and it uses the ncount.py and morse.py helper modules.
Gameplay:
- An enemy moves back and forth at random in the 0 and 3 neopixels.
- Touch 1, or 2 to "shoot" the moving enemy (green pixel).
- If you are lined up with it, you get a hit. If not it's a miss.
- A hit blinks gold for the count of hits. If you miss, you blink the number of misses in pale blue.
- A win is 5 hits, and losing is when you have 5 misses or run out of missiles.
- Winning is followed by multicolored blinking.
- Following loss/win the number of missiles, score and miss count are reset and game restarts.
- NOTE: connected to Thonny or Mu, you can see "boom!" and "miss" printed when you hit or miss. Plus notification when you win (or lose).
-
NeoTrinkey Tool Kit!
It's no secret I think the NeoTrinkey is wonderful. It's small, it's cheap and it runs CircuitPython! Who could ask for more??
As I played with it, one thing I found handy was making some helper modules to assist in building programs - three that are particularly handy are:
-
morse.py - translate text to Morse code, also defines touch pads for input
- def docode(text): # display given text in Morse code
- def blinknum(num,color): #count out a number in a color
- def compthink(): #blink out all the colors when computer "thinking"
-
prt.py - provides a function to print text to the REPL *OR* using HID to send it as typed text.
- def prt(text, REPL): #prints text to REPL if REPL=True; otherwise uses HID to send as typed text
-
ncount.py - blinks numbers, or displays 0-15 in binary.
- def docolor(color): #briefly set all pixels to color
- def blinknum(num,color): #blinks num times in color
- def binnum(num,color): #display num%16 in binary on pixels with color
Using The Modules
Here's a very short program that blinks out, in Morse code some Bible verse fragments (in Klingon - my "nickname" is mrklingon, after all):
from morse import *
John316 = "vaD joH'a' vaj loved the qo'"
Isaiah263 = "Duvoqchugh, vaj rojna'Daq Da'av, DuHarmo'"
Psalm231 = "DevwI'wI' ghaH joH'a''e' jIneHbe'."
while True:
docode(John316)
docode(Isaiah263)
docode(Psalm231)
Pretty simple - it just blinks the code over and over. You could plug it into a power source and let it run - and you could choose your own text. Plugged into a computer running Mu, you would see the text being printed over and over as well.
Using the prt.py module, I wrote magicquest.py. This uses morse.py for the touch pad initialization, and the "compthink()" blinking. Touching pad 1 creates a fantasy character (race, class and name), and pad 2 generates a short story about the character's adventure. I used fantasynamegenerators.com to come up with place names and more.
If you change the value of REPL in the code you can decide if the text gets printed in the REPL using Mu or Thonny, or if it is sent as if typed using a computer.
REPL = False #"printed" text from prt() goes as if typed
REPL = True #"printed" text goes to REPL
I used the ncount.py module's binnum() function in two progams, cards.py and orbit.py.
For the cards.py program, the neotrinkey shuffles a deck of cards when you touch pad1, and pad2 draws a card and prints it in the REPL but displays it as a binary number (1-13) and color
suits = ["diamonds","clubs","hearts","spades"]
scolor = [gold,blue,red,green]Touching 1 and 2 together shuffles and draws three cards.
orbit.py blinks a purple NeoPixel around and around at a speed (sort-of) appropriate to the planet the ship is at - from Mercury to Pluto. This uses binnum() to light up the number 1,2,4, or 8 to move the position around and around the four NeoPixels. Touching pad 1 makes all NeoPixels flash gold (closer to the sun) and shifts to the planet that is next closer to the sun. Touching pad 2 makes all NeoPixels flash blue (farther from the sun) and shifts to the planet next farther out.
Pads 1&2 together make jump the position either to Mercury or Pluto depending on whether you are closer than Mars or at Mar or farther out.
The name of the target planet is printed to the REPL and the orbit speed speeds up or slows down depending on which direction you have moved. (Note: the "speed" is just a factor based the position (planet 1-9) divided by ten. It is not really correct for the real planets).
Adafruit Neotrinkey -
morse.py - translate text to Morse code, also defines touch pads for input
-
Cosmos in a NeoTrinkey!
Yet another silly program from MrKlingon.
Program cosmos.py requires ncount.py to display numbers. You can load both on a neotrinkey. If cosmos.py is saved as code.py the program runs on power up.
A 40x40 cosmos is generated with a variety of stars.
- Touching pad1 changes direction - there are 8 - (think N, NE, E, SE, S, SW, W, NW). The neotrinkey display shows a binary number for which ever is the current direction, then the current X,Y position, then displays the stars at the current 2x2 window the "ship" is at.
- Touching pad2 blinks through showing the stars for 7 steps in the current direction.
- Touching both pads together (1&2) does a display traversing through all the stars.
- Running in Thonny IDE displays current coordinates while "traversing" and names the stars.
Travel the Universe in a NeoTrinkey! -
Ridiculous "Light Saber"
Who doesn't want a light saber? There are lots of projects using neopixels (and products as well). Here's a silly "saber" (dagger? scalpel?) using a neotrinkey. It won't impress many, but it was fun to put together. When you put this in as "code.py" on a neotrinkey, you can plug it into any power source and it will first blink "hello" in Morse Code, then touching pad one will choose a random color. Touching pad two will "ignite" or "douse" the saber.
I originally wrote a saber for a Gemma M0 with a 30 neopixel strip. I didn't like blinking all the saber's lights on/off, and rewrote it to ignite/douse more slowly to make it realistic (as realistic as an imaginary weapon is, of course). Then... I thought it would be just as fun (and more portable) to do the same thing on one of my beloved neotrinkeys. So here it is:
-
Why not a $6 Web Server
So... the Pico Pi W can connect to Wifi. What to do with that? Hmmm...
The Raspberry Pico Pi W -
Teach your NeoTrinkey Morse code!
C3P0 can talk. R2D2 expresses what he's thinking with beeps and boops. What can you do with a Neo Trinkey?
How about.....Morse code? It's simple, and four neopixels is more than enough to say anything! Here's how I set about doing it.
What can you do with a computer this small?