基础博客
请参考我的基于opencv模板匹配的单物体跟踪,基本原理相同,增加了矩阵记录多目标的位置信息等。
代码
import cv2 as cv2 import numpy as np from subprocess import call def template_demo(tpl, target, method = cv2.TM_CCORR_NORMED): th, tw = tpl.shape[:2]# 取高宽,不取通道 模板高宽 result = cv2.matchTemplate(target, tpl, method) min_val, max_val, min_loc, max_loc = cv2.minMaxLoc(result) # 寻找最小值,最大值。最小值位置,最大值位置 tl = max_loc br = (tl[0]+tw, tl[1]+th) print(max_val, tl, br) if max_val < 0.45: lost = 1 else: lost = 0 return tl, br, lost if __name__ == '__main__': number = int(input('please input the number of objects: ')) area = np.zeros((number, 4)) ROI_area = np.zeros((number, 4)) print(area.shape) print("--------- Python OpenCV Tutorial ---------") cap = cv2.VideoCapture('../robot.mp4') ret, frame = cap.read() original_frame = frame print(frame.shape) lam = 1 fourcc = cv2.VideoWriter_fourcc(*'XVID') # 保存视频的编码 out = cv2.VideoWriter('football_output.avi',fourcc, 20.0, (frame.shape[1], frame.shape[0])) for i in range(number): gROI = cv2.selectROI("ROI frame", frame, False) ROI_area[i] = [gROI[1], gROI[1]+gROI[3], gROI[0], gROI[0]+gROI[2]] # ROI = frame[gROI[1]: gROI[1]+gROI[3], gROI[0]:gROI[0]+gROI[2], :] area[i] = [0, frame.shape[1], 0, frame.shape[0]] print(area) print(ROI_area) while True: ret, frame = cap.read() if ret: for k in range(number): ROI = original_frame[int(ROI_area[k, 0]): int(ROI_area[k, 1]), int(ROI_area[k, 2]):int(ROI_area[k,3]), :] frame1 = frame[int(area[k, 2]):int(area[k, 3]), int(area[k, 0]):int(area[k, 1]), :] tl, br, lost = template_demo(ROI, frame1, method=cv2.TM_CCOEFF_NORMED) if lost==1: lam = 2 else: lam = 1 # ROI = frame1[tl[1]:br[1], tl[0]:br[0], :] cv2.imshow('ROI', ROI) print(ROI.shape) result = cv2.rectangle(frame, (int(area[k, 0])+tl[0], int(area[k, 2])+tl[1]), (br[0]+int(area[k, 0]), br[1]+int(area[k, 2])), (k*20, k*10, 255//(k+1)), 2) area[k, 0] = (tl[0] + br[0]) // 2 - lam * (br[0] - tl[0]) + area[k, 0] area[k, 1] = (tl[0] + br[0]) // 2 + lam * (br[0] - tl[0]) + area[k, 0] area[k, 2] = (tl[1] + br[1]) // 2 - lam * (br[1] - tl[1]) + area[k, 2] area[k, 3] = (tl[1] + br[1]) // 2 + lam * (br[1] - tl[1]) + area[k, 2] area[k, 0] = 0 if area[k, 0] < 0 else area[k, 0] area[k, 1] = frame.shape[1] if area[k, 1] > frame.shape[1] else area[k, 1] area[k, 2] = 0 if area[k, 2] < 0 else area[k, 2] area[k, 3] = frame.shape[0] if area[k, 3] > frame.shape[0] else area[k, 3] out.write(result) cv2.waitKey(18) cv2.imshow('result', result) else: break if cv2.waitKey(1) & 0xFF == ord('q'): break cap.release() cv2.destroyAllWindows() command = "ffmpeg -i football_output.avi football_output.mp4" call(command.split())
展示
后记
近期有很多朋友通过私信咨询有关Python学习问题。为便于交流,点击蓝色自己加入讨论解答资源基地