OpenNI2获取华硕XtionProLive深度图和彩色图并用OpenCV显示
实验环境
XtionProLive,Win7 32位,VS2010,OpenNI2.1.0,OpenCV2.4.4
源码
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/opencv.hpp>
#include <iostream>
#include "OpenNI.h"
using namespace openni;
using namespace cv;
using namespace std;
int main()
{
Status rc = STATUS_OK; // OpenNI函数执行结果
//OpenNI2图
VideoFrameRef oniDepthImg, oniColorImg;
//OpenCV图
Mat cvDepthImg, cvBGRImg, cvFusionImg;
//初始化OpenNI2
rc = OpenNI::initialize();
//打开Kinect或Xtion设备
Device device;
const char * deviceURL = openni::ANY_DEVICE; //设备名
rc = device.open(deviceURL);
//创建并打开深度数据流
VideoStream oniDepthStream; //深度数据流
rc = oniDepthStream.create(device, SENSOR_DEPTH); //创建深度数据流
if( STATUS_OK == rc )
{
//设置深度视频模式
VideoMode modeDepth;
modeDepth.setResolution(320,240/*640,480*/); //分辨率
modeDepth.setFps(30); //帧率
modeDepth.setPixelFormat(PIXEL_FORMAT_DEPTH_1_MM); //深度像素格式
oniDepthStream.setVideoMode(modeDepth);
oniDepthStream.start(); // 打开深度数据流
if(STATUS_OK != rc)
{
cerr << "无法打开深度数据流:"<<OpenNI::getExtendedError()<<endl;
oniDepthStream.destroy();
}
}
else
{
cerr << "无法创建深度数据流:"<<OpenNI::getExtendedError()<<endl;
}
//创建并打开彩色数据流
VideoStream oniColorStream; //RGB数据流
rc = oniColorStream.create(device, SENSOR_COLOR);
if(STATUS_OK == rc)
{
//设置彩色视频模式
VideoMode modeColor;
//不知道为什么,彩色图的分辨率无论如何设置始终都是320*240
modeColor.setResolution(320,240/*1280,1040*/);//分辨率
modeColor.setFps(30);//帧率
modeColor.setPixelFormat(PIXEL_FORMAT_RGB888);
//设置深度图和彩色图的配准模式
if(device.isImageRegistrationModeSupported(IMAGE_REGISTRATION_DEPTH_TO_COLOR))
{
device.setImageRegistrationMode(IMAGE_REGISTRATION_DEPTH_TO_COLOR); //深度到彩色图配准
}
rc = oniColorStream.start(); //打开彩色数据流
if( STATUS_OK != rc )
{
cerr<< "无法打开彩色数据流:"<<OpenNI::getExtendedError()<<endl;
oniColorStream.destroy();
}
}
else
{
cerr << "无法创建彩色数据流:"<<OpenNI::getExtendedError()<<endl;
}
if (!oniDepthStream.isValid() || !oniColorStream.isValid())
{
cerr << "彩色或深度数据流不合法"<<endl;
OpenNI::shutdown();
return 1;
}
namedWindow("depth");
namedWindow("RGB");
namedWindow("fusion");
while(true)
{
//读取一帧深度图
if( STATUS_OK == oniDepthStream.readFrame(&oniDepthImg) )
{
Mat cvRawImg16U(oniDepthImg.getHeight(), oniDepthImg.getWidth(), CV_16UC1, (void*)oniDepthImg.getData());
cvRawImg16U.convertTo(cvDepthImg, CV_8U, 255.0/(oniDepthStream.getMaxPixelValue()));
flip(cvDepthImg,cvDepthImg,1);//水平翻转
imshow("depth", cvDepthImg);
}
//读取一帧彩色图
if( STATUS_OK == oniColorStream.readFrame(&oniColorImg) )
{
Mat cvRGBImg(oniColorImg.getHeight(), oniColorImg.getWidth(), CV_8UC3, (void*)oniColorImg.getData());
cvtColor(cvRGBImg, cvBGRImg, CV_RGB2BGR);
flip(cvBGRImg,cvBGRImg,1);//水平翻转
imshow("RGB", cvBGRImg);
}
//融合图
cvtColor(cvDepthImg,cvFusionImg,CV_GRAY2BGR);
addWeighted(cvBGRImg, 0.5, cvFusionImg, 0.5, 0, cvFusionImg);
flip(cvFusionImg,cvFusionImg,1);//水平翻转
imshow("fusion", cvFusionImg);
waitKey(30);//没有waitKey不显示图像
}
destroyWindow("depth");
destroyWindow("RGB");
destroyWindow("fusion");
oniDepthStream.destroy();
oniColorStream.destroy();
device.close();
OpenNI::shutdown();
return 0;
}
}
实验结果
使用OpenNI2打开XtionProLive时有一个问题,彩色图分辨率无论如何设置始终是320*240
,深度图倒是可以设成640*480
,而OpenNI1.x是可以获取640*480
的彩色图的。
彩色图
配准到彩色图后的深度图
1:1融合图
相关资源
源码下载:
http://download.csdn.net/detail/masikkk/7582485
OpenNI2.1下载:
http://download.csdn.net/detail/masikkk/7582489
参考
Kinect+OpenNI学习笔记之2(获取kinect的颜色图像和深度图像)
Kinect+OpenNI学习笔记之4(OpenNI获取的图像结合OpenCV显示)
Kinect开发教程二:OpenNI读取深度图像与彩色图像并显示
上一篇 SQL基础
页面信息
location:
protocol
: host
: hostname
: origin
: pathname
: href
: document:
referrer
: navigator:
platform
: userAgent
: