PRE2017 3 11 Python Code
Jump to navigation
Jump to search
QR scanner with cylinder and platform response
The main script scans QR codes in front of the camera, opens the cylinder and moves the platform down if a correct code is presented.
Import required packages
#!/usr/bin/python from pyzbar.pyzbar import decode # QR reader from PIL import Image # Image reader import cv2 # Image reader import RPi.GPIO as GPIO # GPIO pin control import time # Posibility to delay import signal # Cleanup when ending script import sys # Needed to stop script if no camera
Set up constants
pin_s1 = 29 # Continuous servo 1 pin_s2 = 33 # Continuous servo 2 freq = 50 # Continuous servo frequency [Hz] s1left = 5.00 # 100% velocity to left s1center = 6.70 # no movement s1right = 8.00 # 100% velocity to right s2left = 5.00 # 100% velocity to left s2center = 6.60 # no movement s2right = 8.00 # 100% velocity to right cyldelay = 2 # Time it takes for cylinder to rotate dropdelay = 5 # Time it takes to drop package pauzedelay = 2 # Time between cylinder rotation and platform movement platformdelay = 2 # Time it takes for platform to move down imgname = "image2.jpg" # File frame is temporarily saved in
Imports access codes
# Imports allowed QRcodes
passcodelist = []
with open("authcodes") as file:
passcodelist = [line.strip() for line in file]
Stops the script safely if CTRL+C is pressed
# Releases pins when script is interrupted
def end_run(signal,frame):
global running
print("Ctrl+C captured, ending script")
running = False
servo1.stop()
servo2.stop()
GPIO.cleanup()
# Runs end_run if ctrl+C is clicked
signal.signal(signal.SIGINT, end_run)
Takes a picture with the camera
# Takes picture from camera, reads and evaluates QRcode def QRscanner(passcodelist, camslot): camera = cv2.VideoCapture(camslot) # Initializes camera viewer grabbed, im = camera.read() # Reads figure
Checks if a picture is taken, and if it is not, it looks for other cameras or stops the script
if not grabbed: # Searches for working camera
if camslot < 5:
camstr = "No camera connected in slot: " + str(camslot)
print(camstr)
camslot = camslot + 1
return False, camslot
else:
print("No camera connected")
servo1.stop()
servo2.stop()
GPIO.cleanup()
sys.exit()
Reads QR-codes in the image and checks if a correct code is presented
cv2.imwrite(imgname,im) # Converts image to jpg
img = Image.open(imgname) # Reads jpg
decodedObjects = decode(img) # Decodes image
for obj in decodedObjects: # Makes sure every code is read
qrdata = obj.data # Reads the alphanumerical code
for passcode in passcodelist:
if passcode in qrdata: # Verifies if code is legit
print("Correct code, cylinders start opening")
return True, camslot
else:
print("Wrong code")
return False, camslot
Sets up the output pins that control the servos
GPIO.setmode(GPIO.BOARD) # Board numbering sceme pins GPIO.setup(pin_s1, GPIO.OUT) # Sets pins as output GPIO.setup(pin_s2, GPIO.OUT) servo1 = GPIO.PWM(pin_s1, freq) # Assigns frequency to pins servo2 = GPIO.PWM(pin_s2, freq) servo1.start(s1center) # Starts servos in neutral position servo2.start(s2center)
Sets up variables, starts the script, and runs the QR-code reader until correct code is presented or CTRL+C is pressed
camslot = 0 # Default camera slot
running = True
print("Program Running, provide QR-code")
while running:
rightcode, camslot = QRscanner(passcodelist, camslot) # Runs QR-reader
Opens/closes the cylinder and moves down the platform
if rightcode:
servo1.ChangeDutyCycle(s1right) # Cylinders open
time.sleep(cyldelay) # Duration of cylinder movement
servo1.ChangeDutyCycle(s1center) # Cylinders stop moving
print("Cylinders are open, package can be dropped")
time.sleep(dropdelay) # Duration of package dropping
print("Package dropped, cylinders start closing")
servo1.ChangeDutyCycle(s1left) # Cylinders close
time.sleep(cyldelay) # Duration of cylinder movement
servo1.ChangeDutyCycle(s1center) # Cylinders stop moving
print("Cylinders are closed")
time.sleep(pauzedelay) # Time buffer
print("Platform starts moving down")
servo2.ChangeDutyCycle(s2right) # Platform moves down
time.sleep(platformdelay) # Duration of platform movement
servo2.ChangeDutyCycle(s2center) # Platform stops moving
print("Platform stopped moving down, new code can be scanned")
Calibrator
In order to make sure that the servos rotated exactly long enough, a python script was written which starts and stops the servos on the press of a button:
import RPi.GPIO as GPIO # GPIO pin control
import signal # Cleanup when ending script
# Releases pins when script is interrupted
def end_run(signal,frame):
global running
print("Ctrl+C captured, ending script")
running = False
servo1.stop()
servo2.stop()
GPIO.cleanup()
# Runs end_run if ctrl+C is clicked
signal.signal(signal.SIGINT, end_run)
pin_s1 = 29 # Continuous servo 1
pin_s2 = 33 # Continuous servo 2
freq = 50 # Continuous servo frequency [Hz]
s1left = 5.00 # 100% velocity to left
s1center = 6.70 # no movement
s1right = 8.00 # 100% velocity to right
s2left = 5.00 # 100% velocity to left
s2center = 6.60 # no movement
s2right = 8.00 # 100% velocity to right
GPIO.setmode(GPIO.BOARD)
GPIO.setup(pin_s1,GPIO.OUT)
GPIO.setup(pin_s2,GPIO.OUT)
servo1 = GPIO.PWM(pin_s1,freq)
servo2 = GPIO.PWM(pin_s2,freq)
servo1.start(s1center) # Starts servos in neutral position
servo2.start(s2center)
running = True
print("1(l,c,r), 2(l,c,r): ")
while running:
n = raw_input()
if n == "1l":
servo1.ChangeDutyCycle(s1left)
elif n == "1c":
servo1.ChangeDutyCycle(s1center)
elif n == "1r":
servo1.ChangeDutyCycle(s1right)
elif n == "2l":
servo2.ChangeDutyCycle(s2left)
elif n == "2c":
servo2.ChangeDutyCycle(s2center)
elif n == "2r":
servo2.ChangeDutyCycle(s2right)
Platform Resetter
After the storage box is emptied, the platform has to move back up, which is done with the following python code:
import RPi.GPIO as GPIO # GPIO pin control
import time
import signal # Cleanup when ending script
# Releases pins when script is interrupted
def end_run(signal,frame):
print("Ctrl+C captured, ending script")
servo2.stop()
GPIO.cleanup()
# Runs end_run if ctrl+C is clicked
signal.signal(signal.SIGINT, end_run)
pin_s2 = 33 # Continuous servo 2
freq = 50 # Continuous servo frequency [Hz]
s2left = 5.00 # 100% velocity to left
platformdelay = 4.25 # Time it takes for platform to move down
GPIO.setmode(GPIO.BOARD)
GPIO.setup(pin_s2, GPIO.OUT)
servo2 = GPIO.PWM(pin_s2, freq)
servo2.start(s2left)
time.sleep(platformdelay)
servo2.stop()
GPIO.cleanup()
Cylinder Resetter
If any failures occur when the cylinder is opened, this script can be activated to close the cylinder:
import RPi.GPIO as GPIO # GPIO pin control
import time # Posibility to delay
import signal # Cleanup when ending script
pin_s1 = 29 # Continuous servo 1
freq = 50 # Continuous servo frequency [Hz]
s1left = 5.00 # 100% velocity to left
s1center = 6.70 # no movement
s1right = 8.00 # 100% velocity to right
cyldelay = 1.35 # Time it takes for cylinder to rotate
# Releases pins when script is interrupted
def end_run(signal,frame):
global running
print("Ctrl+C captured, ending script")
running = False
servo1.stop()
servo2.stop()
GPIO.cleanup()
# Runs end_run if ctrl+C is clicked
signal.signal(signal.SIGINT, end_run)
GPIO.setmode(GPIO.BOARD) # Board numbering sceme pins
GPIO.setup(pin_s1, GPIO.OUT) # Sets pins as output
servo1 = GPIO.PWM(pin_s1, freq) # Assigns frequency to pins
servo1.start(s1left) # Starts servos in neutral position
time.sleep(cyldelay)
servo1.stop()
GPIO.cleanup()