In this lesson students will learn about the Raspberry Pi computer and the components provided in the kit. Having a completed kit as an example will be helpful but not necessary. Begin by showing this short video about a raspberry Pi.
Have Raspbian Stretch installed, running, and connected to the internet.
You should refresh on how to easily edit files and navigate the filesystem using a terminal in these tutorials: Terminal Intro Editing Files Intro
Next some configuration,
To correctly output PWM to control the LED ring we first need to disable the native Raspberry Pi soundcard, to do this navigate to /boot/config.txt and comment out the line ‘dtparam=audio=on’
Next step is to install some utilities we will need for setting up our led control libraries and the python environment to talk to them; open a terminal and enter
apt-get install gcc make build-essential python-dev git scons swig
this installs some compilers and utilities we will use in the next step
Next navigate to the folder where you want to setup your LED script in a terminal, use ‘mkdir’ to create a new directory if you want; here we will download the library using git
For more help on navigating and creating directories from within the terminal, see this article -> click here
git clone https://github.com/jgarff/rpi_ws281x
Enter the new rpi_ws281x directory and use the ‘scons’ utility we installed earlier to start building the library into something we can use:
Next enter the python directory, and run the setup and build scripts:
Next to writing the actual script itself…
The first step is a bunch of boilerplate, like telling our library how many LEDs we have and what pin to use ect.
We start off by importing the libraries to control the leds, and read the date and time from the system
from neopixel import *
next are the constants that tell which pin to use, and which kind of led ring we are using
LED_COUNT = 12 # Number of LED pixels.
LED_PIN = 18 # GPIO pin connected to the pixels (18 usesPWM!).
LED_FREQ_HZ = 800000 # LED signal frequency in hertz (usually 800khz)
LED_DMA = 10 # DMA channel to use for generating signal (try 10)
LED_BRIGHTNESS = 10 # Set to 0 for darkest and 255 for brightest
LED_INVERT = False # True to invert the signal (when using NPN transistor level shift)
LED_CHANNEL = 0 # set to '1' for GPIOs 13, 19, 41, 45 or 53
LED_STRIP = ws.WS2811_STRIP_GRB # Strip type and colour ordering
strip = Adafruit_NeoPixel(LED_COUNT, LED_PIN, LED_FREQ_HZ, LED_DMA, LED_INVERT, LED_BRIGHTNESS, LED_CHANNEL, LED_STRIP)
As a brief overview, the important ones for us are:
LED_COUNT: the number of LEDs to try and address, if you have a bigger led ring than normal you might change this; 12 is for the one we gave you
LED_PIN: here we use 18; other pins might be tricky so its probably best to stick with 18
LED_BRIGHTNESS: on full brightness the leds can be super super bright, so we lower it all the way down to 10. Wear sunglasses if you turn it up
Finally with strip we setup the strip using all the constants we just defined.
Now we can actually start writing functions and logic for our program. Python scripts usually execute straight from top to bottom in sequential order; but we can essentially jump around our control flow using functions. Functions take arguments, do things based on these arguments and then exit back to where they were called.
We’ll start with utility functions that will make controlling the ring easier later, before we write the actual clock part. (remember to use tabs for indentation levels).
We start with a function to clear all the leds, essentially turning them all off
def clear (strip):
for i in range(LED_COUNT):
Let’s go through this function line by line: First we define the function and give it a name ‘clear’, followed by a list of arguments it takesLet’s go through this function line by line:
def clear (strip):
Next we start a loop to address all the leds, this pattern will appear alot so pay attention!
for i in range(LED_COUNT):
Notice we use the LED_COUNT variable we named earlier, the loop starts i at 0, and then runs its block over and over until ‘i’ reaches the LED_COUNT value
Here we actually start setting the led colors, we gave this function an argument called ‘strip’ and here its accessing some functionality that the ‘strip’ object holds. In this case ‘setPixelColor’. The ‘setPixelColor’ function demands a pixel number and a color as its arguments so that’s what we give it. We create a color out of R G B values (red green blue) using the ‘Color’ function.
Finally we actually get the leds to update on the physical ring.
And that’s the end of our first function!
Next we’ll make a ‘fill’ function which does almost the same thing; except instead of setting all the leds to off it’ll set them to a color we give as an argument.
The new function will follow the same basic pattern as our old one.
def fill (strip, pixel, color):
for i in range(pixel):
If you compare this and the old function side by side it should be easy to see how they match up and differentiate.
Now we can actually test out our functions and make sure they work.If you compare this and the old function side by side it should be easy to see how they match up and differentiate.
On the line below our functions we can start writing code that will actually execute.
We’ll go over the first few lines to get an idea of how it works:
First we use the ‘begin’ method on our strip to get it ready for any commands
Next we actually call our fill command from earlier, sending it the strip, the number of pixels we want, and a color.
Next we wait for half a second so we get a chance to admire our work.
We repeat the process again for another flash, this time a different color. Of course it would be more impressive if it flashed more than twice, but we don’t want to just keep copying and pasting the same function calls over and over either. And eventually we want our clock to be running indefinitely not just for a few seconds; so we will setup an infinite loop.
When running this script, you can use Control-C to interrupt and exit the program.A while loop repeats everything in its block until the statement we give it isn’t true; ‘True’ is always true so in this case it just loops forever.
Otherwise it’ll just keep flashing your led ring forever!.
Now we have some nice utility tools setup we can actually start writing the clock itself.
First we need to get the time! Luckily we imported the time library earlier.
So start off by erasing our While loop from earlier, because we’ll be writing another one.
now = datetime.datetime.now()
Below our other two functions but above our while loop we’ll put our clock function.Here we fill a variable called ‘now’ with the current time every .5 seconds, but we don’t do anything with it yet. For that we need another function.
hours = now.second%2This turned out to be a pretty simple function so ill go over it section by section.
The most criptic part is the first line:
This is where we work out if we’ll show the hour or the minute hand; the modulo operator is explained in more depth below but basically we are testing if the time in seconds is an even number or not. If it it’s even we set hours to 0 (false) and if it’s odd we set hours to 1 (true).
Next we calculate the hour and minute pixels; which again is explained in the last section below.
hourColor = Color(255,0,0)
minuteColor = Color(0,0,255) Here we set the colours we want to use for the hour and minute hands using RGB values
fill(strip,hourPixel,hourColor) An if statement runs its block of code only if the expression its given is true, the hours variable is set if the seconds are even remember, so every other second we choose to display the hours or the minute hand.
Then we call our fill function from ealier with the desired results.
Finally we put our clock function in our infinite loop from earlier, and our clock is done!
now = datetime.datetime.now()
And here is the final project again to help fix any errors in your own:Remember to run the script as sudo, like at the start with the strandtest.py example!
Looking back over our long clock() function, the most complicated part is the ‘hourPixel’ and ‘minutePixel’ logic; so i’ll go over them in depth here.
hourPixel = (now.hour % LED_COUNT) + 1
hourPixel is a variable which holds a number, the number being which pixel we want to illuminate upto to represent the hour hand of the clock. We start off with the hour in a 24 hour clock format from now.hour
So if it was 2pm the now.hour would equal 14.
To emulate a 12 hour analog clock we need to convert 14 down to 2.
The ‘%’ operator called ‘modulo’ returns the remainder after doing an integer division; this is very useful for testing if a number if perfectly divisible (the remainder would be zero) and for creating ‘circular numbers’ which never pass a certain value. If we look test out the modulus operator we can see the pattern:
1 % 12 == 1
2 % 12 == 2
3 % 12 == 3
11 % 12 == 11
12 % 12 == 0 (perfect divisible)
13 % 12 == 1
14 % 12 == 2
So if we enter ‘13’ hours (1pm) into our modulo operator we get a nice conversion straight to 12 hour time (1).
Because our led ring is addressed from 1 instead of 0, (lighting up the 0th led doesn’t work with this library) we add 1 to the result.
So a straight conversion from 13 hours to 1pm, turns into the second led on the ring.
Leaving us with our final algorithm
hourPixel = (now.hour % LED_COUNT) + 1
The math works in the same way but with slightly more complicated variables for the minutePixel algorithm, it’s a good exercise to try and work out how it works yourself.
This is a continuation of the brush bot activity from the previous class. It may be helpful to have some sort of prize, a 3d printed item or a certificate.
Begin by asking if students got their brushbots to work? To move in a way they wanted? What variables were they able to change? Ask if they feel like their minds grew and what did they notice about themselves as they were building and testing their robots.
Setup and run the 750 mm races and the Sumo competition. Here is a link to some rules.
For this lesson, you will want to have enough Brushbot kits for every student you are working with.
Time: approx. 30 min.
Part 1: Growth mindset and fixed mindset are some patterns that researchers have observed in students.
Here are a series of statements that can be used to assess a person’s fixed or growth mindset. I like to review them before presenting the activity and encourage students just to note where they fit. The actual survey can be found here.
The RSA animate video below has an excellent overview of how Growth and Fixed mindsets express themselves and are developed. To use this with a group of students, plan to pause the video at 4:23 to allow students to talk about the issues raised. Be careful not to equate a fixed mindset with bad and a growth mindset with good.
After watching this video, allow time to review the questions outlined previously and reflect on why mindset is so important. Using daily reminders about growth mindset and keeping company with those that support your growth mindset is important. Make a commitment as a class to support a growth mindset environment and see every setback as a learning opportunity.
Pass out batteries – identify batteries as a technology that today looks common but, was once a science experiment. Have students hold the battery between their thumb and forefinger and envision a tiny bit of electricity moving through their hands.
Pass out the kits – take out the cell phone motor and have students get it moving with the battery.
This a moment pregnant with learning potential.
The flow of electricity, what is causing the motor to vibrate…
What happens if the wires are switched to the opposite side of the battery.
Leave the students with the idea that potential energy is transferred into kinetic energy and that they have the tools in the kit to turn this energy into a robot.
Leave the students to work on their project. This is hard to not help, but control yourself and let them do the exploring. Ask questions to help guide frustrated engineers. Remember, they are learning to exercise growth mindset.
Once it works, have them observe how different ones perform. What can be done to compensate.
At the end of the time help them disconnect their robots and take them home to prepare for the next day’s competition.