44 dlib鼠标指定目标跟踪
dlib提供了dlib.correlation_tracker()类用于跟踪目标。
官方文档入口:http://dlib.net/python/index.html#dlib.correlation_tracker
不复杂,就不介绍了,后面会直接给出两个程序,有注释。
# -*- coding: utf-8 -*-
import sys
import dlib
import cv2 tracker = dlib.correlation_tracker() # 导入correlation_tracker()类
cap = cv2.VideoCapture(0) # OpenCV打开摄像头
start_flag = True # 标记,是否是第一帧,若在第一帧需要先初始化
selection = None # 实时跟踪鼠标的跟踪区域
track_window = None # 要检测的物体所在区域
drag_start = None # 标记,是否开始拖动鼠标 # 鼠标点击事件回调函数
def onMouseClicked(event, x, y, flags, param):
global selection, track_window, drag_start # 定义全局变量
if event == cv2.EVENT_LBUTTONDOWN: # 鼠标左键按下
drag_start = (x, y)
track_window = None
if drag_start: # 是否开始拖动鼠标,记录鼠标位置
xMin = min(x, drag_start[0])
yMin = min(y, drag_start[1])
xMax = max(x, drag_start[0])
yMax = max(y, drag_start[1])
selection = (xMin, yMin, xMax, yMax)
if event == cv2.EVENT_LBUTTONUP: # 鼠标左键松开
drag_start = None
track_window = selection
selection = None if __name__ == '__main__':
cv2.namedWindow("image", cv2.WINDOW_AUTOSIZE)
cv2.setMouseCallback("image", onMouseClicked) # opencv的bgr格式图片转换成rgb格式
# b, g, r = cv2.split(frame)
# frame2 = cv2.merge([r, g, b]) while(1):
ret, frame = cap.read() # 从摄像头读入1帧 if start_flag == True: # 如果是第一帧,需要先初始化
# 这里是初始化,窗口中会停在当前帧,用鼠标拖拽一个框来指定区域,随后会跟踪这个目标;我们需要先找到目标才能跟踪不是吗?
while True:
img_first = frame.copy() # 不改变原来的帧,拷贝一个新的出来
if track_window: # 跟踪目标的窗口画出来了,就实时标出来
cv2.rectangle(img_first, (track_window[0], track_window[1]), (track_window[2], track_window[3]), (0,0,255), 1)
elif selection: # 跟踪目标的窗口随鼠标拖动实时显示
cv2.rectangle(img_first, (selection[0], selection[1]), (selection[2], selection[3]), (0,0,255), 1)
cv2.imshow("image", img_first)
# 按下回车,退出循环
if cv2.waitKey(5) == 13:
break
start_flag = False # 初始化完毕,不再是第一帧了
tracker.start_track(frame, dlib.rectangle(track_window[0], track_window[1], track_window[2], track_window[3])) # 跟踪目标,目标就是选定目标窗口中的
else:
tracker.update(frame) # 更新,实时跟踪 box_predict = tracker.get_position() # 得到目标的位置
cv2.rectangle(frame,(int(box_predict.left()),int(box_predict.top())),(int(box_predict.right()),int(box_predict.bottom())),(0,255,255),1) # 用矩形框标注出来
cv2.imshow("image", frame)
# 如果按下ESC键,就退出
if cv2.waitKey(10) == 27:
break cap.release()
cv2.destroyAllWindows()
注:如果程序卡了,就调一下cv2.waitKey()中的参数,也就是延时时间,调小即可。
运行结果
初始时,窗口中只会显示第一帧的图像;
使用鼠标拖拽一个框,红框中目标后,按回车,设置框内为识别目标;
实时识别,以橙框标出;
按ESC键退出。


(csdn只能上传2M的图片,真心难受)
程序2
由于前面那个程序,只是熟悉下函数写的,我觉得用起来蛋疼,所以又重新封装了一下。看起来舒服多了。
# -*- coding: utf-8 -*-
import sys
import dlib
import cv2 class myCorrelationTracker(object):
def __init__(self, windowName='default window', cameraNum=0):
# 自定义几个状态标志
self.STATUS_RUN_WITHOUT_TRACKER = 0 # 不跟踪目标,但是实时显示
self.STATUS_RUN_WITH_TRACKER = 1 # 跟踪目标,实时显示
self.STATUS_PAUSE = 2 # 暂停,卡在当前帧
self.STATUS_BREAK = 3 # 退出
self.status = self.STATUS_RUN_WITHOUT_TRACKER # 指示状态的变量 # 这几个跟前面程序1定义的变量一样
self.track_window = None # 实时跟踪鼠标的跟踪区域
self.drag_start = None # 要检测的物体所在区域
self.start_flag = True # 标记,是否开始拖动鼠标 # 创建好显示窗口
cv2.namedWindow(windowName, cv2.WINDOW_AUTOSIZE)
cv2.setMouseCallback(windowName, self.onMouseClicked)
self.windowName = windowName # 打开摄像头
self.cap = cv2.VideoCapture(cameraNum) # correlation_tracker()类,跟踪器,跟程序1中一样
self.tracker = dlib.correlation_tracker() # 当前帧
self.frame = None # 按键处理函数
def keyEventHandler(self):
keyValue = cv2.waitKey(5) # 每隔5ms读取一次按键的键值
if keyValue == 27: # ESC
self.status = self.STATUS_BREAK
if keyValue == 32: # 空格
if self.status != self.STATUS_PAUSE: # 按下空格,暂停播放,可以选定跟踪的区域
#print self.status
self.status = self.STATUS_PAUSE
#print self.status
else: # 再按次空格,重新播放,但是不进行目标识别
if self.track_window:
self.status = self.STATUS_RUN_WITH_TRACKER
self.start_flag = True
else:
self.status = self.STATUS_RUN_WITHOUT_TRACKER
if keyValue == 13: # 回车
#print '**'
if self.status == self.STATUS_PAUSE: # 按下空格之后
if self.track_window: # 如果选定了区域,再按回车,表示确定选定区域为跟踪目标
self.status = self.STATUS_RUN_WITH_TRACKER
self.start_flag = True # 任务处理函数
def processHandler(self):
# 不跟踪目标,但是实时显示
if self.status == self.STATUS_RUN_WITHOUT_TRACKER:
ret, self.frame = self.cap.read()
cv2.imshow(self.windowName, self.frame)
# 暂停,暂停时使用鼠标拖动红框,选择目标区域,与程序1类似
elif self.status == self.STATUS_PAUSE:
img_first = self.frame.copy() # 不改变原来的帧,拷贝一个新的变量出来
if self.track_window: # 跟踪目标的窗口画出来了,就实时标出来
cv2.rectangle(img_first, (self.track_window[0], self.track_window[1]), (self.track_window[2], self.track_window[3]), (0,0,255), 1)
elif self.selection: # 跟踪目标的窗口随鼠标拖动实时显示
cv2.rectangle(img_first, (self.selection[0], self.selection[1]), (self.selection[2], self.selection[3]), (0,0,255), 1)
cv2.imshow(self.windowName, img_first)
# 退出
elif self.status == self.STATUS_BREAK:
self.cap.release() # 释放摄像头
cv2.destroyAllWindows() # 释放窗口
sys.exit() # 退出程序
# 跟踪目标,实时显示
elif self.status == self.STATUS_RUN_WITH_TRACKER:
ret, self.frame = self.cap.read() # 从摄像头读取一帧
if self.start_flag: # 如果是第一帧,需要先初始化
self.tracker.start_track(self.frame, dlib.rectangle(self.track_window[0], self.track_window[1], self.track_window[2], self.track_window[3])) # 开始跟踪目标
self.start_flag = False # 不再是第一帧
else:
self.tracker.update(self.frame) # 更新 # 得到目标的位置,并显示
box_predict = self.tracker.get_position()
cv2.rectangle(self.frame,(int(box_predict.left()),int(box_predict.top())),(int(box_predict.right()),int(box_predict.bottom())),(0,255,255),1)
cv2.imshow(self.windowName, self.frame) # 鼠标点击事件回调函数
def onMouseClicked(self, event, x, y, flags, param):
if event == cv2.EVENT_LBUTTONDOWN: # 鼠标左键按下
self.drag_start = (x, y)
self.track_window = None
if self.drag_start: # 是否开始拖动鼠标,记录鼠标位置
xMin = min(x, self.drag_start[0])
yMin = min(y, self.drag_start[1])
xMax = max(x, self.drag_start[0])
yMax = max(y, self.drag_start[1])
self.selection = (xMin, yMin, xMax, yMax)
if event == cv2.EVENT_LBUTTONUP: # 鼠标左键松开
self.drag_start = None
self.track_window = self.selection
self.selection = None def run(self):
while(1):
self.keyEventHandler()
self.processHandler() if __name__ == '__main__':
testTracker = myCorrelationTracker(windowName='image', cameraNum=1)
testTracker.run()
运行结果
操作有一些改变:
初始时,会自动从摄像头采集图像显示;
按下空格,暂停;此时若再按空格,恢复实时显示,但不进行目标跟踪;
暂停时,拖动鼠标会显示红框,按下回车,将红框内物体视为目标进行识别;
随后实时识别,以橙框标出;
按ESC键退出。
dlib这个库的确很方便,能够很轻松地让我们实现一些基础的识别任务,比如人脸识别。但是如果想要在各种识别任务中有更好的效果,肯定是不能只用他给的模型的。那也就是说需要自己训练了,看到官方文档中也提供了一些训练以及自己构建神经网络等的api接口,
44 dlib鼠标指定目标跟踪的更多相关文章
- 用Camshift算法对指定目标进行跟踪
原理 Camshift算法是Continuously Adaptive Mean Shift algorithm的简称. 它是一个基于MeanSift的改进算法.它首次由Gary R.Bradski等 ...
- 目标跟踪之camshift---opencv中meanshift和camshift例子的应用
在这一节中,主要讲目标跟踪的一个重要的算法Camshift,因为它是连续自使用的meanShift,所以这2个函数opencv中都有,且都很重要.为了让大家先达到一个感性认识.这节主要是看懂和运行op ...
- 目标跟踪--CamShift
转载请注明出处! !! http://blog.csdn.net/zhonghuan1992 目标跟踪--CamShift CamShift全称是ContinuouslyAdaptive Mean S ...
- 目标跟踪之粒子滤波---Opencv实现粒子滤波算法
目标跟踪学习笔记_2(particle filter初探1) 目标跟踪学习笔记_3(particle filter初探2) 前面2篇博客已经提到当粒子数增加时会内存报错,后面又仔细查了下程序,是代码方 ...
- 目标跟踪ObjectT综述介绍
此文也很详细:http://blog.csdn.net/maochongsandai110/article/details/11530045 原文链接:http://blog.csdn.net/pp5 ...
- 用于扩展目标跟踪的笛卡尔B-Spline车辆模型
(哥廷根大学) 摘要 文章提出了一种表示空间扩展物体轮廓的新方法,该方法适用于采用激光雷达跟踪未知尺寸和方向的车辆.我们在笛卡尔坐标系中使用二次均匀周期的B-Splines直接表示目标的星 - 凸形状 ...
- MAML-Tracker: 目标跟踪分析:CVPR 2020(Oral)
MAML-Tracker: 目标跟踪分析:CVPR 2020(Oral) Tracking by Instance Detection: A Meta-Learning Approach 论文链接:h ...
- 目标跟踪_MeanShift
找到一些关于目标跟踪的资料 http://blog.csdn.net/jinshengtao/article/details/30258833 http://blog.sina.com.cn/s/bl ...
- TLD目标跟踪算法
1. 简介 TLD目标跟踪算法是Tracking-Learning-Detection算法的简称.这个视频跟踪算法框架由英国萨里大学的一个捷克籍博士生Zdenek Kalal提出.TLD将传统的视频跟 ...
随机推荐
- python(leetcode)498. 对角线遍历
这题难度中等,记录下思路 第一个会超时, 第二个:思想是按斜对角线行进行右下左上交替遍历, def traverse(matrix): n=len(matrix)-1 m=len(matrix[0]) ...
- 【Oracle】常用函数
来源自:https://www.cnblogs.com/lxl57610/p/7442130.html Oracle SQL 提供了用于执行特定操作的专用函数.这些函数大大增强了 SQL 语言的功能. ...
- Codeforces Round #602 (Div. 2, based on Technocup 2020 Elimination Round 3) D2. Optimal Subsequences (Hard Version) 数据结构 贪心
D2. Optimal Subsequences (Hard Version) This is the harder version of the problem. In this version, ...
- Mybatis和Hibernate框架的区别
Mybatis和Hibernate框架的区别1 简单简介 1.1 Hibernate 框架 Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,建立对象与数据 ...
- IT兄弟连 HTML5教程 介绍HTML5给你认识 习题
1.关于HTML5说法正确的是:(C) A.HTML5只是对HTML4的一个简单升级 B.所有主流浏览器都支持HTML5 C.HTML5新增了离线缓存机制 D.HTML5主要是针对移动端进行了优化 2 ...
- app——升级测试点
APP版本升级的测试点 该文章转载于:https://www.cnblogs.com/changpuyi/p/8618755.html 移动端版本更新升级是一个比较重要的功能点,主要分为强制更新和 ...
- Elastic:用Docker部署Elastic栈
安装 因为我们需要使用docker来进行安装,我们必须安装: docker:根据不同的操作系统,请按照要求安装docker.可以到网站https://docs.docker.com/去安装 docke ...
- PHP-Curl模拟HTTPS请求
使用PHP-Curl方式模拟HTTPS请求,测试接口传参和返回值状态 上代码!! <?php /** * 模拟post进行url请求 * @param string $url * @par ...
- Java关键字之abstract、final、static用法
abstract:即抽象的,可以修饰类.方法: 修饰类:当有一个方法为抽象方法时,这个类就是抽象类,抽象类不能被new,它是一个不完整的类. 修饰方法:这个方法就是抽象的,即只能方法的定义,没有方法的 ...
- Taro多端自定义导航栏Navbar+Tabbar实例
运用Taro实现多端导航栏/tabbar实例 (H5 + 小程序 + React Native) 最近一直在捣鼓taro开发,虽说官网介绍支持编译到多端,但是网上大多数实例都是H5.小程序,很少有支持 ...