Kinect深度图像滤波

最近在做机器视觉方面的一点工作,用Kinect作sensor获取深度数据、颜色、手势识别等。非常感激CNBlog上的两篇博文:(1)独钓寒江的http://www.cnblogs.com/yangecnu/archive/2012/03/30/KinectSDK_Geting_Started.html 从中学到了不少关于在WPF平台上使用C#,利用微软Kinect SDK开发自己的应用程序的知识,给了我很大的帮助,在此表示感谢!

但是博主独钓寒江的博文中,针对深度图像滤波,只简要说了取反和用Bgr32表示深度图像,效果不是很理想。

后来,发现了另一篇博文(2)何文西的http://www.cnblogs.com/TravelingLight/archive/2012/05/25/2517680.html介绍了国外的一篇文章,上面介绍了外国作者自己开发的两种滤波方法:像素滤波法,加权移动平均法。效果很好!可惜只有代码片段无法试验,而且滤波算法不是特别容易理解。实在可惜!

前几天偶然跟踪并找到了作者的源代码http://kinectdepthsmoothing.codeplex.com/,下载来看。运行发现,程序要求:VS2012以上、Kinect SDK 1.7以上版本,而根据独钓寒江的博文指导,其中的代码用的是SDK 1.0,进一步发现其中的一些API函数,数据类型都不相同,再者,Kinectdepthsmoothing中xaml代码用的是后台创建,而独钓寒江的博文中xaml用的是布局式,而我对xaml又不懂,如何把这两个程序结合起来呢?

由于独钓寒江的博文给出的程序中,有大量的功能实现,比如保存图像、鼠标单击显示像素深度值、彩色渲染、人体尺寸获取,游戏者索引等等,而外国朋友的kinectdepthsmoothing程序只有滤波和保存图像,那么考虑把滤波模块移植到独钓寒江的程序中,并且不改变原来的布局式界面。在移植的过程中,主要解决了以下几个类型不兼容的问题:

a) 将short[] pixelData类型改成DepthImagePixel[] pixelData,这里注意:SDK 1.8版本中,private DepthImagePixel[] depthPixels;其中获取深度数据为

1 short depth=depthPixels[i].Depth;

而SKD 1.0版本中,short[] pixelData获取深度数据的方式为

1 Int32 depth = this.depthPixels[pIndex] >> DepthImageFrame.PlayerIndexBitmaskWidth;

需要进行移位操作。而且两种方式的depth类型不一样,一个是short16位,一个是Int32位。

b) 用三通道Bgr32格式的colorBitmap存储深度图像,而不是Gray16格式的depthBitmap。除了深度数组的格式不一样之外,外国朋友的程序中,有这样几行代码值得关注,

1                 //获得当前帧最大和最小可用的深度值
2                 short minDepth = (short)lastDepthFrame.MinDepth;
3                 short maxDepth = (short)lastDepthFrame.MaxDepth; 

以及

 1      //在这里将depthPixels数组中的深度值,逐元素,转换并存储到colorPixles中
 2
 3                //最后,将colorPixels写入colorBitmap中
 4
 5                int colorPixelIndex = 0;
 6
 7                for (int i = 0; i < depthPixels.Length; i++)
 8
 9                {
10
11                 //获取该元素(点)的深度值
12
13                 short depth = depthPixels[i].Depth;
14
15                 byte intensity = (byte)255;
16
17                 int newMax = depth - minDepth;
18
19                 if (newMax > 0)
20
21                      {intensity = (byte)(255 - (255 * newMax / (3150)));  }
22
23                  this.colorPixels[colorPixelIndex++] = intensity;//blue
24
25                 this.colorPixels[colorPixelIndex++] = intensity;//green
26
27                 this.colorPixels[colorPixelIndex++] = intensity;//red
28
29                 ++colorPixelIndex;
30              }

最后将数据写入colorBitmap时,代码为

              this.colorBitmap.WritePixels(
                     new Int32Rect(0, 0, this.colorBitmap.PixelWidth, this.colorBitmap.PixelHeight),
                     this.colorPixels,
                     this.colorBitmap.PixelWidth * sizeof(int),
                     0);

使用了 this.colorBitmap.PixelWidth这个写法,而不是独钓寒江博主的程序中,使用depthStream.FrameHeight创建图像的矩形区域this.depthRect = new Int32Rect(0, 0, depthStream.FrameWidth, depthStream.FrameHeight);

c) 此外,初始化变量(数据容器depthPixels和colorPixels)时,要注意colorPixels的大小

1                 this.depthPixels = new DepthImagePixel[depthStream.FramePixelDataLength];
2                 this.colorPixels = new byte[depthStream.FramePixelDataLength * sizeof(int)];

总之,将两个程序结合起来,要注意两个方面,一是界面的形式,布局还是后台创建,二是,.cs程序中由于使用的SDK版本不同,有很多API和数据类型不一致的地方,需要修改。由于正在做后续的实验,比如加入了自己的利用深度数据进行边缘检测的代码,还有很多想法没有实现,暂时写到这里吧。到时候会将完整代码上传到网络上,供大家参考!谢谢。

下篇文章将介绍基于深度值的目标分割,并附上完整代码。

时间: 2024-08-24 09:57:49

Kinect深度图像滤波的相关文章

Kienct与Arduino学习笔记(2) 深度图像和真实世界坐标系中的深度图

转载请注明出处:http://blog.csdn.net/lxk7280 首先,要接触一下KinectOrbit这个摄像机库,这篇文章中有这个库的下载网址和简单的介绍:http://blog.csdn.net/lxk7280/article/details/38184355.将下载得到的文件放到相应的Processing的一个子文件夹后,即可使用.    KinectOrbit库下的鼠标和键盘的操作方法: 1.右键拖拽:摄像机摇拍. 2.左键拖拽:绕对象旋转. 3.滚动:缩放操作. 4.P键保存

【opencv学习笔记1】5种图像滤波辨析:方框、均值、高斯、中值、双边

图像滤波 什么是图像滤波 图像滤波,即在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制,是图像预处理中不可缺少的操作,其处理效果的好坏将直接影响到后续图像处理和分析的有效性和可靠性. 图像滤波的目的 a.消除图像中混入的噪声 b.为图像识别抽取出图像特征 图像滤波的要求 a.不能损坏图像轮廓及边缘 b.图像视觉效果应当更好 滤波器的定义 滤波器,顾名思义,是对波进行过滤的器件.(摘自网络) 以上的定义是针对物理器件的,但对于图像滤波而言显然也是适用的. 大家都用过放大镜,这里就以此举一个例

opencv学习之路(12)、图像滤波

一.图像滤波简介 二.方框滤波--boxFilter() 1 #include<opencv2/opencv.hpp> 2 using namespace cv; 3 4 void main(){ 5 Mat src=imread("E://1.jpg"); 6 Mat dst; 7 //方框滤波器,-1代表原图像深度,size内核大小,true按权重相加(此时等于均值滤波),false按原像素相加(所以很多像素点都大于了255,如上图所示) 8 boxFilter(src

opencv第三课,图像滤波

1.介绍 OpenCV图像处理技术中比较热门的图像滤波操作主要被分为了两大类:线性邻域滤波和非线性滤波.线性邻域滤波常见的有“方框滤波“,”均值滤波“和”高斯滤波“三种,二常见的非线性滤波主要是中值滤波”和“双边滤波”.本文将将简略介绍这几种滤波操作的不同点,以及他们各自的特点. 2.理论与概念讲解 图像滤波,即在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制,是图像预处理中不可缺少的操作,其处理效果的好坏将直接影响到后续图像处理和分析的有效性和可靠性.消除图像中的噪声成分叫作图像的平滑化

kinect2.0 基础篇第3篇 用C#在Visual Studio上编写把深度图像转换成彩色图像

本示例实现的功能有:有两个Radiobutton控件  选一个,点击启动按钮, 第一个是将深度图像转换成彩色图像 第二个是将深度图像做一些简单处理(例如太暗的调白一点) 涉及到一点遥感图像处理知识,将深度数据值转换为色调和饱和度 遥感图像处理那块不懂,有兴趣的自己可以研究研究,代码的基于kinect1的教程,慢慢尝试出来的,虽然功能实现了,但是原理还不是很懂 <Window x:Class="EnhancedDepthWPF.MainWindow" xmlns="htt

【OpenCV】5种图像滤波辨析:方框、均值、高斯、中值、双边

图像滤波 什么是图像滤波 图像滤波,即在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制,是图像预处理中不可缺少的操作,其处理效果的好坏将直接影响到后续图像处理和分析的有效性和可靠性.(摘自网络) 图像滤波的目的 1,消除图像中混入的噪声 2,为图像识别抽取出图像特征 图像滤波的要求 1,不能损坏图像轮廓及边缘 2,图像视觉效果应当更好 滤波器的定义 滤波器,顾名思义,是对波进行过滤的器件.(摘自网络) 以上的定义是针对物理器件的,但对于图像滤波而言显然也是适用的. 大家都用过放大镜,这里就

Kinect 深度图像格式

Kinect的深度图像有16bit,2byte,如图: 第15位:标志位,不用做深度计算 第14~3位:深度图像数据,即距离,以毫米为单位 第0~2位:深度图中人的ID(PlayerID) 深度图有两种格式: FTIMAGEFORMAT_UINT16_D16 16位全表示深度数据,即距离,单位为毫米.不包含PlayerID. FTIMAGEFORMAT_UINT16_D13P3 即为上边图中显示的格式,包含PlayerID. Reference: http://www.benbarbour.co

python+opencv实现机器视觉基础技术(边缘提取,图像滤波,边缘检测算子,投影,车牌字符分割)

目录 一:边缘提取 1.对图像进行阈值分割并反色 2.边缘提取 二:图像滤波 1.读取原图 2.均值滤波 3.中值滤波 4.高斯滤波 5.高斯边缘检测 三:边缘检测算子 1.显示原图 2.对图像进行反色 3.对图像用sobel方法进行边缘检测 4.对图像用robert方法进行边缘检测 四:投影 1.显示原图 2.垂直方向投影 3.水平方向投影 五:车牌字符分割 1.读取原图 2.灰度转换 3.反色 4.阈值分割 5.投影 6.字符识别匹配分割 ??机器视觉是人工智能正在快速发展的一个分支.简单说

11.图像滤波与滤波器

图像滤波,指在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制,是图像预处理中不可缺少的操作,其处理效果的好坏将直接影响到后续图像处理和分析的有效性和可靠性. 消除图像中的噪声成分称为图像的平滑化或者滤波操作.信号或图像的能量大部分集中在幅度谱的低频和中频段.而在较高频段,有用的信息经常被噪声淹没.滤波的目的有2个:一个是抽出对象的特征作为图像识别的特征模式:一个是为适应图像处理的要求,消除图像数字化时所混入的噪声. 对于滤波而言,处理的要求有2个:一个是不能损坏图像的轮廓及边缘等重要信息: