#include "stdafx.h"

#include <XnCppWrapper.h>
#include "cv.h"
#include "highgui.h"

#define SAMPLE_XML_PATH "F:/KFQ/downloads/openni_src/openni/Data/SamplesConfig.xml"
#define MAX_DEPTH 10000
#define CHECK_RC(nRetVal, what)										/
	if (nRetVal != XN_STATUS_OK)									/
	{																/
	printf("%s failed: %s/n", what, xnGetStatusString(nRetVal));	/
	printf("press any key to escape/n");							/
	getchar();														/
	return nRetVal;}	



float g_depthHist[MAX_DEPTH];
xn::ImageMetaData g_imd;
xn::DepthMetaData g_dmd;
xn::Context g_context;
xn::ImageGenerator g_image;	
xn::DepthGenerator g_depth;
IplImage *g_pImgColor=0;
IplImage *g_pImgDepth=0;

//note that the channels' order is B G R in opencv
void UpdateColorImage(IplImage *pImg);
void UpdateDepthImage(IplImage *pImg);
int _tmain(int argc, _TCHAR* argv[])
{
	XnStatus nRetVal = XN_STATUS_OK; 		
	
	nRetVal=g_context.Init();
	g_context.OpenFileRecording("F:/xx.ONI");	
	nRetVal=g_context.FindExistingNode(XN_NODE_TYPE_IMAGE,g_image);	
	CHECK_RC(nRetVal,"find image");
	nRetVal=g_context.FindExistingNode(XN_NODE_TYPE_DEPTH,g_depth);
	CHECK_RC(nRetVal,"find depth");

	g_image.GetMetaData(g_imd);
	g_depth.GetMetaData(g_dmd);

	bool bRun=true;
	int nWidth;
	int nHeight;
	
	while(bRun)
	{
		nRetVal=g_context.WaitAnyUpdateAll();
		if(nRetVal!=XN_STATUS_OK)
		{
			printf("failed update/n");
			continue;
		}
		g_image.GetMetaData(g_imd);
		g_depth.GetMetaData(g_dmd);
		
		if(g_pImgColor==0)
		{
			nWidth=g_imd.XRes();
			nHeight=g_imd.YRes();
			g_pImgColor=cvCreateImage(cvSize(nWidth,nHeight),8,3);
			cvZero(g_pImgColor);
		}
		if(g_pImgDepth==0)
		{
			nWidth=g_dmd.XRes();
			nHeight=g_dmd.YRes();
			g_pImgDepth=cvCreateImage(cvSize(nWidth,nHeight),8,3);
			cvZero(g_pImgDepth);
		}
		
		UpdateColorImage(g_pImgColor);
		UpdateDepthImage(g_pImgDepth);		
		
		cvShowImage("img",g_pImgColor);
		cvShowImage("depth",g_pImgDepth);
		char c=cvWaitKey(30);
		if(27==c)break;
	}
	if(g_pImgDepth)cvReleaseImage(&g_pImgDepth);
	if(g_pImgColor)cvReleaseImage(&g_pImgColor);
	g_context.Shutdown();
	return 0;
}

void UpdateColorImage(IplImage *pImg)
{
	if(pImg->widthStep%4!=0)
	{
		const XnRGB24Pixel *pSrc=g_imd.RGB24Data();
		
		for(int i=0;i<pImg->height;i++)
		{
			char *pDstRow=pImg->imageData+i*pImg->widthStep;
			for(int j=0;j<pImg->width;j++)
			{				
				*(pDstRow+3*j)=pSrc->nBlue;				
				*(pDstRow+3*j+1)=pSrc->nGreen;				
				*(pDstRow+3*j+2)=pSrc->nRed;
				pSrc++;				
			}
		}
	}
	else
	{
		xnOSMemCopy(pImg->imageData,g_imd.RGB24Data(),pImg->width*pImg->height*sizeof(XnUInt8)*3);
		cvCvtColor(pImg,pImg,CV_BGR2RGB);
	}	
}
void UpdateDepthImage(IplImage *pImg)
{
	int numberOfPoints=0;
	const XnDepthPixel* pDepth = g_dmd.Data();
	xnOSMemSet(g_depthHist, 0, MAX_DEPTH*sizeof(float));
	unsigned long int total=0;
	int height=g_dmd.YRes();
	int width=g_dmd.XRes();
	
	//Calculate the accumulative histogram
	for(int i=0;i<height;i++)
	{
		for(int j=0;j<width;j++)
		{
			unsigned int val=*pDepth;
			if(val!=0)
			{
				g_depthHist[val]++;
				
				numberOfPoints++;
			}
			pDepth++;
			total++;
		}
	}
	for (int nIndex=1; nIndex<MAX_DEPTH; nIndex++)
	{
		g_depthHist[nIndex] += g_depthHist[nIndex-1];
	}
	if (numberOfPoints)
	{
		for (int nIndex=1; nIndex<MAX_DEPTH; nIndex++)
		{
			g_depthHist[nIndex] = (unsigned int)(256 * (1.0f - (g_depthHist[nIndex] / numberOfPoints)));
		}
	}
	
	const XnDepthPixel* pDepthRow = g_dmd.Data();
	for(int i=0;i<g_dmd.YRes();i++)
	{
		char *pDstRow=pImg->imageData+i*pImg->widthStep;
		for(int j=0;j<g_dmd.XRes();j++)
		{
			if(*pDepthRow!=0)
			{
				int val=g_depthHist[*pDepthRow];
				//B G R
				*(pDstRow+3*j)=0;
				*(pDstRow+3*j+1)=val;
				*(pDstRow+3*j+2)=val;
			}
			
			pDepthRow++;
		}
	}
}

  

需要注意下的是如果自己手动创建节点,在调用context.StartGeneratingAll()的时候会产生错误,这应该是我在创建的时候没有配置好相关属性还是别的什么,总之为了避免麻烦还是使用xml来配置更好

opencv里的像素通道顺序是BGR

posted on 2011-04-08 03:31  柯大侠  阅读(1519)  评论(0编辑  收藏  举报