1 系统硬件架构
如图1所示,图像识别硬件系统主要由SPCA563B单片机、USB控制器、图像传感器、存储器控制器和语音输出控制器等组成。
1.1 SPCA563B单片机
SPCA563B单片机的硬件特征如下:提供320×240的8位CMOS图像传感器接口;具有自动白平衡和获得参数控制功能;具有图像颜色校正和图像Gamma校正功能;具有7种颜色过滤功能;具有良好的减小噪声的滤波器;能够在一张图片中检测到21个目标物体的大小和位置,并将其结果存放于嵌入在CPU内部的RAM中;16位μnSP CPU内核,内嵌1K×16位的RAM和32K×16位的ROM;具有可选择的外部RAM和ROM接口;具有USBl.1的接口;3.3V电压供电;128/64脚LQFP封装(其中128脚有可选择的并行接口,48脚则没有)。此系统采用48脚的LQFP封装,其硬件电路如图2所示。
1.2 USB控制器
SPCA563B内嵌USBl.1的控制器,利用USB接口可以与PC进行通信,结合PC端软件来实现ISP及在线调试程序,此外可以利用USB来为系统供电。其电路如图3所示。
1.3 图像传感器
本系统采用SPCA3010A CMOS图像传感器,图像输出为QVGA(320×240)大小的RGB格式。SPCA563B通过I2S接口来控制SPCA3010A CMOS图像传感器。此CMOS图像传感器支持stand by省电模式,其电路如图4所示。
1.4 存储器控制器
外扩SPR4096A Flash存储器,主要用来存储系统需要的语音数据。SPR4096A FJash具有如下特征:512K×8位的存储空间;内嵌4K×8位的SRAM;外部CPU可以通过串行接口或8位并行接口来访问Flash/SRAM;I/O接口的电压范围为2.25~3.6 V,并支持stancl by的省电模式。在数据存储量比较小的情况下,用SPR40396A可以大大降低系统的成本。电路如图5所示。
1.5 语音输出控
语音输出控制器的主要作用是将SPCA563B的两路音频输出通过SPY0030放大,由扬声器播放。其硬件电路如图6所示。
2 系统软件设计
本图像识别系统的识别功能主要通过软件系统来实现。为了提高程序的可移植性,为将来该系统功能扩展预留空间,整个软件系统采用分模块、分层次的方法编写程序,采用汇编语言实现对寄存器的读/写以及对中断的控制,并为上层的开发提供灵活的接口。上层采用C语言编写,通过调用底层函数来间接对硬件资源进行操作。这样编写程序使整个系统结构清晰,程序可移植性和可扩展性增强,而且占用硬件资源少,为系统功能的扩展和进一步开发预留充分的空间。
整个软件系统由主程序、图像识别功能模块子程序、中断服务子程序和语音输出子程序等组成。主程序负责整个系统的协调和控制工作,通过调用不同的子程序来实现不同的功能。主程序流程如图7所示。
为突出系统的特点,下面通过手势识别的实例来重点描述图像识别原理。手势识别包含两个步骤:手形的轮廓跟踪,提取其轮廓的相关数据;手势的识别,在上一步得到的数据的基础上进行分析判断而得到结果。
2.1 轮廓跟踪算法实现
轮廓跟踪的目的是获得图像的外部轮廓特征(包括目标物体边缘点的坐标和方向),为图像的形状分析做准备。SPCA563B的DSP针对肤色有一系列的颜色处理,这样系统就可以方便图像转化为肤色与非肤色的二值图像。通过对暂存在SRAM中的二值图像进行数据分析,来提取手形的边缘轮廓。
轮廓跟踪算法步骤如下:
①按从上到下、从左到右的顺序扫描图像,寻找第一个非白像素作为边界起始点A[0],记录A[0]点的坐标(A[0].x,A[0].y)。A[0]是具有最小行和列值的边界点。再定义一个扫描方向变量dir,该变量用于记录上一步中沿着前一个边界点到当前边界点的移动方向。其初始化取值为A[0].dir=7;扫描方向定义如图8所示。
假设当前的坐标为(x,y),则其8个邻域坐标如下:
②按逆时针方向搜索当前像素的3×3的邻域,其起始搜索方向设定如下:
若A[n-1].dir为奇数,则取(A[n-1].dir+7)rood 8;
若A[n-1].dir为偶数,则取(A[n-1].dir+6)mod 8。
在3×3邻域中搜索到的第一个与当前像素相同的像素便为新的边界点A[n],同时更新记录从上一点搜索到边界点A[n]的方向变量A[n].dir,记录新的边界点的坐标(A[n].x,A[n].y)。
③如果边界点A[n]等于第一个边界点A[0],即(A[n].x==A[O].x&&A[n].y==A[0].y)。停止搜索。结束跟踪。否则重复步骤②。
由边界点A[O]、A[1]、A[2]、…、A[n]构成的边界便为要跟踪的边界。算法中步骤①的作用足找出第一个边界点,步骤③的作用是找出所有的边界点。如图9所示,左边为原始图像,右边是用该算法仿真的结果。
2.2 手势识别算法实现
我们的主要目的是找出伸出手指的个数。开始用行扫描的方法通过行内从O→1或1→O黑白像素变化的次数来确定伸出手指的个数,但这种算法对于倾斜一定角度的手指数目判断存在一定问题,因此转而采用“提取指尖点算法”。
提取指尖点的方法着眼于从手势轮廓中搜索出指尖点,一个指尖点对应于一根手指,最后根据得到指尖点的个数来判定手指数目。判断是不是指尖:分析手的形状,手指的两边基本上是平行的。一直按逆时针方向前进,每经过一次指尖,手形轮廓的走向发生反向的变化。由于手形轮廓的边缘存在一定的毛刺,因此可以用多点方向的平均来减小毛刺的影响。这里取36点方向的平均,表示为Average_dix[i]。是否经过指尖的判断条件1:126<=|Average_dir[i-1]一Average_dir[i+1]|<=162。(说明:两点方向相反,其方向值差4,3.5×36=126,4.5×36=162。)
再分析手的形状,两手指之间边缘轮廓的走向也满足判断条件l,故必须添加判断条件。如图10所示,当沿着一个方向搜索手的边缘轮廓时,经过指尖走向一定与手指间缺口走向相反。因此,必须假设判定条件2:
Is_FingerVertex(dir0,dirl,dir2);
这个函数是用来通过连续3点的方向来判断这3点是否为逆时针走向。由于是沿着逆时针方向搜索边缘轮廓的,故在判定条件1成立的前提下加上Is_FingerVertex(Average_dir[i-1],Average_dir[i],Average_dir[i+1])就可以判断是否为指尖,从而判定手指的数目。顺序3点是否为逆时针走向,具体在程序中可以构造一个循环队列来实现。测试结果表明这种算法非常稳定。
结语
SPCA563B内部嵌入功能强大的图像颜色处理的DSP,用它来做图像识别系统的主控芯片十分方便、快捷。同时该系统具有语音输出提示功能,操作更加人性化,并且可以通过USBl.1接口与PC进行通信;配合PC端的调试工具,还可以大大缩短图像识别功能开发的周期。