Raspberry Pi Pico W brings physical computing and the internet together and it’s never been easier. Let’s learn the basics by making a weather indicator
if the new Raspberry Pi Pico W’s wireless LAN capability has got you eager to start making but if you’re not sure where to start, you’re in the right place. We’re going to take a step-by-step look at simple components for inputs and outputs, connect them to Pico W, and then fetch data from the internet and display them. We’re going to do this without any of the difficulty of soldering, or even handling components, by using the SB Components Pico Breadboard kit. This PCB (printed circuit board) comes pre-populated with buttons and LEDs to make your introduction to electronics as simple as possible.
Pico preparation
A great facet of Raspberry Pi Pico W is its support for different languages. By uploading different ‘firmware’ (low-level code that translates for the RP2040 CPU),
Get ahead
To connect to the Pico Breadboard Kit, you will need to have headers soldered onto your Pico. If you do not have a Raspberry Pi Pico H (H for headers), then you need to buy a header kit and solder them yourself. These need to be facing downward so the smaller part of the header is poking through the top of Pico’s PCB on the RP2040 chip side. If soldering yourself, remember to be careful and start by soldering each end pin of the header block, then check everything is level. If not, you can melt the solder to move them into place, then solder all the ones in between.
Choosing a development environment
To write code for Raspberry Pi Pico W, you need to use a computer. Nearly any modern operating system will do, including Raspberry Pi OS. It’s possible to write code using a simple text editor, but it’s a lot easier (and faster) to use an IDE (integrated development environment). Don’t be put off by the fancy name – this is a text editor that understands what a Pico W is and can help transfer programs. On Raspberry Pi OS we recommend Thonny, but you can also use Visual Studio Code with the Pico-Go extension.
Testing time
It’s time to check everything is working. Connect your Raspberry Pi Pico W to your computer using a USB cable. Open up Thonny and look in the bottom right-hand corner. It should say something like ‘Python 3.7.9’. Click on this and, if Pico W has been recognized, you’ll see ‘MicroPython (Raspberry Pi Pico)’ as an option. Select this and you’ll see a welcome message on the bottom half of the screen. Click to the right of the ‘>>>’ prompt and type:
print('Hello') |
…followed by pressing RETURN. If you see ‘Hello’ displayed in response, you’ve just run your first program on your Pico W!
Understanding LEDs
Have a look at the SB Components prototype board. On the bottom-right are four LEDs (light-emitting diodes). These are one of the most common components used when beginning electronics, as we can make them light up and that’s cool! LEDs can be a little naughty and draw too much current if left unchecked, causing permanent damage. To stop this from happening, we need an in-line resistor to limit the flow of current. See the little black and silver squares above the LEDs? They are 330Ω resistors already in place that are perfect for the job, so we can wire everything up without worrying about damaging our LEDs
"We are using the RP2040’s built-in ‘pull-down’ resistor circuit which solves this problem"
Understanding buttons
On the left-hand side of the prototyping board are four buttons (and a buzzer, but we’ll get to that). Each button creates a circuit when the button is pressed down. Wiring these to your Raspberry Pi Pico W lets you detect when the button is pressed. Buttons can be tricky for a microcontroller to handle, as the input is so sensitive it can give inaccurate readings; you can even trigger it by putting your finger next to it. To prevent this, we are using the RP2040’s built‑in ‘pull-down’ resistor circuit which solves this problem. When it comes to coding, you’ll see how we make use of it.
Get wired
It’s time to assemble our circuit. Carefully insert the disconnected Raspberry Pi Pico W into the socket on the prototype board, with the USB end at the top. The LEDs and buttons connect to Pico W using jumper cables. Between the buttons and the LEDs, you’ll see two yellow sets of headers, clearly labeled. The jumper cables need to run from these to the GPIO pins on Pico W. If you’re wondering where the ground connection is, look at the top-right of the board. The GND header must have one wire connected to any of the GND pins on Pico W. Follow the wiring table (overleaf) carefully
Light up the LEDs
Having checked all your wiring carefully, connect Raspberry Pi Pico W to your computer. In Thonny, type the leds.py code listing into the upper window, and then click the ‘Run’ icon. When prompted, ask to save it on the Pico W and name it leds.py. The code will now be uploaded to Pico W. Do you see the LEDs coming on one by one? The code starts by telling Pico W which GPIO pins are connected and what they are for (in this case - output). Then we go into a loop: toggling the state of each pin, then waiting a second. If you want, have a play with the sequence or see if you can change the timings.
Push the button
To check the buttons, create a copy of the file you created in Step 8, and call it buttons.py. Remove the block starting while True:, then add the contents of the buttons.py code listing. Save and run the code. Try pressing the buttons one by one. Each one should now toggle its equivalent LED. This code uses ‘event’ or ‘interrupt’ handlers, blocks of code that run when a GPIO pin changes state. When a button is pressed, the code runs and changes the state of the LED. This is a fundamental part of physical computing. You are taking external input (the button) and creating output (the LED).
Simon says
You’ve now seen how Raspberry Pi Pico W can use code to respond to inputs by creating outputs. We could have wired the buttons directly to the LEDs to create a similar effect (and using the breadboard, you can try that!), but Pico W adds logic that would be hard to implement in raw circuitry alone. To demonstrate this, download memory.py from magpi.cc/memorypy. This is an extension of the code that turns our button script into a memory game. Run the code on your Pico W, and see if you can remember the sequence of LEDs by playing them back on the buttons. Don’t forget to review the code and see how it works!
"If you’re wondering where the ground is, look at the top-right of the board "
Get online
Now we have built our circuit, tested it, and played a game, let’s look at what makes Raspberry Pi Pico W so special. For our weather project, we need to connect to the internet, so let’s start with that. Create a new file called wifi.py and add the contents of the wifi.py listing (overleaf). Replace the SSID and password values with those for your own network. Now run the code on your Pico W using Thonny. Watch the console output and within a few seconds, you should get an IP address the announcement, meaning you’re on the internet!
A key step
We’re going to get some weather info to display on our prototype board. We’ll use openweathermap.org to supply information using an API call. This is just like getting a web page, except the information is returned in a way computers can easily understand (in this case JavaScript Object Notation, or JSON). Sign up for a free account on the site and, once logged in, go to
leds.py
from machine import Pin | |
import utime | |
# Make sure these are the pins connected to your LEDs! | |
leds = { | |
1: Pin(28, Pin.OUT), | |
2: Pin(27, Pin.OUT), | |
3: Pin(26, Pin.OUT), | |
4: Pin(22, Pin.OUT), | |
} | |
# Loop through the LEDs toggling each one then sleeping a second | |
while True: | |
for i, (k, led) in enumerate(leds.items()): | |
led.toggle() | |
utime.sleep_ms(1000) |
buttons.py
from machine import Pin | |
leds = { | |
1: Pin(28, Pin.OUT), | |
2: Pin(27, Pin.OUT), | |
3: Pin(26, Pin.OUT), | |
4: Pin(22, Pin.OUT), | |
} | |
# This function is trigged when any button is pressed | |
def button_handler(pin): | |
# This weird line determines which button was pressed | |
# (Not as easy as you'd think!) | |
button_pressed = int(str(pin)[4:6]) - 17 | |
print(str(button_pressed)) | |
leds[button_pressed].toggle() | |
# This is an efficient way of setting up all four buttons | |
# If we have a bug, we only have to fix it once! | |
for gpio_number in range(18, 22): | |
# Assign a pin to be a button and use the pull-down resistor | |
button = Pin(gpio_number, Pin.IN, Pin.PULL_DOWN) | |
# Trigger the button_handler function when pressed | |
button.irq(trigger=Pin.IRQ_RISING, handler=button_handler) |
‘API Keys’. One will have already been created for you (although it can take an hour or two to start working). Think of this as a password allowing you to access the service. Take a copy – you’re going to need it soon.
Talk about the weather
We’re going to make a request for the current weather. Download weather_1.py from magpi.cc/weather1py, then replace the three new variable values at the top with the API from the previous step and your desired latitude and longitude. Don’t know these? Just enter ‘lat and long for the town’ in a search engine, and you’ll get the answer. The ones in the code are for the Raspberry Pi Foundation in Cambridge. Run the code on your Raspberry Pi Pico W as before, and watch the console output. Here, we use the urequest library to request information from the API server.
Hooking up the buttons
We’ve got four buttons, so let’s pick out four key pieces of information. Each time we press a button, a request will be made to the API and the code will extract a useful piece of data from the request. We’re going to ask for temperature, wind speed, rain, and air quality index. This code is a little longer, so download weather_2.py from magpi.cc/weather2py and transfer it to your Raspberry Pi Pico W as before. Run the code and press each button. Watch the output in the console as you press the buttons.
"Enter ‘lat and long for the town’ in a search engine, and you’ll get the answer"
Lightening
We don’t have a screen (although you can add one if you want!), just four lights to show the data. What we’ll do is divide the results into ranges and light the appropriate amount of lights. For instance, If it’s really hot, all four LEDs will illuminate. Download weather_3.py from magpi.cc/weather3py and run it. Raspberry Pi Pico W will download the JSON data and extract our four data points and display them using the LEDs. Feel free to change the ranges if you wish.
Buzzin’
Calls to the internet can never be fully relied on to succeed. There are many things that can go wrong, from your internet connection is down to the API server having problems. We can catch these errors and signal to the user that there’s a problem. The next version of our code (weather_4.py from magpi.cc/weather4py) creates a short buzz on successful calls and a longer buzz if something went wrong. Keep getting errors? More details will be logged to the console.
Put it all together
Let’s bring the buttons and the LEDs together. Download our final code version, weather_5.py from magpi.cc/weather5py, and run it up as before. Now when you press each button, you can get an idea of whether it’s raining, sunny, hot, or windy! Take some time to walk through the code to see how we hunt through the data, and see what changes you can make! If you would like to run this independently without a computer attached, just rename this file to main.py. Any file of that name will run automatically when power has been applied to Raspberry Pi Pico W
Make it your own
In this tutorial, we’ve learned how to control LEDs, listen to button presses, and combine those with internet data. Feel free to alter the code to show different things. Maybe you could periodically check the API and sound the buzzer when it’s raining? This is just the beginning! For such a low-cost device, the capabilities of Raspberry Pi Pico W go much further than switches and lights. You can add all kinds of sensors, screens, and even motors with the right kit. Get an electronics kit and use the breadboard to add more features. There are endless tutorials out there to help you along. Be curious and have fun!
# Based on code by Pete Gallagher | |
# https://www.petecodes.co.uk/ | |
import time | |
import network | |
ssid = '<Your Wifi Network Name>' | |
password = '<Your Wifi Password>' | |
wlan = network.WLAN(network.STA_IF) | |
wlan.active(True) | |
wlan.connect(ssid, password) | |
# Wait for connect or fail | |
max_wait = 10 | |
while max_wait > 0: | |
if wlan.status() < 0 or wlan.status() >= 3: | |
break | |
max_wait -= 1 | |
print('Waiting for connection...') | |
time.sleep(1) | |
# Handle connection error | |
if wlan.status() != 3: | |
raise RuntimeError('Network connection failed') | |
else: | |
print('Connected') | |
status = wlan.ifconfig() | |
print( 'IP Address = ' + status[0] ) | |
# Important to tidy up the connection | |
wlan.disconnect() |