Kinect开发教程八:OpenNI2显示深度、彩色及融合图像
Kinect开发教程八:OpenNI2显示深度、彩色及融合图像
- 标签:
- OpenNI /
- Kinect /
- 人机互动 /
- 计算机视觉
- 23427
在《Kinect开发教程二:OpenNI读取深度图像与彩色图像并显示》中,小斤介绍了OpenNI读取深度与彩色图像数据的方法,并且借助OpenCV进行显示。
OpenNI2在接口上与OpenNI有了较大变化,具体更新可以查看《OpenNI Migration Guide》。从获取深度,彩色传感器的数据而言,小斤觉得调用更为直观,但对于Kinect,一大缺憾是不支持OpenNI2提供的深度与彩色图像配准的方法(体现在下文中的device.isImageRegistrationModeSupported()方法)。
但使用Kinect的童鞋也不必沮丧,在OpenNI2.1 beta中,小斤看到了新增的convertDepthToColorCoordinates()方法可以做一些深度与彩色坐标数据的转化,它的效果应该是与device.setImageRegistrationMode( IMAGE_REGISTRATION_DEPTH_TO_COLOR )类似的,有兴趣的童鞋可以尝试一下。
在显示方面,小斤还是使用OpenCV,这次是使用OpenCV的C++接口进行操作。
- /*************************
- OpenNI2 Deep, Color and Fusion Image
- Author: Xin Chen, 2013.2
- Blog: http://blog.csdn.net/chenxin_130
- *************************/
- #include <stdlib.h>
- #include <iostream>
- #include <string>
- #include "OpenNI.h"
- #include "opencv2/core/core.hpp"
- #include "opencv2/highgui/highgui.hpp"
- #include "opencv2/imgproc/imgproc.hpp"
- using namespace std;
- using namespace cv;
- using namespace openni;
- void CheckOpenNIError( Status result, string status )
- {
- if( result != STATUS_OK )
- cerr << status << " Error: " << OpenNI::getExtendedError() << endl;
- }
- int main( int argc, char** argv )
- {
- Status result = STATUS_OK;
- //OpenNI2 image
- VideoFrameRef oniDepthImg;
- VideoFrameRef oniColorImg;
- //OpenCV image
- cv::Mat cvDepthImg;
- cv::Mat cvBGRImg;
- cv::Mat cvFusionImg;
- cv::namedWindow("depth");
- cv::namedWindow("image");
- cv::namedWindow("fusion");
- char key=0;
- //【1】
- // initialize OpenNI2
- result = OpenNI::initialize();
- CheckOpenNIError( result, "initialize context" );
- // open device
- Device device;
- result = device.open( openni::ANY_DEVICE );
- //【2】
- // create depth stream
- VideoStream oniDepthStream;
- result = oniDepthStream.create( device, openni::SENSOR_DEPTH );
- //【3】
- // set depth video mode
- VideoMode modeDepth;
- modeDepth.setResolution( 640, 480 );
- modeDepth.setFps( 30 );
- modeDepth.setPixelFormat( PIXEL_FORMAT_DEPTH_1_MM );
- oniDepthStream.setVideoMode(modeDepth);
- // start depth stream
- result = oniDepthStream.start();
- // create color stream
- VideoStream oniColorStream;
- result = oniColorStream.create( device, openni::SENSOR_COLOR );
- // set color video mode
- VideoMode modeColor;
- modeColor.setResolution( 640, 480 );
- modeColor.setFps( 30 );
- modeColor.setPixelFormat( PIXEL_FORMAT_RGB888 );
- oniColorStream.setVideoMode( modeColor);
- //【4】
- // set depth and color imge registration mode
- if( device.isImageRegistrationModeSupported(IMAGE_REGISTRATION_DEPTH_TO_COLOR ) )
- {
- device.setImageRegistrationMode( IMAGE_REGISTRATION_DEPTH_TO_COLOR );
- }
- // start color stream
- result = oniColorStream.start();
- while( key!=27 )
- {
- // read frame
- if( oniColorStream.readFrame( &oniColorImg ) == STATUS_OK )
- {
- // convert data into OpenCV type
- cv::Mat cvRGBImg( oniColorImg.getHeight(), oniColorImg.getWidth(), CV_8UC3, (void*)oniColorImg.getData() );
- cv::cvtColor( cvRGBImg, cvBGRImg, CV_RGB2BGR );
- cv::imshow( "image", cvBGRImg );
- }
- if( oniDepthStream.readFrame( &oniDepthImg ) == STATUS_OK )
- {
- cv::Mat cvRawImg16U( oniDepthImg.getHeight(), oniDepthImg.getWidth(), CV_16UC1, (void*)oniDepthImg.getData() );
- cvRawImg16U.convertTo( cvDepthImg, CV_8U, 255.0/(oniDepthStream.getMaxPixelValue()));
- //【5】
- // convert depth image GRAY to BGR
- cv::cvtColor(cvDepthImg,cvFusionImg,CV_GRAY2BGR);
- cv::imshow( "depth", cvDepthImg );
- }
- //【6】
- cv::addWeighted(cvBGRImg,0.5,cvFusionImg,0.5,0,cvFusionImg);
- cv::imshow( "fusion", cvFusionImg );
- key = cv::waitKey(20);
- }
- //cv destroy
- cv::destroyWindow("depth");
- cv::destroyWindow("image");
- cv::destroyWindow("fusion");
- //OpenNI2 destroy
- oniDepthStream.destroy();
- oniColorStream.destroy();
- device.close();
- OpenNI::shutdown();
- return 0;
- }
小斤由上到下解释一把:
【1】使用OpenNI::initialize()方法进行初始化,对于错误处理,可以使用OpenNI::getExtendedError()方法。在这里,Device对象打开任意一个可用设备。
【2】在OpenNI2中,可以通过创建VideoStream视频流对象来读取设备的深度图像和色彩图像数据。
【3】对于VideoStream视频流对象,我们可以设备它的Mode,包括分辨率,FPS,像素格式等等。对于像素格式的类型,可以使用VideoStream的getSensorInfo()方法获得,目前Kinect只有PIXEL_FORMAT_DEPTH_1_MM可供选择。
【4】如果设备支持深度与彩色图像配准的话,小斤在这里使用OpenNI2自带的接口进行配准。在while循环中,各个VideoStream对象通过readFrame()来读取对应的图像数据。
【5】将OpenNI的图像数据转换为OpenCV可显示的图像格式。对于彩色图像,可以先将数据塞入OpenCV三通道(8位)RGB对象,再转换到BGR来显示。对于深度图像,先放入单通道(16位)对象(这是因为深度数据的值域较大),最近将深度值等比例缩小到[0,255]的值域中,作为灰度图显示。
【6】最后的图像融合,由于addWeighted()方法需要两个输入图像是同一类型,所以小斤首先将深度灰度图(单通道),转化为BGR图像,这样就与彩色图像一致了。再通过该方法进行融合,小斤使用的比例是0.5,0.5,也就是融合图像的每个像素点的值,都是(深度图像该点的像素值*0.5)+ (彩色图像该点的像素值*0.5)。
Kinect开发教程八:OpenNI2显示深度、彩色及融合图像相关推荐
- 由于找不到openni2_Kinect开发教程八:OpenNI2显示深度、彩色及融合图像
在<Kinect开发教程二:OpenNI读取深度图像与彩色图像并显示>中,小斤介绍了OpenNI读取深度与彩色图像数据的方法,并且借助OpenCV进行显示. OpenNI2在接口上与Ope ...
- Kinect开发教程二:OpenNI读取深度图像与彩色图像并显示
细心的朋友肯定已经发现Kinect上长了三只眼睛,其中一个是彩色摄像头,另外两个深度摄像头,一个负责发射红外光,一个负责接收,这样,我们便能通过Kinect得到一幅彩色图像和一幅深度图像.如果大家对K ...
- Kinect开发教程四:用Kinect控制鼠标玩水果忍者PC版
最近Kinect连接Xbox玩水果忍者的视频非常红火,可惜小斤只有本本和Kinect,没法玩Xbox上的体感游戏.幸运的是,寻寻觅觅后,小斤发现水果忍者有PC版本,既然上一个教程我们已经可以让Kine ...
- ODOO13 开发教程八 自定义导出数据到Excel
前面几篇文章,我们已经说明怎么去创建并安装自己的模块.如果你跟着前几篇去做了,那太好了,我们可以一起进行本篇文章的学习了. 本篇实际上为新的odoo开发者说明,如何在odoo中,使用第三方包将数据导出 ...
- 如何开发一个黑白照片还原成彩色,AI黑白图像图片上色系统毕业设计毕设作品
开发准备 第1步:准备好百度智能云的账号 第2步:在百度智能云领取对应AI开发的免费资源包 第3步:创建对应的应用,然后获取对应的开发信息,主要是下面几个 AppID:应用列表中 API Key:应用 ...
- Kinect开发学习笔记之(二)Kinect开发学习资源整理
Kinect开发学习笔记之(二)Kinect开发学习资源整理 zouxy09@qq.com http://blog.csdn.net/zouxy09 刚刚接触Kinect,在网上狂搜资料,获得了很多有 ...
- Kinect开发教程一:OpenNI的安装与开发环境配置
小斤注:关于OpenNI2.X版本的安装与开发环境配置,请参考<Kinect开发教程六:OpenNI2简介.安装与VS开发环境配置> --------------------------- ...
- Kinect开发学习笔记之(八)彩色、深度、骨骼和用户抠图结合
Kinect开发学习笔记之(八)彩色.深度.骨骼和用户抠图结合 zouxy09@qq.com http://blog.csdn.net/zouxy09 我的Kinect开发平台是: Win7 x86 ...
- SAP UI5 应用开发教程之六十八 - 如何实现 SAP UI5 路由失败时显示自定义的 NOT Found 页面
我们平时访问的不少网站,在浏览器地址栏故意输入一个不存在的页面地址时, 都会自动跳转到一个自定义的 NOT Found 页面,比如: 我们在本系列第 31 个步骤学习了 SAP UI5 应用的路由功能 ...
- Kinect开发学习笔记之(六)带游戏者ID的深度数据的提取
Kinect开发学习笔记之(六)带游戏者ID的深度数据的提取 zouxy09@qq.com http://blog.csdn.net/zouxy09 我的Kinect开发平台是: Win7x86 + ...
最新文章
- poj1129Channel Allocation
- mysql命令程序_MySQL命令大全经典版
- 解决IOS微信中 HTML5 中audio的自动播放问题。
- 反击CobaltStrike
- 基于朴素贝叶斯的垃圾邮件分类-着重理解拉普拉斯变换
- 无人机图像处理工具更新——多线程优化版
- build.gradle里test标签的实现原理
- 计组之中央处理器:3、数据通路(单总线结构、专用通路结构)
- Java校招笔试题-Java基础部分(七)
- 微信占用空间太大,删除又担心工作相关聊天记录,有啥好办法没?
- 动态修改ViewPagerIndicator CustomTabPageIndicator Tab标签文字颜色
- 2021最新漫画小程序源码,流量主必备。
- 软件测试的模式(一、)
- [详细]分享验证码接收平台工作原理
- 源码:Spark SQL 分区特性第一弹
- 受保护的Word文档如何编辑?
- 波段划分相关资料总结
- python中shape是什么意思_对numpy中shape的深入理解
- 《彻底卸载chrome及注册表清理》
- oracle10g rac ocssd,求教:安装oracle10g rac 报crs-0223错误问题