关键词不能为空

当前您在: 主页 > 英语 >

AFORGE 图像处理手势识别

作者:高考题库网
来源:https://www.bjmy2z.cn/gaokao
2021-02-09 07:01
tags:

-

2021年2月9日发(作者:bewilderment)




基于


Aforge


的手势识别之二


~~~


单点手势识别< /p>



分类:



计算机视觉


2010-05-04 13:46 9058


人阅读



评论


(12)


收藏






ima geprocessing


图形


objectc



本文来自


/hellogv/


,引用必须注明出处!




本文把


Aforge


的运动识别



前面介绍的手写识别


融合在一起,


实现单个手指的手势识别。


下图演示了本文代码运行的结果,

< p>
图片有


点大,请稍候。。。




我预先让程序学习了


B



C


这两个字母,然后通过手指的手势


识别向程序绘画图形,


所以点击


rec orgize


时,


就自动把图形的特征


对应的字母给识别出来了。



这个例子关键部分在于如何灵活运用


Aforge


的运动识 别,


如何


判断是要画图,


还是普通的移 来移去呢?在这里,


我判断移动对象的


大小,当突然面积增大< /p>


(


即两个指套合并


)

则开始绘图


(


手势识别的开



)



当拆开再合并则为解除绘图

< p>
(


手势识别的结束


)


,< /p>


说白了就是用一


个当前状态


=!


当前状态去做。




本文的代码可以到这里下载:


/source/2313846




下面贴出运动判断的核心代码:



[c-sharp]



view plaincopyprint?



1.



private



void


videoSourcePlayer1_NewFrame(


object



sender,


ref


Bitmap image )



2.



{



3.



nowImg = (Bitmap)();



4.





5.



Bitmap objectImage = ( image


);



6.





7.




// lock image for further processing




8.



BitmapData objectData = ts(



new


Rectangle( 0, 0, , )


,



9.



ly, ormat


);



10.






11.





// grayscaling




12.




UnmanagedImage grayImage = (



new


UnmanagedImage( objectData ) );



13.






14.





// unlock image




15.




Bits( objectData );



16.






17.





// locate blobs




18.




sImage( grayImage );



19.




List rects =


new


List(


);



20.




ge(ectsRectan


gles());



21.






22.





if


( >0 )



23.




{



24.




#region


去掉内部和黏在一起的对象




25.





for


(


int


i = 0; i < - 1; i++


)



26.




{



27.





//tru e


表示


X


轴上不能相交,


false


表示相





28.




Boolean isNoTouchX = (rects[


i + 1].Right , rects[i].Right) - (rects[i


+ 1].Left ,rects[i].Left) > (rects[i].Width + re


cts[i + 1].Width);



29.





//true


表示


Y


轴上不能相交,


false


表示相





30.




Boolean isNoTouchY = (rects[


i + 1].Bottom, rects[i].Bottom) - (rects[


i + 1].Top, rects[i].Top) > (rects[i].Height + re


cts[i + 1].Height);



31.





if


(isNoTouchX ==


false


&& isNoTouch


Y ==


false

)


//


如果两个对象相交




32.




{



33.




Rectangle rect =


new


Rectangle(M


(rects[i].Left, rects[i + 1].Left),



34.




(rects[i].Top, rects


[i + 1].Top),



35.




(rects[i].Right, rec


ts[i + 1].Right) - (rects[i].Left, rects[


i + 1].Left),



36.




(rects[i].Bottom, re


cts[i + 1].Bottom) - (rects[i].Top, rects


[i + 1].Top));



37.




At(i + 1);



38.




At(i);



39.






40.




(rect);



41.




i = 0;



42.




}



43.




}



44.




#endregion




45.





46.




#region


画出表示点




47.




Rectangle objectRect = rects[0];



48.






49.





int


oldSize=+


;



50.





int


nowSize=rects[0].Width+rects[0].Heig


ht;



51.






52.





if


(nowSize > (oldSize * 1.2 ))


//


如果突然


变大,即两个指套合 并




53.




{



54.




isCapture =!isCapture;



55.




();



56.




}



57.






58.




Graphics g = age(image);




59.






60.





if


(isCapture)


//< /p>


如果捕捉到对象




61.




{



62.




Pen pen =


new


Pen(gb(255


, 0, 0), 3);



63.




ctangle(pen, objectRect);



64.





int


x = ( + objectRec


/ 2) * / videoSourcePlayer1.


Width;



65.





int


y = ( + objectRect


.Height / 2) * / videoSourcePlayer1


.Height;



66.




(x,y );



67.




}



68.





else


//


如果没有捕捉到对象




69.




{



70.




Pen pen =


new


Pen(gb(160


, 255, 160), 3);



71.




ctangle(pen, objectRect);



72.




}



73.






74.




e();



75.







76.




#endregion




77.






78.




oldRect = rects[0];



79.






80.




}



81.






82.




UpdateObjectPicture(objectImage );



83.






84.



}





基于


Af orge


的手势识别之三


~~~


多点手 势识别



分类:



计算机视觉


2010-05-07 12:54 8158


人阅读



评论


(11)


收藏






ima geprocessingobject


图形


c



本文来自


/hellogv/


,引用必须注明出处!




上次介绍了


单点手势识别


,这次就继续 介绍一下如何实现多点


手势识别,


先来看看本文实现的效果图,


图片有点大,


请稍候。








我预先让程序学习了


B



C


这两个字母,第一个对象通过点击


鼠标左键去选择颜色


(


对象为绿色


)


,第二个对象通过点击鼠标右键去


选择颜 色


(


对象为红色


)

,然后通过两支手指的手势识别分别向程序绘


画图形,


所以 点击


recorgize


时,


就自动把 图形的特征对应的字母给


识别出来了。




本文上一篇文章的延伸,如图中所示,这里通过 一个对象的消



/


重现来识别是否开始 绘图,


当突然消失


/


重现则开始绘图,


再次消



/


重 现则停止绘图。本文的代码可以到这里下载:


/source/2323958




接下来贴出本文的核心代码:



[c-sharp]



view plaincopyprint?



1.



private



void


videoSourcePlayer1_NewFrame(


object



sender,


ref


Bitmap image )



2.



{



3.




//


保存捕获到的对象




4.



List []rects =


new


List


[2];



5.





6.



Bitmap[] objectImage =


new


Bitmap[2];



7.




for


(


int


i = 0; i < ObjectSum; i ++)


//


捕获对


< br>



8.



{



9.



nowImg[i] = (Bitmap)();



10.






11.




objectImage[i] = colorFilter[i].Apply(no


wImg[i]);



12.






13.





// lock image for further processing




14.




BitmapData objectData = objectIm age[i].L


ockBits(


new

Rectangle(0, 0, ,


ight),



15.




ly,


ormat);



16.






17.





// grayscaling




18.




UnmanagedImage grayImage =


new


Grayscale


BT70 9().Apply(


new


UnmanagedImage(objectData));



19.






20.





// unlock image




21.




objectImage[i].UnlockBits(objectData);



22.






23.





//


从颜色中筛选有效的对象




24.




blobCounter[i].ProcessImage(grayImage);




25.




rects[i] =


new


List();



26.




rects[i].AddRange(blobCounter[i] .GetObje


ctsRectangles());



27.






28.





//


如果当前对象


i


不存在,并且原有的对象


i


又是


存在的,则表示是对象


i


隐藏起来了




29.





if


(rects[i].Count == 0 && oldRect[i].Is


Empty ==


false


)



30.




{



31.




isCapture[i] = ! isCapture[i];


//


改变为


反模式




32.




clsHandWrite[i].Clear();



33.




}



34.





else



if


(rects[i].Count > 0)

< p>
//


如果当前对



i


存在




35.




{



36.




#region


去掉内部和黏在一起的对象




37.





for


(


int


ii = 0; ii < rects[i].Count


- 1; ii++)



38.




{



39.





/ /true


表示


X


轴上不能相交,


false



示相交




40.




Boolean isNoTouchX = (re


cts[i][ii + 1].Right, rects[i][ii].Right) - Math.


Min(rects[i][ii + 1].Left, rects[i][ii].Left) > (


rects[i][ii].Width + rects[i][ii + 1].Width);



41.





/ /true


表示


Y


轴上不能相交,


false



示相交




42.




Boolean isNoTouchY = (re


cts[i][ii + 1].Bottom, rects[i][ii].Bottom) - Mat


(rects[i][ii + 1].Top, rects[i][ii].Top) > (


rects[i][ii].Height + rects[i][ii + 1].Height);



43.





if


(isNoTouchX ==


false


&& isNoT


ouchY ==


false

)


//


如果两个对象相交




44.




{



45.




Rectangle rect =


new


Rectang


le((rects[i][ii].Left, rects[i][ii + 1].L


eft),



46.




(rects[i][ii].To


p, rects[i][ii + 1].Top),



47.




(rects[i][ii].Ri


ght, rects[i][ii + 1].Right) - (rects[i][


ii].Left, rects[i][ii + 1].Left),



48.




(rects[i][ii].Bo


ttom, rects[i][ii + 1].Bottom) - (rects[i


][ii].Top, rects[i][ii + 1].Top));



49.




rects[i].RemoveAt(ii + 1);



50.




rects[i].RemoveAt(ii);



51.






52.




rects[i].Add(rect);



53.




ii = 0;



54.




}



55.




}



56.




#endregion




57.





58.




#region


画出表示点




59.




Rectangle objectRect = rects[i][0];


/


/


只取得该对象第一个矩阵




60.




Graphics g = age(imag


e);



61.






62.





if


(is Capture[i])


//


如果捕捉到对象

< br>



63.




{



64.




Pen pen =


new


Pen(gb


(255, 255, 255), 3);



65.




ctangle(pen, objectRect)


;



66.





int


x = ( + objec


/ 2) * / videoSourcePla


;



67.





int


y = ( + object


/ 2) * / videoSourcePl


;



68.




clsHandWrite[i].Draw(x, y);



69.




}



70.





else< /p>


//


如果没有捕捉到对象




71.




{



72.




Pen pen =


new


Pen(gb


(160, 255, 160), 3);



73.




ctangle(pen, objectRect)


;



74.




}



75.






76.




e();



77.






78.




oldRect[i] =


new


Rectangle() ;


//


初始





79.




oldRect[i] = rects[i][0];



80.




#endregion




81.




}



82.




}



83.




Cls_ObjectPicture(


ref


pictureBo


x1, objectImage[0]);


//


显示过滤颜色的对象


1




84.




Cls_ObjectPicture(


ref


pictureBo


x2, objectImage[1]);


//


显示过滤颜色的对象


2




85.



}




86.






87.



/


//




88.



/


//


选择绿色的物体为识别的对象




89.



/


//




90.



p


rivate



void


videoSourcePlayer1_Mous eUp(


object


s


ender, MouseEventArgs e)



91.



{




92.





if


( == )

< p>
//


点击左键,


识别绿色对象



93.




Cls_een(nowImg[0],


ref


colo


rFilter[0], e.X, e.Y);



94.





else



if


( == )


//


点击右键,识别红色对象




95.




Cls_d(nowImg[1],


ref


colorF


ilter[1], e.X, e.Y);



96.



}






手手势识别



通过

安德鲁


Kirillov




一些想法关于手手势识别在静止图像和视频。




示例应用程序


(


)- 149 k



示例应用程 序


(


二进制


)- 130 k



样例视频


# 1 - 7290 k



样例视频


# 2 - 11084 k




发布


:


2008



10



12



更新


:


2010



2



16


< br>


编程语言


:


C#



AForge



NET


框架


:


2.1.1





介绍



自从我写了第一篇关于运动检测 的文章


,


我有很多


< br>电子邮件来自世界各地不同的人


,


发现这篇文

< p>
章相当



有用


,


发现许多应用程序的代码在许多不同的领域。



那些



地区包括从简单的视频监控工< /p>


具相当印象应用程序


,


像激光手势识别


,


检测与望远镜彗星


,


检测只蜂鸟



并使镜头的控制高压水

< br>炮和许多其他应用程序。



在本文中

,


我想讨论一个应用程序


,


它使用 运动



检测的第一步


,


然后做一些有趣的检测例程



对象

——


手手势识别。



让我们假定我 们有一个相机


,


显示器



一些区域。



当有人进入该地区


,


使一些


手手势在前面



的相机


,


应用程序应该检测类型的 姿态


,


提高事件


,


为例。



当检测到双手手势识别



,


应用程序可能



执行不同的操作取决于类型的姿态。



例如


,


手势



识别应用程序可以控制一些


设备或另一个应用程序发送



不同的命令根据公认的姿态。



什么样的手



手势我们谈论吗


?


这个


特定的应用程序


,


这是在讨论



篇文章


,


可能认识


15


手势


,


这是


4


个不同位置的组合



2< /p>


手的手不提



,


斜斜向下


,


或提高



直。



本文中描述的算法都是基于



框架


,


它提供了 不同的图像处理应用程序使用的例


程。





应用程序也使用一些运动检测例程


,


受到启发



另一篇文章的框架和专用的


运动检测




在我们进入深入讨论什么应用程序


,


以 及它是如何



实现


,



?


年代看看很快演示


……



运动对象检测和提取



我们可以开始双 手手势识别之前


,


首先我们需要提取



人类吗


?


年代的身体


,


这表明一些手势


,



到一个好的时刻


,




实际应该做手势识别。



我们要对这两个任务



重用一些运动检 测的想法中描


述致力于运动检测



篇文章。



为对象提取任务我们要使用 的方法


,


基于背景



建模。



让吗


?


年代假设视频的第一帧不包含任何


移动



对象


,


但仅仅包含一个背景场景。



当然这样的假设不能调用情况下有效。



但是


,


首先


,


它可能是有效的



对于大多数的情况下


,


所以


很适用


,


和第二个


?


我们的算法



自适应

< br>,


所以它可以处理情况下


,


不仅 当第一帧包含背景。



但是


,


我们呢


?


年代连续


……


所以

< br>,


我们的拳头框架可以作为背景的近似



框架。



/ /


检查背景帧



如果


(backgroundFrame = = null)


{


/ /


保存图片尺寸



宽度


=


身高


=


frameSize =



*



;



/ /


创建初始背景图像



bitmapData = ts(


新矩形

< br>(0,0,


宽度、高度


),


ImageLockMode



PixelFormat


只读的。


Format24bppRgb);


/ /


应用灰度滤波器获得非托管的形象



backgroundFrame = grayscaleFilter




应用


(



UnmanagedImag e(bitmapData));


/ /


打开源图像



的形象。


UnlockBits(bitmapData);





}


现在来吗


?


年代后假设当我们收到一 个新的框架


,


其中包含一些对象


,


和我们



任务是提取它。



当我们有两个图像< /p>


,


图像的背景和对象


,

< br>我们可以使用


区别


过滤得到一个不同的形象


:


/ /


锁定源图像



bitmapData = ts(


新矩形

< br>(0,0,


宽度、高度


),


ImageLockMode



PixelFormat


只读的。


Format24bppRgb);



/ /


应用灰度过滤器



grayscaleFilter




应用


(



Un managedImage(bitmapData)currentFrame);



/ /


打开源图像



的形象。


UnlockBits(bitmapData);



/ /


设置背景帧作为不同的覆盖过滤器



differenceFilter



UnmanagedOverlayImage = backgroundFrame;



/ /


应用不同过滤器



differenceFilter




应用


(currentFrame motionObjectsImage);


差分图像可以看到绝对区别两个图片吗


?


更白



区域显示更高的地区差异和黑色 区域显示领域


的没有区别。





下一个两个步骤


:


1.



阈值图像使用的区别

< p>
阈值


过滤器


,


所以对每个 像素进行分类



重大变化


(

< p>
最有可能造成移


动对象


)


或无显著变化。



2.



去除噪声的图像使用阈值差异


开放


过滤器。



在这一步



独立的像 素


,


这可能是造成嘈杂


的相机和其他的 情况下


,


将被删除


,


所以我们吗


?


会有一个图像


,


这只描述了或多或少的


改变

< br>(


运动区域


)


的重要领域。



/ /


应用阈值过滤



thresholdFilter



ApplyInPlace(motionObjectsImage);



/ /


打开过滤器适用于去除噪声



openingFilter



ApplyInPlace(motionObjectsImage);


看起来我们 有不错的手动作形象


,


下一步我们准备好了吗

< br>?


识别


……


还没有。



的对象吗


?


年代

图像我们很识别作为一个例子代表了人类


?


的身体


,


展示了我们一些手的姿势。



但是


,


之前我们


会得到这样的形象在我们的视频 中


,


我们呢


?


我收到一个



许多其他的框架


,


我们可能会有很多其


他不同的对象

< p>
,


这远非人类的身体。



这样的对象可能是别的越过现场


,


或甚至可能相当大的噪声




我们过滤掉。



摆脱一些错误的对象


,



?


通过图像中的所有对象



并检查它们的大小。



为实

< p>
现这一目标我们将使用


BlobCounter



:


/ /


处理


blob


blobCounter



ProcessImage(motionObjectsImage);


Blob[]= blobCounter


废品。


GetObjectInformation();



int


最大尺寸


= 0;


Blob maxObject =



Blob(0,


新矩形


(0,0,0,0));



/ /


找到最大的


blob


如果


(


斑点


! = NULL)


{


foreach(Blob Blob Blob)


{


int blobSize = gle




宽度


*



如果


(blobSize >


最大尺寸


)


{


最大尺寸


= blobSize;


maxObject =


斑点


;


}


}


}


我们将如何使用信息最大的对象吗


?


年代的尺寸吗


?


首先我们要



实现自适应的背景


,


我们呢


?


前面提到的。



假设时间可能会有



小场景的变化


,


如轻微改变光的条件下


,


甚至是一些运动的小对




小对象出现在现场。



考虑到这些变化


,


我们要



自适应背景


?


我们要改变我们的背景 框架


(



是最初的初始化



第一视频帧


)


的方向变化


致力于


过滤器。



致力于


过滤器的变化略一个图像的


方向与第二提供图像产生较小的影响。



例如


,


如果我们有一个背景图像


,


其中包含场景


,


一个物体


的图像


,


其中包含的



同一 场景加上一个对象


,


然后按顺序应用


致 力于


过滤背景图像


,


将对象图像


经过一段时间的一样吗


?


我们应用


致力于


过滤器的背景



形象


,


更加突出成为对象的存在


(


背景图


像变得





对象形象吗


?

< br>变得更小


)


的区别。



所以


,


我们正在检查当前帧中的最大对象的大小


,


如果不是那么大


,

< br>我们考虑



对象不重要


,


我们只


是更新我们的背景框架


,


适应变化


:


/ /


如果我 们只有小物体


,


我们采用场景的变化



如果


(gle




宽度


< 20)| |(gle




高度


>


20))


{


/ /


移动对当前帧的背景



moveTo wardsFilter



UnmanagedOverlayImage = currentFrame;


m oveTowardsFilter



ApplyInPlace(backgroundFrame);


}


第二个最大的使用对象


?


年代大小是 找到一个


,


这是很重要的


,

< p>
哪些可能



是一个人吗


?


年代的身


体。



为了节省


CPU


时间我们的手手势识别算法不会分析任何对象


,


在当前帧是最大的


,


但只有


对象满足一些要求


:


如果


(gle




宽度


> = minBodyWidth)& &


(gle




高度


> = minBodyHeight)& &


(! firstFrame))


{


/ /


做进一步处理的框架



}



,


现在 我们有一个形象


,


其中包含移动对象


,


对象的大小是很合理


,


所以它可能是一 个



人类吗


?


身体可能。



我们准备通过手手势识别模块的图像进一步处理


?

< p>
再一次


,


没有


……



是的


,


我们呢


?


已经检测到一个相当大的对象


,


这可能是一个人吗


?


年代的身体展示一些姿态。



但是


,


如果对象



还在动吗


?


如果对象没有停止


,


它还没有准备好证明我们真正的姿态将



想展示



?


我们真的想通过所有这些框架手手势识别模块


,


对象是什么



还在运动


,


加载 我们的


CPU



?


更多的


,


因为对象运动仍在< /p>


,


我们甚至可以检测到



的姿态


,


不是想展示的对象。



那么


,


我们



?


没有匆忙与手势识别。



后我们发现的


,


这是一个候选人进行进一步的处 理


,


我们想给它一个机会停下来



一段时间


,


证明


我 们一些吗


?


一个手势。


< p>
如果对象是不断移动


,


我们不想证明什么


,


所以我们可以跳过其处理。



捕捉的时刻对象已经停止


,


我们将使用另一个运动检 测器


,


基于帧间差异。


< p>
运动探测器检查两个


后续视频帧之间的数量变化



(


当前和前一个


),

< br>根据这个做出决定是否有或没有运动检测。



但是


,


在这个特定的



我 们不感兴趣的运动检测


,


但检测的运动。



/ /


检查帧之间的运动水平



differenceFilter



UnmanagedOverlayImage = previousFrame;



/ /


应用不同过滤器



differenceFilter




应用


(currentFrame betweenFramesMotion);



/ /


应用阈值过滤



thresholdFilter



ApplyInPlace(betweenFramesMotion);



/ /


打开过滤器适用于去除噪声



openingFilter



ApplyInPlace(betweenFramesMotion);



/ /


计算像素数量的改变



VerticalIntensityStatistics vis =



VerticalIntensityStatistics(betwe enFramesMotion);



int[]


直方图


=

-


-


-


-


-


-


-


-



本文更新与2021-02-09 07:01,由作者提供,不代表本网站立场,转载请注明出处:https://www.bjmy2z.cn/gaokao/619612.html

AFORGE 图像处理手势识别的相关文章