Session 7 - Microtransmitters Flashcards
This is a computer that we can embed - (2)
Python code into to do clever things
has USB cable plugged into computer to desktop
What is this?
It is a whole computer system
it is designed to interface to the real world - all those little gold contacts around the edge are input / output pins that can send
and receive data from the world. It even has a cute little built-in thermometer.
This is called a …
It is the cheapest…
More often… - (3)
The RP2040 is a microcontroller chip developed by Raspberry Pi.
Cheapest computer you can buy
More often though, they are used as embedded computers in things like robotics projects
This has a - (3)
import port and two buttons of reset button and boot button
an LEG with 3 colours - inside got red, green and blue LED and can make any colour with it
inbuilt theometer to measure temperature of the chip
Each group has…
First thing is to attach the - (2)
Each group has an RP2040 and a USB-C cable. You will also need to be logged in to a Windows PC.
Attach the RP2040 to the PC.
The RP2040 is a computer. Like all computers it needs an
You are used to… - (2)
‘operating system’.
You are used to computers already coming with different operating systems (Windows, Linux, macOS)… but you will need to install one on the RP2040.
You will download an operating system for the RP2040 from a website and then
install it over the USB cable
There are lots of possible operating systems you can put on RP2040 device and
At least two of them let you control it in Python.
here are lots of possible operating systems you can put on this RP2040 device
We are going to install operating system called
Circuitpython on the RP2040 device - lets Python run on RP2040 device
We can download the Circuitpython operating system from a link which will - (7)
Then steps to put Circuitpython operating system onto RP2040 device
This will put a ‘.uf2’ file in your downloads folder. It should be about 1.7MB.
The RP2040 has two buttons on it called Reset and Boot. You need good eyes to see the words but the buttons are easy to see.
You are going to tell the RP2040 that you want to install a new operating system (essentially, you are going to “wipe its memory”). To do this… hold down the Boot button for a few seconds. Then while it’s down, press the Reset’ button at the same time and hold both for a couple more seconds.
So
“Boot”…. one, … two,…. “Reset”, one…., two…., “Release”
When you do this, the RP2040 should show up as a device (‘RPI-RP2’) in the Explorer window. It looks like you just plugged in a thumbdrive.
To install CircuitPython, drag the .uf2 file you just downloaded to the RP2040 in the file explorer. That’s it.
The RP2040 will reboot (or you can force it to reset with the Reset button) and it will show up again on the Explorer as something like ‘CIRCUITPY’ instead of CIRCUITPY
Inside CIRCUITPY (D:) it has a file called ‘code.py’
this is where purpose of this computer device is to find code.py in directory and then run whatever code is in it
However, today we will settle for making the onboard LED flash different colours.
The LED is the
white dot between the two buttons.
To make the onboard LED flash different colours, we need to add a
add a single ‘library’ to the ones that come bundled with CircuitPython. “neopixel” that doesnt have in toolkit which comes from Ada fruit to allow to flash LED
We can download neopixel via a link and - (3)
drag neopixel.mpy into ‘lib’ (where it likes to store all its libaries)
The library file you downloaded is called neopixel.mpy
Drag this over to the lib folder on the RP2040 in the file explorer
In the CIRCUITPY directory (see above) you can see a file called code.py
If you put Python code in this file, it will run when the
RP2040 is turned on.
You can edit the code in the code.py file and it would - (2)
edit a text file on a thumbdrive.
But to make our lives easier we will use a program called muEditor.
What is muEditor? - (3)
This is just a normal text editor but it is designed for use with little Python projects like this.
You can find it in the applications menu of your Windows PC.
Its good to run Python on attached devices
If your RP2040 board is plugged in when you start muEditor
it will try to detect it.
First time you run , you need to tell muEditor you are using
CircuitPython
Diagram of muEditor box
To edit the code.py file in muEditor, we load it in
using load buton
At top is the code the device is run and at the bottom is the - (4)
input and output of the computer
What your desktop is doing is talking to the other machine the other computer through a serial line (this pops up when pressing ‘Serial’ (‘S’ in USB’) and if machine prints something it outputs in serial terminal
If you enter some text, it will go back to the other computer
Can reload things by saying Control D
Explain this code that we will put in muEditor line by line - (10)
import time: This line imports the time module, which provides various time-related functions.
import board: This line imports the board module, which provides access to the pins on the microcontroller board.
import neopixel: This line imports the neopixel module, which allows control of NeoPixel LEDs.
led = neopixel.NeoPixel(board.NEOPIXEL, 1): This line creates a NeoPixel object named ‘led’ using the neopixel library. It specifies that the LED is connected to the pin labeled NEOPIXEL on the microcontroller board, and there is only one LED.
led.brightness = 0.3: This line sets the ongoing brightness of the LED to 30% of its maximum brightness.
while True:: This line starts an infinite loop that will continuously execute the code block that follows.
led[0] = (255, 0, 0): This line sets the color of the LED to red. The NeoPixel library represents colors as tuples of three integers, representing the amount of red, green, and blue respectively. Here, (255, 0, 0) represents full red, no green, and no blue.
time.sleep(0.5): This line pauses the execution of the program for 0.5 seconds, causing a half-second delay.
led[0] = (0, 0, 0): This line turns off the LED by setting its color to black. In the NeoPixel library, (0, 0, 0) represents no red, no green, and no blue, effectively turning off the LED.
time.sleep(0.5): This line again pauses the execution of the program for 0.5 seconds, creating another half-second delay before the loop repeats.
What would this code effectively do?
The board will automatically reboot (thanks to the magic of muEditor) and a red light should blink on and off.
led.brightness = 0.99 would make.. - (2)
Setting the LED brightness to 0.99 makes the LED nearly at its maximum brightness.
In the NeoPixel library, the brightness attribute ranges from 0 (off) to 1 (full brightness).
Code: Setting both to be the same - (2)
time.sleep(0.5)
time.sleep(0.5)
Setting both time.sleep()
calls to the same duration, such as 0.5 seconds each, creates a square wave pattern with a 50% duty cycle.
This means the LED blinks on and off at regular intervals, with each state lasting for the same amount of time.
If I alter duty cycle by having - (2)
time.sleep(0.8)
time.sleep(0.2)
By setting time.sleep(0.8)
for the on state and time.sleep(0.2)
for the off state, the duty cycle of the square wave pattern is altered.
The LED will be on for a longer duration compared to being off, resulting in an increased duty cycle.
If you divide time.sleep by 10 , LED will flicker
faster
Explain what this code would do if we put in muEditor of file code.py? - (13)
import time: Imports the time module, which provides various time-related functions.
import board: Imports the board module, which provides access to the pins on the microcontroller board.
import math: Imports the math module, which provides mathematical functions. - importing another library to do maths
import neopixel: Imports the neopixel module, which allows control of NeoPixel LEDs.
led = neopixel.NeoPixel(board.NEOPIXEL, 1): Initializes a NeoPixel object named ‘led’ using the neopixel library. It specifies that the LED is connected to the pin labeled NEOPIXEL on the microcontroller board, and there is only one LED.
led.brightness = 0.3: Sets the ongoing brightness of the LED to 30% of its maximum brightness.
freq=2: Sets the frequency of the sinusoidal wave to 2 Hz.
startTime=time.monotonic(): returns the current elapsed time since the device was turned on in second using time.monotonic()
while True:: Starts an infinite loop that will continuously execute the code block that follows.
eTime=time.monotonic()-startTime: Calculates the elapsed time since the loop started using time.monotonic() in seconds
val=int(math.sin(eTime2freq3.1415)127+128): Calculates the brightness value for the LED based on a sinusoidal function. math.sin() calculates the sine of the input value (in radians), and the result is scaled to fit the range of NeoPixel brightness values (0-255). - basically calculating sine based on what the current elapsed time is (‘eTime’)
led[0] = (val,val,val): Sets the color of the LED to a grayscale value determined by ‘val’. This creates a pulsating effect from black to white based on the sine function - RBG all the same - black to white
time.sleep(.05): Pauses the execution of the program for 0.05 seconds, creating a delay between each iteration of the loop. This controls the speed of the pulsating effect.
What would happen to the LED?
The LED brightness would pulsate in a sinusoidal pattern, transitioning from black to white and back again, at a frequency of 2 Hz.
How to make the LED pulsate a bit slower? - (2)
To make the LED pulsate slower, adjust the frequency of the sinusoidal wave.
By changing the value of freq
to a lower number, such as 0.5 Hz, the LED will pulsate at a slower rate, resulting in a the LED will pulsate at a slower rate, resulting in a slower transition between brightness levels, with one cycle occurring every 2 seconds or freq to 0.25 within a very slow transition between brightness levels, with one cycle occurring every 4 seconds.
To make LED pulsate faster then change freq variable to values like - (2)
To make the LED pulsate faster, increase the frequency of the sinusoidal wave. By changing the value of freq
to a higher number, such as 2 Hz, the LED will pulsate at a faster rate, resulting in a quicker transition between brightness levels, with two cycles occurring every second.
OR To make the LED pulsate even faster, further increase the frequency of the sinusoidal wave. By changing the value of freq
to a higher number, such as 5 Hz, the LED will pulsate at a rapid rate, resulting in a very quick transition between brightness levels, with five cycles occurring every second.
If you change led[0] to not be all val but instead be
led[0] = (val, 0, val) then… - (2)
By modifying the LED color to (val, 0, val), you’re creating shades of purple, as it mixes red and blue while keeping green constant at 0.
This changes the LED’s color from grayscale to various shades of purple, transitioning in a sinusoidal pattern as the brightness value (val
) changes over time.
If you change led[0] to different stuff like:
led[0] = (val, 0, 0) - (3)
By setting led[0] = (val, 0, 0)
- Adjusts LED brightness, creating red pulsating from off to bright red.
led[0] = (0, val, 0) - Adjusts LED brightness, creating green pulsating from off to bright green.
led[0] = (0, 0, val) - Adjusts LED brightness, creating blue pulsating from off to bright blue.
In this code, we set to muEditor, we doing something super fancy, such as setting each R,G,B component at slightly different frequency and as they drift apart and together in phase, you should see the LED make all the different possible colours like a rainbow and pulsate at different colours
Explain this code line by line - (9)
Imports necessary modules: import time
, import board
, import neopixel
, and import math
.
-
Defines frequencies and constants:
f1=1.1
,f2=1.2
,f3=1.3
, andpi=3.1415
. -
Initializes NeoPixel object:
led = neopixel.NeoPixel(board.NEOPIXEL, 1)
. -
Sets LED brightness:
led.brightness = 0.3
. -
Records the start time:
startTime=time.monotonic()
. -
Starts an infinite loop:
while True:
. -
Calculates elapsed time:
thisTime=time.monotonic()-startTime
. -
Computes brightness values for RGB components:
a1=(math.sin(thisTime*2*pi*f1)*127+128)
a2=(math.sin(thisTime*2*pi*f2)*127+128)
-
a3=(math.sin(thisTime*2*pi*f3)*127+128)
.
-
Sets LED color:
led[0] = (a1,a2,a3)
.
The thing that determines how quickly colours change is
difference between the three different frequencies: f1,f2,f3 not the frequencies themselves
What happens setting all the different frequencies close together? f1,f2,f3? - (2)
f1=1.17
f2=1.2
f3=1.22
By making the frequencies closer together, such as setting f1=0.5, f2=0.6, and f3=0.7, the LED’s color modulation (colour shift) occurs at a slower rate.
This adjustment results in a smoother color transition with less noticeable changes, as the frequencies drift apart and together at a slower pace.
If you open the plotting panel:
It plots the data( numbers) it receives from the computer board
muEditor has a built-in plotter that will plot numbers it receives on the
serial line (output) if you send them as tuples (enclosed in round brackets like this: (10,20,30)
muEditor has a built-in plotter that will plot numbers it receives on the serial line if you send them as tuples (enclosed in round brackets like this: (10,20,30). For example, try this code and switch to the plotter mode:
Explain this code line by line - (7)
Imports necessary modules: import time
and import random
are used to import modules providing time-related functions and random number generation, respectively.
-
Starts an infinite loop:
while True:
initiates a loop that will run indefinitely. -
Introduces a pause:
time.sleep(0.05)
introduces a 0.05-second pause between iterations of the loop. This pause prevents flooding the serial line with data. -
Generates random temperature data:
random.randint()
is used to generate random integers representing temperature readings.- The first temperature (
random.randint(0, 100)
) is generated within the range 0 to 100, representing temperatures between 0°C and 100°C. - The second temperature (
random.randint(-100, 0)
) is generated within the range -100 to 0, representing temperatures between -100°C and 0°C. - The third temperature (
random.randint(-50, 50)
) is generated within the range -50 to 50, representing temperatures between -50°C and 50°C.
- The first temperature (
-
Prints temperature data:
print()
function is used to print the generated temperature data as tuples(temperature1, temperature2, temperature3)
to the serial line.
What is the output of this code? - (4)
The code is paused in while loop for 0.05 s
This code will produce three random numbers (stored in tuples) and plots them
Then goes stop of code and repeats that
These tuples of random numbers can be plotted using a serial plotter tool in the development environment.”
It prints the output because The way in which it gets the numbers out of the device is making them as a tuple , the brackets and separate them by comma
meaning…
- (3)
“The ‘device’ refers to the RP2040 microcontroller.
It generates the random numbers as tuples, encapsulating them within parentheses and separating them by commas.
This formatting ensures that the numbers are structured as a tuple before being transmitted through the serial line to the computer.”
The RP2040 has a built-in thermometer that will read the temperature. You can read this thermometer like this: - (2)
“This code snippet utilizes the microcontroller module to access the built-in thermometer of the RP2040 microcontroller.
Specifically, it reads the temperature using the cpu.temperature attribute, which retrieves the temperature of the RP2040 microcontroller itself, and assigns the temperature value to the variable temp.”
Explain this code - (7) (remove dot at the end)
-
Accessing Microcontroller Temperature: The code utilizes the
microcontroller
module to access the built-in thermometer of the RP2040 microcontroller. Specifically, it reads the temperature usingmicrocontroller.cpu.temperature
. -
Storing Temperature in Variable: The temperature value is read and stored in the variable
temp
. -
Sending Temperature as Tuple: The temperature value stored in
temp
is sent out as a tuple along with reference values of 0 and 37.5°C. This tuple is printed to the output. -
Looping Continuously: The code runs in an infinite loop (
while True:
) to continuously read and send temperature data. -
Introducing Pause:
time.sleep(0.1)
introduces a short pause of 0.1 seconds between each iteration of the loop to prevent overwhelming the serial line. -
Temperature Variation: By placing the device in hand, the temperature sensed by the microcontroller may vary, leading to changes in the temperature readings stored in
temp
. - Visualizing Data in muEditor: The additional reference points of 0 and 37.5 help muEditor to autoscale the plotter for better visualization of the temperature data.
Explain this code - (6)
These lines import necessary modules: time for time-related functions, microcontroller for accessing microcontroller-specific functionalities, neopixel for controlling NeoPixel LEDs, and board for accessing pin mappings. - importing at top
This function create_colormap(n) generates a colormap with n steps, transitioning from blue to green to red. It loops over a range of n values and calculates RGB values based on the current step. The colors transition from blue to green for the first half of steps and from green to red for the second half. - def function
This line initializes a NeoPixel object led to control the onboard LED connected to the pin NEOPIXEL. - led = neopixel.NeoPixel(board.NEOPIXEL, 1)
These lines define parameters: nSteps specifies the number of steps in the colormap, while minTemp and maxTemp set the temperature range to measure over. - nSteps = 20
minTemp = 32.0, maxTemp = 42.0
This line calls the create_colormap() function to generate the colormap based on the specified number of steps - cMap = create_colormap(nSteps)
while true loop - This block of code runs in an infinite loop (while True:) to continuously monitor the temperature.
time.sleep(1) introduces a 1-second delay between temperature readings to avoid flooding the CPU.
temp = microcontroller.cpu.temperature reads the temperature from the microcontroller.
index calculates the index within the colormap based on the temperature reading.
Conditional statements ensure that the calculated index stays within the valid range.
led[0] = cMap[int(index)] sets the color of the onboard LED based on the colormap and the calculated index.
print((0, temp, 37)) prints the current temperature, along with reference values of 0°C and 37°C, as a tuple.
What does this code achieve? - (3)
We can make the RP2040 into a very primitive ‘standalone’ thermometer.
Write code based on the two examples above to set the LED colour based on the temperature. The tricky bit here is working out the colours. We want to set the colours over a range from about 30 to 42c with 30 being ‘blue, 37 (ish) being ‘green’ and 42 being red.
Probably the easiest way to do this is to make three lists of numbers for the R, G anb B LEDs. They will go from (255 ->0->0) for B, (0->255->0) for G and (0->0->255) for R with 200 numbers or so in each range. Then we will pick the R,G,B values based on the current temperature.
Explain the def function - (6)
-
Function Definition: The
create_colormap()
function is defined to generate a colormap with a specified number of steps (n
). -
Colormap Initialization: An empty list
colormap
is initialized to store the RGB values of each step in the colormap. -
Looping Over Range: The function iterates over a range of values from 0 to
n-1
using afor
loop. -
Color Calculation: Depending on the value of
i
, the function calculates the RGB values for each step of the colormap.- For values of
i
less thann // 2
, it calculates the green component (g
) based on the ratio ofi
to half ofn
, and the blue component (b
) as the complement to 255. - For values of
i
greater than or equal ton // 2
, it calculates the red component (r
) based on the ratio of the difference betweeni
and half ofn
to half ofn
, and the green component (g
) as the complement to 255. The blue component (b
) is set to 0.
- For values of
-
Appending to Colormap: The calculated RGB values are appended to the
colormap
list as tuples(r, g, b)
. - Returning Colormap: Finally, the function returns the generated colormap.