1、案例介绍
案例实现对视频中的行人进行实时检测,并可在视频画面通过鼠标绘制矩形区域,行人经过区域内后,程序会进行判断行人已进入该区域,行人检测框颜色将变为蓝色。该程序主要使用python的opencv模块实现,实现流程:首先利用Haar分类器实现行人检测功能,其次利用opencv鼠标事件框选矩形区域,计算行人中心点,判断如果中心点在区域内后,就对行人检测框进行颜色的转变。
2、案例实现
- 实现行人检测,加载Haar的人体识别器模型,读取视频流每一帧,使用矩形绘制方法rectangle绘制出行人。
import cv2
if __name__ == '__main__':
# 加载Haar级联分类器模型
cascade_classifier = cv2.CascadeClassifier('./model/haarcascade_fullbody.xml')
# 加载视频
video_capture = cv2.VideoCapture('./data/test.mp4')
cv2.namedWindow('image')
while True:
# 获取视频的一帧
ret, frame = video_capture.read()
# 转换为灰度图像
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
# 检测人体
bodies = cascade_classifier.detectMultiScale(gray, 1.1, 4)
# 在图像上绘制人体框并显示
for (x, y, w, h) in bodies:
cv2.rectangle(frame, (x, y), (x+w, y+h), (0, 255, 0), 2)
cv2.imshow('image', frame)
# 按'q'键退出
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# 释放资源
video_capture.release()
cv2.destroyAllWindows()
- 实现鼠标事件绘制矩形,通过opencv的事件监听器,获取矩形对角线的两点并通过rectangle方法将矩形绘制出来。
import cv2
import numpy as np
# 鼠标事件
def OnMouseAction(event, x, y, flags, param):
global position1, position2
if event == cv2.EVENT_LBUTTONDOWN: # 按下左键
position1 = (x, y)
position2 = None
elif event == cv2.EVENT_MOUSEMOVE and flags == cv2.EVENT_FLAG_LBUTTON: # 按住左键拖曳不放开
position2 = (x, y)
elif event == cv2.EVENT_LBUTTONUP: # 放开左键q
position2 = (x, y)
if __name__ == '__main__':
# 加载Haar级联分类器模型
cascade_classifier = cv2.CascadeClassifier('./model/haarcascade_fullbody.xml')
# 加载视频
video_capture = cv2.VideoCapture('./data/test.mp4')
cv2.namedWindow('image')
cv2.setMouseCallback('image', OnMouseAction)
position1 = None
position2 = None
x0, yo = None, None
cnt = None
while True:
# 获取视频的一帧
ret, frame = video_capture.read()
# 转换为灰度图像
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
# 检测人体
bodies = cascade_classifier.detectMultiScale(gray, 1.1, 4)
# 在图像上绘制人体框并显示
for (x, y, w, h) in bodies:
cv2.rectangle(frame, (x, y), (x+w, y+h), (0, 255, 0), 2)
if ret:
if position1 != None and position2 != None:
cv2.rectangle(frame, position1, position2, (0, 0, 255), 1, 4)
cv2.imshow('image', frame)
# 按'q'键退出
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# 释放资源
video_capture.release()
cv2.destroyAllWindows()
- 计算行人中心点并判断中心点是否在矩形区域内,这里设置到我们初中学习的一个数字知识点,中心点的计算公式:x0,y0 = (x1+x2)/2,(y1+y2)/2,其次通过pointPolygonTest方法判断中心点是否在指定区域内。
import cv2
import numpy as np
# 鼠标事件
def OnMouseAction(event, x, y, flags, param):
global position1, position2
if event == cv2.EVENT_LBUTTONDOWN: # 按下左键
position1 = (x, y)
position2 = None
elif event == cv2.EVENT_MOUSEMOVE and flags == cv2.EVENT_FLAG_LBUTTON: # 按住左键拖曳不放开
position2 = (x, y)
elif event == cv2.EVENT_LBUTTONUP: # 放开左键q
position2 = (x, y)
if __name__ == '__main__':
# 加载Haar级联分类器模型
cascade_classifier = cv2.CascadeClassifier('./model/haarcascade_fullbody.xml')
# 加载视频
video_capture = cv2.VideoCapture('./data/test.mp4')
cv2.namedWindow('image')
cv2.setMouseCallback('image', OnMouseAction)
position1 = None
position2 = None
x0, yo = None, None
cnt = None
while True:
# 获取视频的一帧
ret, frame = video_capture.read()
# 转换为灰度图像
gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
# 检测人体
bodies = cascade_classifier.detectMultiScale(gray, 1.1, 4)
# 在图像上绘制人体框并显示
for (x, y, w, h) in bodies:
cv2.rectangle(frame, (x, y), (x+w, y+h), (0, 255, 0), 2)
if ret:
if position1 != None and position2 != None:
cv2.rectangle(frame, position1, position2, (0, 0, 255), 1, 4)
for (x, y, w, h) in bodies:
x0, yo = int((x + x + w) / 2), int((y + y + h) / 2)
if cv2.pointPolygonTest(cnt, (x0, yo), False) >= 0:
cv2.rectangle(frame, (x, y), (x + w, y + h), (255, 0, 0), 2)
cv2.imshow('image', frame)
# 按'q'键退出
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# 释放资源
video_capture.release()
cv2.destroyAllWindows()
3、项目结构
4、总结
上述只是做了一个基础案例,该案例依然存在以下几点小的问题,第一点问题就是效率问题,针对视频流的处理是非常消耗内存的如果电脑是cpu的话,所以针对这个问题我查阅了一下资料,使用numba可以提升对视频流处理速度。第二点问题是行人识别准确度问题,当前使用Haar的识别器效果还是不好的,我们可以使用yolov5或者MobileNet-SSD模型对行人进行识别效果会更佳,第三个问题是绘制区域的优化,目前是默认矩形区域,实际形形况中可能是非矩形的多边形区域,所以针对这个需要进一步的优化。以上就是今天的案例分享,如果对大家有帮助可以点个赞奥~♥♥文章来源:https://www.toymoban.com/news/detail-703900.html
百度网盘 请输入提取码 文章来源地址https://www.toymoban.com/news/detail-703900.html
到了这里,关于python使用opencv实现识别指定区域的行人的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!