こんにちは、ヒガシです。
このページでは、以下の動画内にある物体の重心位置の履歴を
こんな感じでグラフ化してみようと思います。
それではさっそくやっていきましょう!
必要なライブラリ一覧
今回は以下のライブラリを使用します。
★openCV
★numpy
★matplotlib
インストールしていないものがあればインストール作業から始めましょう。
openCVに関しては以下の記事で紹介していますので、参考にしてみてください。
【Python-OpenCV】インストール方法、バージョン確認、使用時の注意点
動画ファイルから各フレームの画像を切り出す方法
今回は動画ファイルの各フレームをまずは画像化し、その画像の中に写っている物体の重心を算出する、という作業を動画の全フレームに対して繰り返すことで、物体の重心位置履歴を取得します。
というわけでまずは動画を各フレームごとに画像化するスキルが必要になります。
その作業に関しては以下でやり方を詳細解説していますので、興味があればこちらも参考にしてみてください。
【Python-openCV】動画(gif,mp4)ファイルからフレームごとの画像を出力!
画像内物体の重心位置を算出する方法
先ほど紹介したスキルによって、動画内の1フレームの画像を取得できたら、次はその中に写っている物体の重心位置を算出します。
そのやり方については以下の記事で詳細に解説していますので、こちらもあわせてご覧ください。
【python-openCV】画像内物体の重心位置を算出する方法!
動画内物体の重心位置履歴を出力する方法
それではここまでに紹介した2つのスキル(①動画から画像を切り出す②画像から重心を算出する)を繰り返すことで、動画内物体の重心位置を算出するサンプルコードをご紹介していきます。
以下がそのコードです。
#ライブラリインポート
import cv2
import numpy as np
import matplotlib.pyplot as plt
#動画ファイルの読み込み
movie = cv2.VideoCapture('sample_movie.mp4')
#フレーム数の取得
nframe = int(movie.get(cv2.CAP_PROP_FRAME_COUNT))
#重心計算関数
def calc_moment(img):
img=cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
img=255-img
h,w=img.shape[:2]
#二値化処理
thresh, img_thresh = cv2.threshold(img, 60, 255, cv2.THRESH_BINARY)
#輪郭抽出
contours, hierarchy = cv2.findContours(img_thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
#塗りつぶし画像の作成
black_img=np.zeros((h,w),np.uint8)
cv2.drawContours(black_img, contours, 0, 255, -1)
#重心計算
M = cv2.moments(black_img, False)
x,y= int(M["m10"]/M["m00"]) , int(M["m01"]/M["m00"])
return x,y
#重心履歴の算出
XYdata=[]
for i in range(nframe):
ret, frame = movie.read()
x,y=calc_moment(frame)
XYdata.append([x,y])
XYdata=np.array(XYdata)
#重心履歴の可視化
plt.scatter(XYdata[:,0],XYdata[:,1],color='red', linestyle='solid', linewidth = 2.0, label='moment')
plt.xlabel('x',color='black',fontsize=14)
plt.ylabel('y',color='black',fontsize=14)
plt.savefig('moment.jpg', dpi=300)
今回のコードはあくまで冒頭で紹介した私が使った画像でうまく追跡できるようにチューニングしているものです。
ですのであなたの動画に適用する際は、重心計算関数の内部パラメータを少し修正する必要があると思います。
あるいは背景減算処理なんかを追加するのも有効だと思います。
いろいろと試行錯誤してやってみるのが良いでしょう。
サンプルコードの実行結果
最後に先ほどのコードを実行してみましょう。
以下が使用した動画ファイル。
以下が出力された重心の履歴結果です。
上の動画は縦1000、横1000ピクセルですので、X,Yともに500付近を中心にうろうろしている結果が問題なく出力されていますね。
おわりに
というわけで今回はpythonを使って、動画内物体の重心位置履歴を出力する方法をご紹介しました。
ぜひあなたの動画にも適用して遊んでみてください。
このように、私のブログでは様々なスキルを紹介しています。
今は仕事中で時間がないかもしれませんが、ぜひ通勤時間中などに他の記事も読んでいただけると嬉しいです。
⇒興味をもった方は【ヒガサラ】で検索してみてください。
確実にスキルアップできるはずです。
最後に、この記事が役に立ったという方は、ぜひ応援よろしくお願いします。
↓ 応援ボタン
にほんブログ村
それではまた!
Follow @HigashiSalary
コメント