基于c++、opencv的dnn模块的手势识别

先看效果:

老规矩话不多,实现的方法步骤,细节全在我的代码注释里面,只你跟着注释写,相信你也写得出来的!

#include <opencv2/dnn.hpp>
#include<opencv2/opencv.hpp>
#include<Windows.h>
#include <iostream>using namespace std;
using namespace cv;
using namespace dnn;//大致步骤:加载网络文件,输入到网络去,加载检测的图片,图片预处理,处理的图片送入网络,网络返回结果,再结果中找到点,点的位置再拟合到原图中,展示原图 int nPoints = 22;//21个关键带你
string protoFile = "H:\\openpose_data\\0.prototxt";//prototxt表示模型的配置文件
string weightsFile = "H:\\openpose_data\\1.caffemodel";//caffeModel表示模型的权重二进制文件const int POSE_PAIRS[20][2] =//手指姿势数组
{//每个手指4个关键点(一点两个位置坐标参数)(5个手指每个手指4个关键点加一个手掌点等于21,故【20】【2】的数组){0,1}, {1,2}, {2,3}, {3,4},         // 拇指{0,5}, {5,6}, {6,7}, {7,8},         // 食指{0,9}, {9,10}, {10,11}, {11,12},    // 中指{0,13}, {13,14}, {14,15}, {15,16},  // 无名指{0,17}, {17,18}, {18,19}, {19,20}   // 小指
};int main()
{Mat img;VideoCapture cap;cap.open("H:\\openpose_data\\my_hand.mp4");if(!cap.isOpened()){cout << "video can not open " << endl;}//cap.set(CAP_PROP_FOURCC, VideoWriter::fourcc('M', 'J,', 'P', 'G'));//cap.set(CAP_PROP_FRAME_WIDTH, 640);//cap.set(CAP_PROP_FRAME_HEIGHT, 480);namedWindow("pose", WINDOW_AUTOSIZE);int a = 0;while (true){a += 30;if (a >= cap.get(CAP_PROP_FRAME_COUNT))//得到总的帧数{cout << "检测完成" << endl;break;}cap.set(CAP_PROP_POS_FRAMES, a);  //(跳帧)优化图片,缩减尺寸和提高图片质量(直方图均衡化),设置缓冲区,处理时间小于帧差间隔(重点)if (cap.get(CAP_PROP_POS_MSEC) != 0)//暂停几秒,让图片完成装载{Sleep(100);}cap >> img;//resize(img, img, Size(640,480));//缩减尺寸float aspect_ratio = img.cols / (float)img.rows;//获取图片的宽高比int inHeight = 368;int inWidth = (int)(aspect_ratio * inHeight);//感觉这里的*8/8没用啊float thresh = 0.01;//定义关键点的阈值Net net = readNetFromCaffe(protoFile, weightsFile);//加载网络模型函数net.setPreferableBackend(DNN_BACKEND_OPENCV);//此函数是加速网络推理的设置Mat inpBlob = blobFromImage(img, 1.0 / 255, Size(inWidth, inHeight), Scalar(0, 0, 0), false, false);//用于图片识别时图片预处理,图片缩放和减均值处理//模型推理过程就是神经网络模型进行一次前向传播,在OpenCV中,用以下可读性非常强的两行代码即可完成net.setInput(inpBlob);Mat output = net.forward();// 返回预测结果(类别,置信度,2个坐标位置(x、y))//类别的对应清单,从classification_classes_ILSVRC2012.txt获取//forward函数返回一个Mat变量,返回值是指输入的layername首次出现的输出默认输出整个网络的运行结果int H = output.size[2];int W = output.size[3];//这里的H、W是在预测的关键点位置信息// 寻找关键点vector<Point> points(nPoints);//赋值22给points(22->0-21就是上面手的21个关键点)for (int n = 0; n < nPoints; n++)//遍历{// 相应身体部分的概率图Mat probMap(H, W, CV_32F, output.ptr(0, n));//将关键点x作为H、y作为W构建一个矩阵,再将21个关键点输入进这个矩阵中resize(probMap, probMap, Size(img.cols, img.rows));//裁剪相应的大小,恢复成原图的大小,也便确定点的位置Point maxLoc; // 获取位置double prob; //取最大的概率数据minMaxLoc(probMap, 0, &prob, 0, &maxLoc);//在数组中找到全局最小和最大值//参数1输入的数组若是图像需为单通道图像、参数2返回最小值的指针若无需返回此值设为 NULL、参数3返回最大值的指针若无需返回此值设为 NULL//参数4返回最小值位置的指针(二维情况下)若无需返回此值设为 NULL、参数5返回最大值位置的指针(二维情况下)若无需返回此值设为 NULL、参数6可选的掩膜操作points[n] = maxLoc;//把最大概率的点的位置装入动态数组内,为接下来画线做准备}//关键点之间画线int nPairs = sizeof(POSE_PAIRS) / sizeof(POSE_PAIRS[0]);for (int n = 0; n < nPairs; n++){// 查找 2 个连接的身体/手部部件Point2f partA = points[POSE_PAIRS[n][0]];Point2f partB = points[POSE_PAIRS[n][1]];if (partA.x <= 0 || partA.y <= 0 || partB.x <= 0 || partB.y <= 0)continue;line(img, partA, partB, Scalar(0, 255, 255), 2);//画线函数circle(img, partA, 8, Scalar(0, 0, 255), -1);circle(img, partB, 8, Scalar(0, 0, 255), -1);}imshow("pose", img);waitKey(30);}   cap.release();return 0;
}
//对关键点之间的操作映射为鼠标事件
//就可以使用手势来实现一些电脑上的操作

识别效果:
B站(这个也是我的账号呦)

总结:2天写出来,1天改代码优化,效率还可以吧!但是最后视频还是有卡顿,感觉有3秒1帧,这里说一下我分析的卡顿的原因:1、视频读入速度快,图片处理慢 2、视频出来的图片没处理好 3、没用GPU跑代码 4、也没有用线程去处理 总之项目是可以了的,也是由于视频检测卡顿的原因我就没写手势映射到鼠标的逻辑操作了,如果检测的视频有25fps,那么就可以利用手势来控制鼠标做一些鼠标能做到的事情了。

AI入门之神经网络(9)基于c++、opencv的dnn模块的视频手势识别相关推荐

  1. 用opencv的dnn模块做yolov5目标检测

    最近在微信公众号里看到多篇讲解yolov5在openvino部署做目标检测文章,但是没看到过用opencv的dnn模块做yolov5目标检测的.于是,我就想着编写一套用opencv的dnn模块做yol ...

  2. OpenCV之DNN模块,实现深度学习网络的推理加速

    OpenCV是计算机视觉领域使用最为广泛的开源库,以功能全面使用方便著称.自3.3版本开始,OpenCV加入了对深度神经网络(DNN)推理运算的支持.在LiveVideoStack线上交流分享中英特尔 ...

  3. OpenCV的dnn模块调用TesorFlow训练的MoblieNet模型

    七月 上海| 高性能计算之GPU CUDA培训 7月27-29日三天密集式学习  快速带你入门阅读全文> 正文共2073个字,2张图,预计阅读时间10分钟. 一.初得模型 那是一个月之前的事情了 ...

  4. python读取视频流做人脸识别_基于 Python + OpenCV 进行人脸识别,视频追踪代码全注释...

    1 #-*- coding: utf-8 -*- 2 from __future__ importunicode_literals3 #操作文件 4 importos5 #科学计算 6 importn ...

  5. OpenCV的DNN模块

    文章目录 Mat的构造函数 blobFromImage函数 dnn::Net 的 forward() Mat的构造函数 Mat::Mat()//无参数构造方法: Mat::Mat(int rows, ...

  6. python、C++ 中通过OpenCV的DNN模块使用YoloV4

    目录 1 Python环境下调用 2 C++环境下调用(编写CMakeLists.txt文件) 2.1 OpenCV安装 2.2 程序编写 2.2.1 main.cpp 2.2.2 Detection ...

  7. 深度学习与OpenCV DNN模块:权威指南

    计算机视觉领域自20世纪60年代末就已经存在.图像分类和目标检测是计算机视觉领域的一些最古老的问题,研究人员已经努力解决了几十年.使用神经网络和深度学习,我们已经达到了一个阶段,计算机可以开始真正地理 ...

  8. Opencv、dnn部署自己的Yolov5模型记录

    Opencv.dnn部署自己的Yolov5模型记录 一.环境配置 1.opencv == 4.5.1+dnn模块 2.pytorch == 1.8 3.ubuntu18.04 二.代码来源 1.htt ...

  9. C++从零实现简单深度神经网络(基于OpenCV)

    代码地址如下: http://www.demodashi.com/demo/11138.html 一.准备工作 ####需要准备什么环境 需要安装有Visual Studio并且配置了OpenCV.能 ...

最新文章

  1. 嵌入式开发输出调试信息的几种方法(常规法及非常规法)
  2. Adobe Achemy入门指南(二)
  3. MyBatis学习总结(1)——MyBatis快速入门
  4. 2017微服务 mysql集群_成功升P7多亏掌握了这几点:高并发+Nginx+微服务+Redis+MySQL...
  5. debian及ubuntu挂载本地硬盘的ISO镜像文件
  6. 工作95视频上传逻辑
  7. Z-Blog 爬虫 node实现
  8. LeetCode 501. 二叉搜索树中的众数(中序遍历)
  9. 智慧中国杯算法赛解读 | 精准资助数据探索(一)
  10. python安装无法直接安装的包
  11. 《转载》python爬虫实践之模拟登录
  12. HTML5实践 -- 可伸缩的mobile搜索框
  13. 解决“应用程序无法启动,因为应用程序的并行配置不正确“问题
  14. Lync 2010升级到Lync 2013POC计划-过程!
  15. speedoffice(Excel)图片上怎么添加文字
  16. 从安卓手机ROOT提取微信聊天记录到利用Python进行词云分析全过程
  17. mysql myisam 主键关联_MySQL中myisam和innodb的主键索引有什么区别?
  18. X的学习日记LinuxOS篇
  19. 2021湖南高考成绩查询考生版,湖南省普通高校招生考试考生综合信息平台入口2021...
  20. 小程序源码:修复登录接口版最新知识付费变现小程序源码下载-独立后台版本

热门文章

  1. android 拍照人像对正框
  2. SSL TLS HTTP HTTPS SSH 分别是什么意思?
  3. vsnprintf 与 _vsnprintf 的区别
  4. vsnprintf函数使用
  5. C#编程,使用虚拟键盘的一种方法
  6. android nfc 配对蓝牙 开发,NFC和蓝牙两种配对方式_配件评测-中关村在线
  7. 小程序选择图片音视频的方法chooseMedia
  8. 批量删除Windows补丁
  9. 基本蛙跳算法(Frog leaping algorithm,FLA)
  10. 赛元SC92F8463B/SC95F8523的PWM 实现无源蜂鸣器功能