Raspberry Pi(Raspbian)で写真を撮るプログラムを作る
はじめに
Raspberry Pi(Raspbian)で写真を撮るプログラムの紹介です。
カメラモジュールの準備方法は下記を参照して下さい。
- Raspberry Pi(Raspbian)で写真を撮る方法 - Qiita
必要なもの
- RaspbianがインストールされているRaspberry Pi
- Raspberry Pi用のカメラモジュール
- ブレッドボード
- タクトスイッチ
- ジャンパー線(オス/メス)x2
配線
GPIOとGNDならどこでも可ですが、今後の拡張性などを考えるとGPIOのみのピン(3, 5, 8, 10, 19, 21, 23, 24, 25以外)を使う方が無難だと思います。
この投稿では37(GPIO26), 39(GND)ピンを使用しています。
プログラム
camera.py
#Import Files
import RPi.GPIO as GPIO
import picamera
import time
#GPIO Settings
GPIO.setmode(GPIO.BCM)
GPIO.setup(26, GPIO.IN, pull_up_down=GPIO.PUD_UP)
#Camera Settings
CAM_DIR = "/home/pi/python/_photo/"
camera = picamera.PiCamera()
#Main
try:
while True:
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
camera.capture(save_dir_filename)
except KeyboardInterrupt:
GPIO.cleanup()
解説
- スイッチの制御に使用する
RPi.GPIO
ライブラリをインポートする
- Raspberry Piのカメラモジュールの制御に使用する
picamera
ライブラリをインポートする
- 時間を取得するために使用する
time
ライブラリをインポートする
- GPIOのモードをBCMに設定する(物理的なピン番号ではなく、GPIO**を使用する)
- GPIO26を入力端子に設定し、状態をプルアップ(Hi)にする(Hi=OFF, Low=ON)
-
CAM_DIR
に保存先のディレクトリを設定する
- PiCameraクラスのインスタンスを生成する
- スイッチが入力されるのを待つ必要があるので
while True:
で無限ループさせる
- スイッチが押されたら(GPIO26がLowになったら)写真を撮る処理を行う
-
time.strftime
でスイッチが押された時の日時を取得する
-
time.strftime
で取得した日時+拡張子(.jpeg)をファイル名にする
-
CAM_DIR
で指定したディレクトリとファイル名を連結させる
-
camera.capture
で写真を撮る
-
CAM_DIR
で指定したディレクトリに写真を保存する
- 解説9に遷移 or プログラムが終了するのを待つ
- Control+Cが押されたらGPIOを解放してプログラムを終了する
プログラムを実行してみる
- プログラムを実行する
- スイッチを押す
-
CAM_DIR
で指定したディレクトリに写真が保存される
- スイッチを押したら写真を撮るプログラム完成
- ファイル名が固定ではないので何回写真を撮ってもデータが上書きされない
写真が何枚も撮れてしまう問題の対処法(1)
camera.py
#Main
try:
while True:
time.sleep(0.1)
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
cam.capture(save_dir_filename)
except KeyboardInterrupt:
GPIO.cleanup()
#Import Files
import RPi.GPIO as GPIO
import picamera
import time
#GPIO Settings
GPIO.setmode(GPIO.BCM)
GPIO.setup(26, GPIO.IN, pull_up_down=GPIO.PUD_UP)
#Camera Settings
CAM_DIR = "/home/pi/python/_photo/"
camera = picamera.PiCamera()
#Main
try:
while True:
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
camera.capture(save_dir_filename)
except KeyboardInterrupt:
GPIO.cleanup()
- スイッチの制御に使用する
RPi.GPIO
ライブラリをインポートする - Raspberry Piのカメラモジュールの制御に使用する
picamera
ライブラリをインポートする - 時間を取得するために使用する
time
ライブラリをインポートする - GPIOのモードをBCMに設定する(物理的なピン番号ではなく、GPIO**を使用する)
- GPIO26を入力端子に設定し、状態をプルアップ(Hi)にする(Hi=OFF, Low=ON)
-
CAM_DIR
に保存先のディレクトリを設定する - PiCameraクラスのインスタンスを生成する
- スイッチが入力されるのを待つ必要があるので
while True:
で無限ループさせる - スイッチが押されたら(GPIO26がLowになったら)写真を撮る処理を行う
-
time.strftime
でスイッチが押された時の日時を取得する -
time.strftime
で取得した日時+拡張子(.jpeg)をファイル名にする -
CAM_DIR
で指定したディレクトリとファイル名を連結させる -
camera.capture
で写真を撮る -
CAM_DIR
で指定したディレクトリに写真を保存する - 解説9に遷移 or プログラムが終了するのを待つ
- Control+Cが押されたらGPIOを解放してプログラムを終了する
プログラムを実行してみる
- プログラムを実行する
- スイッチを押す
-
CAM_DIR
で指定したディレクトリに写真が保存される
- スイッチを押したら写真を撮るプログラム完成
- ファイル名が固定ではないので何回写真を撮ってもデータが上書きされない
写真が何枚も撮れてしまう問題の対処法(1)
camera.py
#Main
try:
while True:
time.sleep(0.1)
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
cam.capture(save_dir_filename)
except KeyboardInterrupt:
GPIO.cleanup()
CAM_DIR
で指定したディレクトリに写真が保存される
#Main
try:
while True:
time.sleep(0.1)
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
cam.capture(save_dir_filename)
except KeyboardInterrupt:
GPIO.cleanup()
チャタリング対策のため、time.sleep(待ち時間)
の処理を追加する。
time.sleep(0.01)
で10ms、time.sleep(0.1)
で100ms、time.sleep(1)
で1s待つ。
待ち時間を長くするとスイッチを押しているのに反応しないように感じるため、100〜200ms程度が無難。
この方法だとスイッチを長押しした場合に何枚も写真が撮れてしまう問題が発生する。
短押しで1枚、長押しで連写とするのであれば問題ないが、長押しでも1枚としたい場合は別の対策が必要になる。
写真が何枚も撮れてしまう問題の対処法(2)
camera.py
#Main
try:
while True:
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
cam.capture(save_dir_filename)
time.sleep(1)
except KeyboardInterrupt:
GPIO.cleanup()
#Main
try:
while True:
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
cam.capture(save_dir_filename)
time.sleep(1)
except KeyboardInterrupt:
GPIO.cleanup()
time.sleep(待ち時間)
の処理を追加し、写真を撮る処理を行ってから一定時間は写真を撮る処理を行わないようにする。
この方法でも写真が何枚も撮れてしまう問題の対処法(1)
同様、スイッチを長押しした場合に何枚も写真が撮れてしまう問題が発生する。
写真が何枚も撮れてしまう問題の対処法(3)
camera.py
#Import Files
import RPi.GPIO as GPIO
import picamera
import time
#GPIO Settings
GPIO.setmode(GPIO.BCM)
GPIO.setup(26, GPIO.IN, pull_up_down=GPIO.PUD_UP)
#Camera Settings
CAM_DIR = "/home/pi/python/_photo/"
camera = picamera.PiCamera()
#Camera Function
def camera_func(x):
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
camera.capture(save_dir_filename)
#Interrupt
GPIO.add_event_detect(26, GPIO.FALLING, callback=camera_func)
#Main
try:
while True:
pass
except KeyboardInterrupt:
GPIO.cleanup()
-
#Main
内にあった写真を撮る処理
をcamera_func(x)
に分離
- スイッチを押したら
camera_func(x)
を実行するようGPIO.add_event_detect
を追加
-
while True:
内の処理が無くなったのでpass
を追加
#Import Files
import RPi.GPIO as GPIO
import picamera
import time
#GPIO Settings
GPIO.setmode(GPIO.BCM)
GPIO.setup(26, GPIO.IN, pull_up_down=GPIO.PUD_UP)
#Camera Settings
CAM_DIR = "/home/pi/python/_photo/"
camera = picamera.PiCamera()
#Camera Function
def camera_func(x):
if GPIO.input(26) == 0:
filename = time.strftime("%Y%m%d%H%M%S") + ".jpeg"
save_dir_filename = CAM_DIR + filename
camera.capture(save_dir_filename)
#Interrupt
GPIO.add_event_detect(26, GPIO.FALLING, callback=camera_func)
#Main
try:
while True:
pass
except KeyboardInterrupt:
GPIO.cleanup()
#Main
内にあった写真を撮る処理
をcamera_func(x)
に分離camera_func(x)
を実行するようGPIO.add_event_detect
を追加while True:
内の処理が無くなったのでpass
を追加上記の対策を行うことでスイッチ押下時のみ写真を撮るようになる。
参考
-
GPIO.FALLING
はスイッチ押下時に処理を行う
-
GPIO.RISING
はスイッチを離した時に処理を行う
GPIO.FALLING
はスイッチ押下時に処理を行うGPIO.RISING
はスイッチを離した時に処理を行うAuthor And Source
この問題について(Raspberry Pi(Raspbian)で写真を撮るプログラムを作る), 我々は、より多くの情報をここで見つけました https://qiita.com/Yuta_Chief/items/97192cd1f1b719538629著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .