手势识别开源代码千千万,为啥我要用此方法,原因有三:
首先,我们项目要求这个手势识别是不分环境的,也就是半夜三更黑灯瞎火也能用,这一下子就把纯RGB的方式给去除了,而且也要考虑用户戴手套(手套颜色不限制)使用,那么肤色过滤什么的咱们再见;
其次,我们的运行主板计算量真的很弱鸡,深度学习推测什么的就别想跑了;
最后,我们只能选择深度信息来进行手势识别,深度信息的话可以有两种处理方式,一种是对深度灰度图像进行处理,一种是转换成点云用借助PCL进行处理,博主我以前玩过haar+adaboost做猫脸检测,所以就先试试对深度灰度图像进行处理。
正样本制作
正样本的图片我是从网上下载的,网址->Hands
总共11076张,我只选择了其中的1000张,然后我写了一个脚本将这些图片二值化:
#!/usr/bin/python
# -*- coding: utf-8 -*-
import cv2
import os
path = '/home/ian/Downloads/hands/negative'
files = os.listdir(path)
for file in files:
img = cv2.imread(path + '/' + file)
gray_img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) #转为灰度图
ret, thresh1 = cv2.threshold(gray_img, 220, 255, cv2.THRESH_BINARY_INV) #二值化
img = cv2.resize(img, (img.shape[1]/8, img.shape[0]/8), interpolation=cv2.INTER_CUBIC) #缩放
cv2.imwrite('/home/ian/Downloads/hands/' + file, img)
尺寸是40X30,然后需要制作一个正样本的描述文件,我是用脚本弄的,生成的描述文件和图片放在同一个目录下即可
#!/usr/bin/python
# -*- coding: utf-8 -*-
import os
files = os.listdir('.')
f = open('./pos.txt','a')
for file in files:
file = 'positive/' + file
file = file + ' 1 0 0 40 30' # 数量 1 ,特征从像素0 0 到40 30
f.writelines(file + '\n')
f.close()
后来我发现直接用这个就可以了: ls ./neg/. > neg.txt
生成的描述文件如下:
负样本制作
负样本制作和正样本类似,我是自己通过深度相机录制了5000张负样本图片,负样本的图片尺寸是80X60(没办法,训练主机太弱,太大的话算到猴年马月了)
好了,有了正负样本,下面就有进入关键的两个步骤了
样本处理
生成vec文件
进行训练需要用到一个后缀为vec的文件,生成办法可以通过opencv自带的opencv_createsamples,使用的例子如下,其余参数可以看其帮助。
opencv_createsamples.exe -vec pos.vec -info positive/pos.txt -bg negative/neg.txt -w 40 -h 30 -num 1000
经过这一步,就能获得在当前目录下获得一个叫pos.vec的文件,接着为了报错,在当前目录创建一个data的空文件夹,之后,输入以下指令,我们就开开心心等着开始训练吧。
opencv_traincascade -data ./data -vec ./pos.vec -bg ./neg.txt -numPos 700 -numNeg 3500 -numStage 15 -w 40 -h 30 -minHitRate 0.99 -maxFalseAlarmRate 0.5 -mode ALL
训练过程
遇到的问题
当我敲下训练指令时,报错接踵而至,让我措手不及,首先第一个是:
Train dataset for temp stage can not be filled. Branch training terminated.
解决办法:这是因为训练器找不到图片路径,检查一下程序去读描述文件时是否能够找到图片。