Skip to content

Instantly share code, notes, and snippets.

@Evgenus
Created March 3, 2015 11:27
Show Gist options
  • Save Evgenus/970171a1665d5fe4690e to your computer and use it in GitHub Desktop.
Save Evgenus/970171a1665d5fe4690e to your computer and use it in GitHub Desktop.
import io
import time
import threading
import picamera
from PIL import Image
from PIL import ImageOps
# Create a pool of image processors
done = False
lock = threading.Lock()
pool = []
class ImageProcessor(threading.Thread):
def __init__(self):
super(ImageProcessor, self).__init__()
self.stream = io.BytesIO()
self.event = threading.Event()
self.terminated = False
self.start()
def run(self):
# This method runs in a separate thread
global done
while not self.terminated:
# Wait for an image to be written to the stream
if self.event.wait(1):
try:
self.stream.seek(0)
# Read the image and do some processing on it
image = Image.open(self.stream)
inverted_image = ImageOps.invert(image)
image.save("captured.jpg")
self.stream.seek(0)
inverted_image.save(self.stream, format="JPEG")
inverted_image.save("processed.jpg")
# Set done to True if you want the script to terminate
# at some point
#done=True
finally:
# Reset the stream and event
self.stream.seek(0)
self.stream.truncate()
self.event.clear()
# Return ourselves to the pool
with lock:
pool.append(self)
def streams():
while not done:
with lock:
if pool:
processor = pool.pop()
else:
processor = None
if processor:
yield processor.stream
processor.event.set()
else:
# When the pool is starved, wait a while for it to refill
time.sleep(0.1)
with picamera.PiCamera() as camera:
pool = [ImageProcessor() for i in range(4)]
camera.resolution = (640, 480)
camera.framerate = 30
camera.start_preview()
time.sleep(2)
camera.capture_sequence(streams(), use_video_port=True)
# Shut down the processors in an orderly fashion
while pool:
with lock:
processor = pool.pop()
processor.terminated = True
processor.join()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment