Skip to content

Instantly share code, notes, and snippets.

@martinohanlon
Last active August 29, 2022 20:53
Show Gist options
  • Save martinohanlon/52a7557a91d9e5b353a278447fbacc34 to your computer and use it in GitHub Desktop.
Save martinohanlon/52a7557a91d9e5b353a278447fbacc34 to your computer and use it in GitHub Desktop.
a guizero app which uses the picamera to make stop motion gifs
# This is a simple gui for creating stop motion animations using the Pi camera
# martin@ohanlonweb.com
# stuffaboutcode.com
# Instructions:
# - Connect a camera module
# - Enable the camera (Menu > Preferences > Raspberry Pi Configuration, Interfaces, Camera)
# - Install the relevant modules, open a terminal (Menu > Accessories > Terminal) and run:
# - sudo pip3 install guizero
# - sudo pip3 install imageio
# - Run the program
# - python3 guizero_stopmotion.py
from guizero import App, Box, Picture, Text, PushButton, info
from io import BytesIO
import imageio
from PIL import Image
from picamera import PiCamera
from picamera.array import PiRGBArray
from time import time
def update_gui():
if len(animation.images) == 0:
instructions.value = "take your first image"
pic_button.enable()
del_button.disable()
reset_button.disable()
save_button.disable()
animation.hide()
else:
# build gif from animation.images
# write the animated gif to BytesIO object
gif_output = BytesIO()
imageio.mimsave(gif_output, animation.images, format="gif")
# set the animation to a PIL image of the gif
animation.image = Image.open(gif_output)
instructions.value = "take another image"
# enable the gui
pic_button.enable()
del_button.enable()
reset_button.enable()
save_button.enable()
animation.show()
def take_pic():
# take a picture
pic_button.disable()
instructions.value = "adding ..."
gui.tk.update()
# capture the image
camera.capture(camera_output, "rgb")
# append the camera image to the list as a numpy array
animation.images.append(camera_output.array)
# truncate the camera output now we have dealt with it
camera_output.truncate(0)
update_gui()
def del_pic():
instructions.value = "deleting ..."
gui.tk.update()
animation.images.pop()
update_gui()
def reset():
animation.images = []
update_gui()
def save():
file_name = "animation_{}.gif".format(time())
imageio.mimsave(
file_name,
animation.images,
format="gif")
info("save", "animation saved as {}".format(file_name))
# create the camera
camera = PiCamera(resolution="640x480")
camera_output = PiRGBArray(camera)
# create the gui
gui = App(title="stop motion animation")
controls = Box(gui, layout="grid")
instructions = Text(gui)
pic_button = PushButton(
controls,
text="take image",
command=take_pic,
grid=[0,0])
del_button = PushButton(
controls,
text="delete last",
command=del_pic,
grid=[1,0])
reset_button = PushButton(
controls,
text="reset",
command=reset,
grid=[2,0])
save_button = PushButton(
controls,
text="save",
command=save,
grid=[3,0])
animation = Picture(gui)
animation.images = []
update_gui()
gui.display()
@dglaude
Copy link

dglaude commented Jun 18, 2018

I have the feeling that you keep the default auto value for exposure.
As far as I know, you want to have a fixed value that is identical for all the frame from your stop motion.
Otherwise, fixed element in the picture might change "color" just because the average light of the scene.
To avoid that, best would be to take a first picture in auto mode, get the chosen exposure and fix it to that value for all picture.

Full disclosure, I never player much with camera on the Pi and the last time I did stop motion was likely 30 years ago in the analog world...

Regards

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment