30 minute projects part 2

By Russell Barnes. Posted

Want a quick project to do? Here are some more fun, short things to do with your Raspberry Pi!

In part two of our 30-minute projects, we look at Minecraft, alarms and even a stylophone using only spoons and paper clips. Read part one for more project ideas if you haven't already.

The full article can be found in The MagPi 39

TNT Run! A Minecraft game

One of the many amazing things about Raspberry Pis is that they have their own edition of Minecraft for free! And what’s even better, you can code it in Python using the Minecraft API! In the next 30 minutes you will create a game called TNT RUN, in which you start at one end of a long line of TNT and have to make it to the safe area without the TNT exploding in your face.

 Run for your life!

The Minecraft API gives us complete control over many elements of the game. This includes teleporting players around the world and displaying helpful messages to the screen. We are also able to place blocks automatically – not just one at a time, but as a three-dimensional collection of blocks.

This game will also include a block which is unique to Pi and Pocket editions: invisible bedrock. We use this block to keep the TNT from falling to the ground when lit, and as an invisible path leading to the safe area. You may find something strange about this block when you place it next to a non-invisible block, so try experimenting with that - you need to look directly into the invisible bedrock.

TNT also behaves differently in the Pi edition. Whereas in other editions you set off TNT with flint and steel, a fire charge or a flaming arrow, in the Pi edition you just need to hit it a couple of times with anything. However, you can’t just do this with any old TNT block: first, we need to set its block data value to an odd number (1, 3, 5, 7, or 9). Most blocks have a block data value and by changing this, it will alter the block’s behaviour. For example, when you set Nether Reactor Core’s block data value to 1, it appears in a red colour; if you set it to 2 then it will come out as a dark blue colour. We use these cool-looking blocks to mark where the teleporter is and as a part of the end podium. The teleporter function in the code is designed so that if you manage to get to a certain point along the line of TNT, it gives you a boost and teleports you forward.

When you create your Minecraft world, fly around it and find a cool location to create your TNT course (i.e. not when you are near a cliff or the end of the world). Your code takes the player’s position and constructs the TNT course, using this location as the starting point. When you run the code, make sure Minecraft is running, otherwise your code will give you a connection error.

Once you have finished the project, you can customise your own version of the TNT Run game by adding changes like making the row of TNT longer, or creating a fancier safe area. Also, when you’re connected to a network with other Raspberry Pis, you can join someone else’s world, create two lines of TNT and race to the safe areas simultaneously!

Code listing

# import all the necessary modules
from mcpi.minecraft import Minecraft
from mcpi import block
import time

# connect with the Minecraft world
mc=Minecraft.create()

# get the player’s position
pos=mc.player.getTilePos()

# check if the end of the world will engulf your #creation & then move you if you’re too close
if pos.z

Infrared Video Alarm

Requirements: PIR motion sensor, breadboard, 10kohm resister

PIR motion sensors are a common type of security device. Standing for ‘passive infrared’, these sensors normally lurk in the corner of a room and sometimes light up as you walk past. During the day they don’t tend to do anything, but sneak around at night and they may well set off the security alarm. In this project we’ll be hooking a PIR sensor up to the Raspberry Pi to trigger a Rickroll whenever someone walks past!

 A humble PIR sensor and a video file can help you create an excellent alarm

Using sensors

Smaller PIR motion sensors are an easily available component that can be attached to the Pi. In this project we used one (Product Code: 312) from Cool Components.

PIR sensors come with three wires. You attach one to the power, one to ground, and one to a GPIO pin. When you power up the PIR sensor, it takes a couple of seconds to get a snapshot of the default levels in the room. Then, if anything changes the infrared levels because a person has moved in front of the sensor, the alarm pin will go low.

Which cable is power, ground and alarm will vary on each device. On our PIR unit, if you look at the dome with the wires pointing towards you, the middle wire is ground, the right wire is alarm, and the left is live. The colours can vary but typically they will be red (live), black (ground), and brown (alarm). Check the instructions to find out which layout your model is using.

Speaking of the dome, that’s a Fresnel lens. This is used to magnify the infrared light and make the PIR sensor more effective. The actual infrared sensor is beneath it.

Connecting the PIR Sensor

You could hook up the PIR sensor directly to your Raspberry Pi, but it’s a good idea to connect it via a breadboard. Connect the live to the positive rail and the ground to the negative rail, and place the alarm cable into any spare pin.

Now connect the breadboard to the Raspberry Pi. Use a black jumper wire to connect GPIO GND (pin 6) to the negative rail, and a red jumper wire to connect GPIO 5V (pin 2) to the positive rail. Connect GPIO 17 (pin 11) to the same rail as the alarm cable.

So that’s our trigger set up: the PIR sensor will power up, set its levels to the current room, and monitor for any change. When it detects one, it will drop the input on GPIO 17 to low.

What we need now is a means to play our video clip.

Getting a video roll

You can play any video clip you want, or even use the Camera Module to record your own message, but we decided to go with Rick Astley’s Never Gonna Give You Up and build an automatic Rickroll alarm. We’re using a video in MP4 format that we bought from the iTunes Store; this is DRM-free and we transferred it to the Music folder on our Raspberry Pi using a USB thumb drive.

We’re going to play this file using omxplayer. You should have omxplayer installed as default in Raspbian Jessie – enter omxplayer --version to check it’s installed. If not, enter sudo apt-get update and then sudo apt-get install omxplayer.

Move into the folder with the video clip; we’ve placed ours in the Music folder as it’s a music video, but you can put yours into any folder. Now enter omxplayer -o hdmi [filename] to play the video clip. The -o hdmi option ensures that the audio is outputted through the HDMI output; it may work without this, but it’s best to include it just in case.

The video should start playing in a full-screen window on top of your desktop, or full-screen if you are in the command line. Omxplayer is a handy tool to have, and you can use it as a regular media player. Press P or SPACE to pause the video (and again to resume it), and use the + and - keys to increase or decrease the volume so your alarm is at the level you want. Press ESC when you’ve had enough of the video. Incidentally, you can use omxplayer -k to view all of the shortcut keys.

Now use mkdir to create a folder for the code, and use touch to create a file called piralarm.py. Use a text editor to add the code below, or clone it from GitHub. Make sure you change the [Media File] part to the name of your video clip.

# detects motion sensor from PIR Sensor Module attached to GPIO 17.
# change [MediaFile] in path to name of media file in Music folder.

import os
import RPi.GPIO as GPIO

GPIO.setmode(GPIO.BCM)

GPIO.setup(17, GPIO.IN)

while True:
    if GPIO.input(17):
        os.system(“omxplayer -o hdmi /home/pi/Music/[Media File].m4v”)

Enter python piralarm.py to arm and set your alarm. Now, when a person moves, they will trigger the code and play your video.

You’ll probably find the PIR sensor too effective at first. Some PIR motion sensors come with a potentiometer that can be used to adjust the sensitivity of the device. One it’s set to the correct level, you can leave it to trigger whenever anybody walks into your room

The Spoon-o-phone

Requirements: 20 large metal paper clips, a teaspon, M3 nut and bult, 22 jumper cables with female headers, 4 10-way header shell and 2 pieces of cardboard about 170x70mm

Create your own version of the classic Stylophone, without the need for any electronic components or soldering.

 A glamorous instrument for the maker

How it works

The paper clips are wired directly to some GPIO pins, and the spoon to a ground pin. The software sets the GPIO pins to be inputs, with the internal pull-up resistors enabled; they will normally read back as a logic 1. However, if the grounded spoon touches a paper clip, that input will now read as a logic low. When the code sees this, it will trigger the playing of a sample for that note. Like the original Stylophone, the Spoon-o-phone has a vibrato effect, turned on and off with a mouse click in the small on-screen window. With the vibrato effect on, a different set of samples are selected. You need a Model 2 or B+ Pi for this project as it needs 20 input pins, but you could make it with older Pi models if you cut down the range or omitted black notes.

Materials used

The Make your own Cable Kit was used for the crimped wires and shells, but any other method will do just fine. The cardboard back of an A4 writing pad is ideal; it has to be thin enough to take the paper clips. Make sure the holes on the shells are on the outside so you can change the wires over if you make a mistake. Fix the ground wire to the teaspoon with an M3 nut and bolt. Once the keyboard is finished and tested, tuck all the wires under the cardboard and make a sandwich by hot-melt-gluing another piece of cardboard to the underside.

 How to build your spoon-o-phone, click to enlarge

Software

Get the sound samples from the source or the GitHub. The code is written in Pygame, but uses a music system designed for continuous background audio: as the Stylophone samples are very short, they must be looped so a note can be played for as long as you hold the spoon on a clip.

The GPIO pins used are in the list pinList and can be shuffled about if you get your wiring wrong. The notes list contains the names of the sample files for each note, with a ‘v’ appended for vibrato. They all sit in a stylo_smpl directory at the same level as the main program. Small time.sleep delays are used to minimise any contact bounce effects on the input pins.

#!/usr/bin/python
# Spoon-o-phone - Stylophone emulator By Mike Cook - Sept 2015
import pygame, time, os
import wiringpi2 as io

pygame.init()
os.environ[‘SDL_VIDEO_WINDOW_POS’] = ‘center’
pygame.display.set_caption(“Stylophone”)
screen = pygame.display.set_mode([190,40],0,32)
pygame.mixer.quit()
pygame.mixer.init(
frequency=22050, size=-16, channels=2, buffer=512)
pygame.event.set_allowed(None)
pygame.event.set_allowed(
[pygame.MOUSEBUTTONDOWN,pygame.KEYDOWN,pygame.QUIT])
font = pygame.font.Font(None, 36) ; vibrato = False  
pinList = [21,26,20,19,16,13,6,12,5,11,7,8,9,25,10,24,
22,23,27,18] # GPIO pins
notes = [“a2”,”a#2”,”b2”,”c3”,”c#3”,”d3”,”d#3”,”e3”,”f3”,
”f#3”,”g3”,”g#3”,“a3”,”a#3”,”b3”,”c4”,”c#4”,”d4”,”d#4”,”e4”]

def main():
   initGPIO()
   print”Stylophone - By Mike Cook”
   drawWords(“vibrato off”,36,6)
   while True:
      checkForEvent()
      for pin in range (0,len(pinList)):
        if io.digitalRead(pinList[pin]) == 0:
           sound = getSample(pin)
           pygame.mixer.music.load(“stylo_smpl/”+sound+”.wav”)
           pygame.mixer.music.set_volume(1.0)
           pygame.mixer.music.play(-1,0.0)
           time.sleep(0.030)
           while io.digitalRead(pinList[pin]) == 0:
               pass
           pygame.mixer.music.fadeout(100)
           time.sleep(0.030) # debounce time
           
def getSample(number):
   sample = notes[number]
   if vibrato :
      sample +=”v”  
   return sample  
   
def initGPIO():
   try :
      io.wiringPiSetupGpio()
   except :
      print”start IDLE with ‘gksudo idle’               from command line”
      os._exit(1)
   for pin in range (0,len(pinList)):
      io.pinMode(pinList[pin],0) # make pin into an input
      io.pullUpDnControl(pinList[pin],2) # enable pull-up
      
def drawWords(words,x,y) :
        textSurface = pygame.Surface((len(words)*12,36))
        textRect = textSurface.get_rect()
        textRect.left = x ; textRect.top = y
        pygame.draw.rect(screen,(0,0,0),  
        (x,y,len(words)*12,26), 0)
        textSurface = font.render(
words, True, (255,255,255), (0,0,0))
        screen.blit(textSurface, textRect)
        pygame.display.update()
      
def terminate(): # close down the program
    pygame.mixer.quit() ; pygame.quit()
    os._exit(1)
 
def checkForEvent(): # keyboard commands
    global vibrato
    event = pygame.event.poll()
    if event.type == pygame.MOUSEBUTTONDOWN:
       vibrato = not vibrato
       if vibrato:
          drawWords(“vibrato on “,36,6)
       else:
          drawWords(“vibrato off”,36,6)
    if event.type == pygame.QUIT :
         terminate()
    if event.type == pygame.KEYDOWN :
       if event.key == pygame.K_ESCAPE :
          terminate()
             
# Main program logic:
if __name__ == ‘__main__’:    
    main()

From The MagPi store

Subscribe

Subscribe to the newsletter

Get every issue delivered directly to your inbox and keep up to date with the latest news, offers, events, and more.