質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

0回答

863閲覧

OpenCVを用いたボールトラッキングのIndexエラー

Banana8773

総合スコア0

OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2021/12/21 04:50

前提・実現したいこと

テニスボールのトラッキングをKalmanFilterを用いて実現しようと考えています。
KalmanFilterを用いていない既存のソースコードを用いてKalmanFilterを導入することで実現しようと考えているのですが、コードを実行してみたところ以下のようなエラーが出ます。

発生している問題・エラーメッセージ

Traceback (most recent call last): File "/Users//Downloads/Gazou5.py", line 117, in <module> X,P=Kalman_filter(ball_temp[0],xPre,pPre,sigmaW,sigmaV) IndexError: list index out of range

該当のソースコード

Python

1import time 2import math 3import cv2 4import sympy 5import numpy as np 6 7def isCourt(p):#ボール座標がコートの中にあるかを判定 8 from sympy.geometry import Point, Polygon 9 poly = Polygon((520,178), (905,178), (1065,600), (360,600)) 10 point=p 11 return poly.encloses_point(point) 12 13def dilation(dilationSize,kernelSize,img):#膨張処理 14 kernel=np.ones((kernelSize,kernelSize),np.uint8) 15 element=cv2.getStructuringElement(cv2.MORPH_RECT,(2*dilationSize+1,2*dilationSize+1),(dilationSize,dilationSize)) 16 dilation_img = cv2.dilate(img,kernel,element) 17 18 return dilation_img 19 20def detect(gray_diff):# 21 retval, black_diff = cv2.threshold(gray_diff, 30, 255, cv2.THRESH_BINARY) 22 img=black_diff 23 24 dilation_img=dilation(18,20,img) 25 26 img2=dilation_img.copy() 27 img2=cv2.cvtColor(img2,cv2.COLOR_GRAY2RGB) 28 29 contours, hierarchy = cv2.findContours(dilation_img,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE) 30 31 temp=[] 32 p_array=[] 33 area_array=[] 34 ball_p=[] 35 for i in range(len(contours)): 36 37 count=len(contours[i]) 38 temp.append(count) 39 area = cv2.contourArea(contours[i])#面積計算 40 area_array.append(area) 41 x=0.0 42 y=0.0 43 for j in range(count): 44 x+=contours[i][j][0][0] 45 y+=contours[i][j][0][1] 46 47 x/=count 48 y/=count 49 x=int(x) 50 y=int(y) 51 p_array.append([x,y]) 52 53 if(area<1000):#面積が一定以下 54 if(isCourt([x,y])):#コート内かどうか 55 #cv2.drawContours(img2,contours,i,(0,255,255),2)#黄 56 ball_p=[x,y] 57 58 return ball_p,img2,p_array,area_array 59 60 61def Kalman_filter(balltemp,xPre,pPre,sigmaW,sigmaV): 62 xForecast=xPre#今季の状態=前期の状態 63 pForecast=pPre+sigmaW#今期の状態の予測誤差の分散 = 前期の状態の予測誤差の分散 + 状態方程式のノイズの分散 64 kGain=pForecast/(pForecast+sigmaV)#カルマンゲイン = 状態の予測誤差の分散 ÷(状態の予測誤差の分散+観測方程式のノイズの分散) 65 xFiltered=xForecast+kGain*(balltemp-xForecast)#補正後の状態 = 補正前の状態 + カルマンゲイン ×(本物の観測値-予測された観測値) 66 pFiltered=(1-kGain)*pForecast#補正後の状態の予測誤差の分散 =(1ーカルマンゲイン)× 補正前の状態の予測誤差の分散 67 68 return xFiltered,pFiltered 69 70 71VIDEO_DATA = "Movie.mp4" 72ESC_KEY = 0x1b 73DURATION = 1.0 74cv2.namedWindow("tennis") 75video = cv2.VideoCapture(VIDEO_DATA) 76 77fps = video.get(cv2.CAP_PROP_FPS) 78height = video.get(cv2.CAP_PROP_FRAME_HEIGHT) 79width = video.get(cv2.CAP_PROP_FRAME_WIDTH) 80# 形式はMP4Vを指定 81fourcc = cv2.VideoWriter_fourcc(*'MJPG') 82# 出力先のファイルを開く 83out = cv2.VideoWriter('output.avi',fourcc,20.0, (int(width), int(height))) 84 85# 最初のフレームの読み込み 86end_flag, frame_next = video.read()#read() 1つ1つのフレームを読み込む 87height, width, channels = frame_next.shape 88motion_history = np.zeros((height, width), np.float32) 89frame_pre = frame_next.copy() 90 91p=[] 92a=[] 93ball=[] 94ball_tempold=[] 95iii=1 96 97while(end_flag): 98#for i in range(150): 99 color_diff = cv2.absdiff(frame_next, frame_pre)# フレーム間の差分計算 100 gray_diff = cv2.cvtColor(color_diff, cv2.COLOR_BGR2GRAY)# グレースケール変換 101 retval, black_diff = cv2.threshold(gray_diff, 100, 1, cv2.THRESH_BINARY)# 2値化 102 103 proc_time = time.time()# プロセッサ処理時間(sec)を取得 104 cv2.motempl.updateMotionHistory(black_diff, motion_history, proc_time, DURATION)# モーション履歴画像の更新 105 hist_color = np.array(np.clip((motion_history - (proc_time - DURATION)) / DURATION, 0, 1) * 255, np.uint8)# 古いモーションの表示を経過時間に応じて薄くする 106 hist_gray = cv2.cvtColor(hist_color, cv2.COLOR_GRAY2BGR)# グレースケール変換 107 ball_temp,img,p_temp,a_temp=detect(gray_diff) 108 if (iii==1): 109 ball_tempold=ball_temp 110 xPre=0 111 pPre=1000 112 113 sigmaW=100 114 sigmaV=100 115 116 117 X,P=Kalman_filter(ball_temp[0],xPre,pPre,sigmaW,sigmaV) 118 119 cv2.line(img,X,xPre,(0,255,255),2) 120 121 xPre=X#前回の状態 122 123 124 #if(i>50): 125 p.append(p_temp) 126 a.append(a_temp) 127 if(len(ball_temp)>0): 128 ball.append(ball_temp) 129 130 ball_array=np.array(ball) 131 court_array=np.array([[520,178], [905,178], [1065,600], [360,600]]) 132 service1_array=np.array([[440,250],[1000,250]]) 133 service2_array=np.array([[380,420],[1050,420]]) 134 service3_array=np.array([[712,250],[712,420]]) 135 img=cv2.polylines(img,[ball_array],False,(0,255,255)) 136 img=cv2.polylines(img,[court_array],True,(0,255,0)) 137 img=cv2.polylines(img,[service1_array],True,(0,255,0)) 138 img=cv2.polylines(img,[service2_array],True,(0,255,0)) 139 img=cv2.polylines(img,[service3_array],True,(0,255,0)) 140 141 cv2.imshow("tennis", img)# モーション画像を表示 142 out.write(img) 143 144 if cv2.waitKey(20) == ESC_KEY:# Escキー押下で終了 145 break 146 147 # 次のフレームの読み込み 148 frame_pre = frame_next.copy() 149 end_flag, frame_next = video.read() 150 ball_tempold=ball_temp 151 iii+=1 152# 終了処理 153cv2.destroyAllWindows() 154out.release() 155video.release() 156

補足情報(FW/ツールのバージョンなど)

既存のソースコードの意味を理解していない部分が少しあり、detect関数の戻り値であるball_pに差分処理で得られたボールの位置がlistで入っていると考えていたのですが、そこのあたりでエラーが起きているみたいなので、そこの辺りを教えていただけるとありがたいです。よろしくお願い致します。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだ回答がついていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問