void drawSelectionChanged(SelectionState state, IntRect selection) { g_DrawUserInput.State = state; g_DrawUserInput.Rect = selection; if (state == SELECTION_DONE) { // Crop depth if (getDepthStream().isValid() && isDepthOn() && g_DrawConfig.Streams.Depth.Coloring != DEPTH_OFF) { drawCropStream(getDepthStream(), g_DrawConfig.DepthLocation, selection, 2); } // Crop image if (getColorStream().isValid() && isColorOn() && g_DrawConfig.Streams.Color.Coloring != COLOR_OFF) { drawCropStream(getColorStream(), g_DrawConfig.ColorLocation, selection, 4); } // Crop IR if (getIRStream().isValid() && isIROn() && g_DrawConfig.Streams.Color.Coloring != COLOR_OFF) { drawCropStream(getIRStream(), g_DrawConfig.ColorLocation, selection, 4); } } }
bool captureOpenWriteDevice() { XnStatus nRetVal = XN_STATUS_OK; NodeInfoList recordersList; nRetVal = g_Context.EnumerateProductionTrees(XN_NODE_TYPE_RECORDER, NULL, recordersList); START_CAPTURE_CHECK_RC(nRetVal, "Enumerate recorders"); // take first NodeInfo chosen = *recordersList.Begin(); nRetVal = g_Context.CreateProductionTree(chosen); START_CAPTURE_CHECK_RC(nRetVal, "Create recorder"); g_Capture.pRecorder = new Recorder; nRetVal = chosen.GetInstance(*g_Capture.pRecorder); START_CAPTURE_CHECK_RC(nRetVal, "Get recorder instance"); nRetVal = g_Capture.pRecorder->SetDestination(XN_RECORD_MEDIUM_FILE, g_Capture.csFileName); START_CAPTURE_CHECK_RC(nRetVal, "Set output file"); if (getDevice() != NULL) { nRetVal = g_Capture.pRecorder->AddNodeToRecording(*getDevice(), XN_CODEC_UNCOMPRESSED); START_CAPTURE_CHECK_RC(nRetVal, "add device node"); } if (isDepthOn() && (g_Capture.DepthFormat != CODEC_DONT_CAPTURE)) { nRetVal = g_Capture.pRecorder->AddNodeToRecording(*getDepthGenerator(), g_Capture.DepthFormat); START_CAPTURE_CHECK_RC(nRetVal, "add depth node"); } if (isImageOn() && (g_Capture.ImageFormat != CODEC_DONT_CAPTURE)) { nRetVal = g_Capture.pRecorder->AddNodeToRecording(*getImageGenerator(), g_Capture.ImageFormat); START_CAPTURE_CHECK_RC(nRetVal, "add image node"); } if (isIROn() && (g_Capture.IRFormat != CODEC_DONT_CAPTURE)) { nRetVal = g_Capture.pRecorder->AddNodeToRecording(*getIRGenerator(), g_Capture.IRFormat); START_CAPTURE_CHECK_RC(nRetVal, "add IR stream"); } if (isAudioOn() && (g_Capture.AudioFormat != CODEC_DONT_CAPTURE)) { nRetVal = g_Capture.pRecorder->AddNodeToRecording(*getAudioGenerator(), g_Capture.AudioFormat); START_CAPTURE_CHECK_RC(nRetVal, "add Audio stream"); } return true; }
void drawColor(IntRect* pLocation, IntPair* pPointer, int pointerRed, int pointerGreen, int pointerBlue) { if (g_DrawConfig.Streams.Color.Coloring == COLOR_OFF) return; if (!isColorOn() && !isIROn()) { drawClosedStream(pLocation, "Color"); return; } openni::VideoFrameRef colorMD; int depthWidth = 0, depthHeight = 0, depthFullWidth = 0, depthFullHeight = 0; int depthOriginX = 0, depthOriginY = 0; if (isColorOn()) { colorMD = getColorFrame(); if (!colorMD.isValid()) return; } else if (isIROn()) { colorMD = getIRFrame(); } else return; if (!colorMD.isValid()) return; if (colorMD.getFrameIndex() == 0) { return; } openni::VideoFrameRef depthMetaData = getDepthFrame(); int width = colorMD.getWidth(); int height = colorMD.getHeight(); int fullWidth = colorMD.getVideoMode().getResolutionX(); int fullHeight = colorMD.getVideoMode().getResolutionY(); int originX = colorMD.getCropOriginX(); int originY = colorMD.getCropOriginY(); XnUInt8* pColor = (XnUInt8*)colorMD.getData(); bool useDepth = false; openni::PixelFormat format = colorMD.getVideoMode().getPixelFormat(); openni::DepthPixel* pDepth = NULL; if (depthMetaData.isValid()) { useDepth = true; depthWidth = depthMetaData.getWidth(); depthHeight = depthMetaData.getHeight(); depthFullWidth = depthMetaData.getVideoMode().getResolutionX(); depthFullHeight = depthMetaData.getVideoMode().getResolutionY(); depthOriginX = depthMetaData.getCropOriginX(); depthOriginY = depthMetaData.getCropOriginY(); pDepth = (openni::DepthPixel*)depthMetaData.getData(); } for (XnUInt16 nY = 0; nY < height; nY++) { XnUInt8* pTexture = TextureMapGetLine(&g_texColor, nY + originY) + originX*4; if (format == openni::PIXEL_FORMAT_YUV422) { YUV422ToRGB888(pColor, pTexture, width*2, g_texColor.Size.X*g_texColor.nBytesPerPixel); pColor += width*2; } else if (format == openni::PIXEL_FORMAT_YUYV) { YUYVToRGB888(pColor, pTexture, width*2, g_texColor.Size.X*g_texColor.nBytesPerPixel); pColor += width*2; } else { XnDouble dRealY = (nY + originY) / (XnDouble)fullHeight; XnInt32 nDepthY = dRealY * depthFullHeight - depthOriginY; for (XnUInt16 nX = 0; nX < width; nX++, pTexture+=4) { XnInt32 nDepthIndex = 0; if (useDepth) { XnDouble dRealX = (nX + originX) / (XnDouble)fullWidth; XnInt32 nDepthX = dRealX * depthFullWidth - depthOriginX; if (nDepthX >= depthWidth || nDepthY >= depthHeight || nDepthX < 0 || nDepthY < 0) { nDepthIndex = -1; } else { nDepthIndex = nDepthY*depthWidth + nDepthX; } } switch (format) { case openni::PIXEL_FORMAT_RGB888: pTexture[0] = pColor[0]; pTexture[1] = pColor[1]; pTexture[2] = pColor[2]; pColor+=3; break; case openni::PIXEL_FORMAT_GRAY8: pTexture[0] = pTexture[1] = pTexture[2] = *pColor; pColor+=1; break; case openni::PIXEL_FORMAT_GRAY16: pTexture[0] = pTexture[1] = pTexture[2] = *((XnUInt16*)pColor) >> 2; pColor+=2; break; default: assert(0); return; } // decide if pixel should be lit or not if (g_DrawConfig.Streams.Color.Coloring == DEPTH_MASKED_COLOR && (!depthMetaData.isValid() || nDepthIndex == -1 || pDepth[nDepthIndex] == 0)) { pTexture[3] = 0; } else { pTexture[3] = 255; } } } } if (pPointer != NULL) { TextureMapDrawCursor(&g_texColor, *pPointer, pointerRed, pointerGreen, pointerBlue); } TextureMapUpdate(&g_texColor); TextureMapDraw(&g_texColor, pLocation); }
void drawFrame() { // calculate locations g_DrawConfig.DepthLocation.uBottom = 0; g_DrawConfig.DepthLocation.uTop = WIN_SIZE_Y - 1; g_DrawConfig.DepthLocation.uLeft = 0; g_DrawConfig.DepthLocation.uRight = WIN_SIZE_X - 1; g_DrawConfig.ColorLocation.uBottom = 0; g_DrawConfig.ColorLocation.uTop = WIN_SIZE_Y - 1; g_DrawConfig.ColorLocation.uLeft = 0; g_DrawConfig.ColorLocation.uRight = WIN_SIZE_X - 1; if (g_DrawConfig.Streams.ScreenArrangement == SIDE_BY_SIDE) { g_DrawConfig.DepthLocation.uTop = WIN_SIZE_Y / 2 - 1; g_DrawConfig.DepthLocation.uRight = WIN_SIZE_X / 2 - 1; g_DrawConfig.ColorLocation.uTop = WIN_SIZE_Y / 2 - 1; g_DrawConfig.ColorLocation.uLeft = WIN_SIZE_X / 2; } // Texture map init openni::VideoFrameRef* pDepthMD = &getDepthFrame(); if (isDepthOn() && pDepthMD->isValid()) { int maxDepth = 0; maxDepth = getDepthStream().getMaxPixelValue(); g_fMaxDepth = maxDepth; TextureMapInit(&g_texDepth, pDepthMD->getVideoMode().getResolutionX(), pDepthMD->getVideoMode().getResolutionY(), 4, pDepthMD->getWidth(), pDepthMD->getHeight()); fixLocation(&g_DrawConfig.DepthLocation, pDepthMD->getVideoMode().getResolutionX(), pDepthMD->getVideoMode().getResolutionY()); } openni::VideoFrameRef* pImageMD = NULL; if (isColorOn()) { pImageMD = &getColorFrame(); } else if (isIROn()) { pImageMD = &getIRFrame(); } if (pImageMD != NULL && pImageMD->isValid()) { TextureMapInit(&g_texColor, pImageMD->getVideoMode().getResolutionX(), pImageMD->getVideoMode().getResolutionY(), 4, pImageMD->getWidth(), pImageMD->getHeight()); fixLocation(&g_DrawConfig.ColorLocation, pImageMD->getVideoMode().getResolutionX(), pImageMD->getVideoMode().getResolutionY()); } // check if pointer is over a map bool bOverDepth = (pDepthMD != NULL && pDepthMD->isValid()) && isPointInRect(g_DrawUserInput.Cursor, &g_DrawConfig.DepthLocation); bool bOverImage = (pImageMD != NULL && pImageMD->isValid()) && isPointInRect(g_DrawUserInput.Cursor, &g_DrawConfig.ColorLocation); bool bDrawDepthPointer = false; bool bDrawImagePointer = false; int imagePointerRed = 255; int imagePointerGreen = 0; int imagePointerBlue = 0; IntPair pointerInDepth = {0,0}; IntPair pointerInColor = {0,0}; if (bOverImage) { pointerInColor.X = (double)(g_DrawUserInput.Cursor.X - g_DrawConfig.ColorLocation.uLeft) / (g_DrawConfig.ColorLocation.uRight - g_DrawConfig.ColorLocation.uLeft + 1) * pImageMD->getVideoMode().getResolutionX(); pointerInColor.Y = (double)(g_DrawUserInput.Cursor.Y - g_DrawConfig.ColorLocation.uBottom) / (g_DrawConfig.ColorLocation.uTop - g_DrawConfig.ColorLocation.uBottom + 1) * pImageMD->getVideoMode().getResolutionY(); bDrawImagePointer = true; } if (bOverDepth) { pointerInDepth.X = (double)(g_DrawUserInput.Cursor.X - g_DrawConfig.DepthLocation.uLeft) / (g_DrawConfig.DepthLocation.uRight - g_DrawConfig.DepthLocation.uLeft + 1) * pDepthMD->getVideoMode().getResolutionX(); pointerInDepth.Y = (double)(g_DrawUserInput.Cursor.Y - g_DrawConfig.DepthLocation.uBottom) / (g_DrawConfig.DepthLocation.uTop - g_DrawConfig.DepthLocation.uBottom + 1) * pDepthMD->getVideoMode().getResolutionY(); bDrawDepthPointer = true; if (!bOverImage && g_DrawConfig.bShowPointer && pointerInDepth.X >= pDepthMD->getCropOriginX() && pointerInDepth.X < (pDepthMD->getCropOriginX() + pDepthMD->getWidth()) && pointerInDepth.Y >= pDepthMD->getCropOriginY() && pointerInDepth.Y < (pDepthMD->getCropOriginY() + pDepthMD->getHeight())) { // try to translate depth pixel to image openni::DepthPixel* pDepthPixels = (openni::DepthPixel*)pDepthMD->getData(); openni::DepthPixel pointerDepth = pDepthPixels[(pointerInDepth.Y - pDepthMD->getCropOriginY()) * pDepthMD->getWidth() + (pointerInDepth.X - pDepthMD->getCropOriginX())]; if (convertDepthPointToColor(pointerInDepth.X, pointerInDepth.Y, pointerDepth, &pointerInColor.X, &pointerInColor.Y)) { bDrawImagePointer = true; imagePointerRed = 0; imagePointerGreen = 0; imagePointerBlue = 255; } } } glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT); // Setup the opengl env for fixed location view glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(0,WIN_SIZE_X,WIN_SIZE_Y,0,-1.0,1.0); glDisable(GL_DEPTH_TEST); if (g_DrawConfig.Streams.Depth.Coloring == CYCLIC_RAINBOW_HISTOGRAM || g_DrawConfig.Streams.Depth.Coloring == LINEAR_HISTOGRAM || g_DrawConfig.bShowPointer) calculateHistogram(); drawColor(&g_DrawConfig.ColorLocation, bDrawImagePointer ? &pointerInColor : NULL, imagePointerRed, imagePointerGreen, imagePointerBlue); drawDepth(&g_DrawConfig.DepthLocation, bDrawDepthPointer ? &pointerInDepth : NULL); printRecordingInfo(); if (g_DrawConfig.bShowPointer) drawPointerMode(bOverDepth ? &pointerInDepth : NULL); drawUserInput(!bOverDepth && !bOverImage); drawUserMessage(); drawPlaybackSpeed(); if (g_DrawConfig.strErrorState[0] != '\0') drawErrorState(); if (g_DrawConfig.bHelp) drawHelpScreen(); glutSwapBuffers(); }
void drawColorImage(IntRect* pLocation, IntPair* pPointer, int pointerRed, int pointerGreen, int pointerBlue) { if (g_DrawConfig.Streams.bBackground) TextureMapDraw(&g_texBackground, pLocation); if (g_DrawConfig.Streams.Image.Coloring == IMAGE_OFF) return; if (!isImageOn() && !isIROn()) { drawClosedStream(pLocation, "Image"); return; } const MapMetaData* pImageMD; const XnUInt8* pImage = NULL; if (isImageOn()) { pImageMD = getImageMetaData(); pImage = getImageMetaData()->Data(); } else if (isIROn()) { pImageMD = getIRMetaData(); pImage = (const XnUInt8*)getIRMetaData()->Data(); } else return; if (pImageMD->FrameID() == 0) { return; } const DepthMetaData* pDepthMetaData = getDepthMetaData(); double grayscale16Factor = 1.0; if (pImageMD->PixelFormat() == XN_PIXEL_FORMAT_GRAYSCALE_16_BIT) { int nPixelsCount = pImageMD->XRes()*pImageMD->YRes(); XnUInt16* pPixel = (XnUInt16*)pImage; for (int i = 0; i < nPixelsCount; ++i,++pPixel) { if (*pPixel > g_nMaxGrayscale16Value) g_nMaxGrayscale16Value = *pPixel; } if (g_nMaxGrayscale16Value > 0) { grayscale16Factor = 255.0 / g_nMaxGrayscale16Value; } } for (XnUInt16 nY = pImageMD->YOffset(); nY < pImageMD->YRes() + pImageMD->YOffset(); nY++) { XnUInt8* pTexture = TextureMapGetLine(&g_texImage, nY) + pImageMD->XOffset()*4; if (pImageMD->PixelFormat() == XN_PIXEL_FORMAT_YUV422) { YUV422ToRGB888(pImage, pTexture, pImageMD->XRes()*2, g_texImage.Size.X*g_texImage.nBytesPerPixel); pImage += pImageMD->XRes()*2; } else { for (XnUInt16 nX = 0; nX < pImageMD->XRes(); nX++, pTexture+=4) { XnInt32 nDepthIndex = 0; if (pDepthMetaData != NULL) { XnDouble dRealX = (nX + pImageMD->XOffset()) / (XnDouble)pImageMD->FullXRes(); XnDouble dRealY = nY / (XnDouble)pImageMD->FullYRes(); XnUInt32 nDepthX = dRealX * pDepthMetaData->FullXRes() - pDepthMetaData->XOffset(); XnUInt32 nDepthY = dRealY * pDepthMetaData->FullYRes() - pDepthMetaData->YOffset(); if (nDepthX >= pDepthMetaData->XRes() || nDepthY >= pDepthMetaData->YRes()) { nDepthIndex = -1; } else { nDepthIndex = nDepthY*pDepthMetaData->XRes() + nDepthX; } } switch (pImageMD->PixelFormat()) { case XN_PIXEL_FORMAT_RGB24: pTexture[0] = pImage[0]; pTexture[1] = pImage[1]; pTexture[2] = pImage[2]; pImage+=3; break; case XN_PIXEL_FORMAT_GRAYSCALE_8_BIT: pTexture[0] = pTexture[1] = pTexture[2] = *pImage; pImage+=1; break; case XN_PIXEL_FORMAT_GRAYSCALE_16_BIT: XnUInt16* p16 = (XnUInt16*)pImage; XnUInt8 textureValue = 0; textureValue = (XnUInt8)((*p16) * grayscale16Factor); pTexture[0] = pTexture[1] = pTexture[2] = textureValue; pImage+=2; break; } // decide if pixel should be lit or not if (g_DrawConfig.Streams.Image.Coloring == DEPTH_MASKED_IMAGE && (pDepthMetaData == NULL || nDepthIndex == -1 || pDepthMetaData->Data()[nDepthIndex] == 0)) { pTexture[3] = 0; } else { pTexture[3] = 255; } } } } if (pPointer != NULL) { TextureMapDrawCursor(&g_texImage, *pPointer, pointerRed, pointerGreen, pointerBlue); } TextureMapUpdate(&g_texImage); TextureMapDraw(&g_texImage, pLocation); }
void drawFrame() { // calculate locations g_DrawConfig.DepthLocation.uBottom = 0; g_DrawConfig.DepthLocation.uTop = WIN_SIZE_Y - 1; g_DrawConfig.DepthLocation.uLeft = 0; g_DrawConfig.DepthLocation.uRight = WIN_SIZE_X - 1; g_DrawConfig.ImageLocation.uBottom = 0; g_DrawConfig.ImageLocation.uTop = WIN_SIZE_Y - 1; g_DrawConfig.ImageLocation.uLeft = 0; g_DrawConfig.ImageLocation.uRight = WIN_SIZE_X - 1; if (g_DrawConfig.Streams.ScreenArrangement == SIDE_BY_SIDE) { g_DrawConfig.DepthLocation.uTop = WIN_SIZE_Y / 2 - 1; g_DrawConfig.DepthLocation.uRight = WIN_SIZE_X / 2 - 1; g_DrawConfig.ImageLocation.uTop = WIN_SIZE_Y / 2 - 1; g_DrawConfig.ImageLocation.uLeft = WIN_SIZE_X / 2; } // Texture map init const DepthMetaData* pDepthMD = getDepthMetaData(); if (isDepthOn()) { g_nMaxDepth = getDepthGenerator()->GetDeviceMaxDepth(); TextureMapInit(&g_texDepth, pDepthMD->FullXRes(), pDepthMD->FullYRes(), 4, pDepthMD->XRes(), pDepthMD->YRes()); fixLocation(&g_DrawConfig.DepthLocation, pDepthMD->FullXRes(), pDepthMD->FullYRes()); } const MapMetaData* pImageMD = NULL; if (isImageOn()) { pImageMD = getImageMetaData(); } else if (isIROn()) { pImageMD = getIRMetaData(); } if (pImageMD != NULL) { TextureMapInit(&g_texImage, pImageMD->FullXRes(), pImageMD->FullYRes(), 4, pImageMD->XRes(), pImageMD->YRes()); fixLocation(&g_DrawConfig.ImageLocation, pImageMD->FullXRes(), pImageMD->FullYRes()); } // check if pointer is over a map bool bOverDepth = (pDepthMD != NULL) && isPointInRect(g_DrawUserInput.Cursor, &g_DrawConfig.DepthLocation); bool bOverImage = (pImageMD != NULL) && isPointInRect(g_DrawUserInput.Cursor, &g_DrawConfig.ImageLocation); bool bDrawDepthPointer = false; bool bDrawImagePointer = false; int imagePointerRed = 255; int imagePointerGreen = 0; int imagePointerBlue = 0; IntPair pointerInDepth; IntPair pointerInImage; if (bOverImage) { pointerInImage.X = (double)(g_DrawUserInput.Cursor.X - g_DrawConfig.ImageLocation.uLeft) / (g_DrawConfig.ImageLocation.uRight - g_DrawConfig.ImageLocation.uLeft + 1) * pImageMD->FullXRes(); pointerInImage.Y = (double)(g_DrawUserInput.Cursor.Y - g_DrawConfig.ImageLocation.uBottom) / (g_DrawConfig.ImageLocation.uTop - g_DrawConfig.ImageLocation.uBottom + 1) * pImageMD->FullYRes(); bDrawImagePointer = true; } if (bOverDepth) { pointerInDepth.X = (double)(g_DrawUserInput.Cursor.X - g_DrawConfig.DepthLocation.uLeft) / (g_DrawConfig.DepthLocation.uRight - g_DrawConfig.DepthLocation.uLeft + 1) * pDepthMD->FullXRes(); pointerInDepth.Y = (double)(g_DrawUserInput.Cursor.Y - g_DrawConfig.DepthLocation.uBottom) / (g_DrawConfig.DepthLocation.uTop - g_DrawConfig.DepthLocation.uBottom + 1) * pDepthMD->FullYRes(); // make sure we're in cropped area if (pointerInDepth.X >= pDepthMD->XOffset() && pointerInDepth.X < (pDepthMD->XOffset() + pDepthMD->XRes()) && pointerInDepth.Y >= pDepthMD->YOffset() && pointerInDepth.Y < (pDepthMD->YOffset() + pDepthMD->YRes())) { bDrawDepthPointer = true; if (!bOverImage && g_DrawConfig.bShowPointer) { // try to translate depth pixel to image if (getImageCoordinatesForDepthPixel(pointerInDepth.X, pointerInDepth.Y, pointerInImage.X, pointerInImage.Y)) { bDrawImagePointer = true; imagePointerRed = 0; imagePointerGreen = 0; imagePointerBlue = 255; } } } } glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT); // Setup the opengl env for fixed location view glMatrixMode(GL_PROJECTION); glPushMatrix(); glLoadIdentity(); glOrtho(0,WIN_SIZE_X,WIN_SIZE_Y,0,-1.0,1.0); glDisable(GL_DEPTH_TEST); if (g_DrawConfig.Streams.Depth.Coloring == CYCLIC_RAINBOW_HISTOGRAM || g_DrawConfig.Streams.Depth.Coloring == LINEAR_HISTOGRAM || g_DrawConfig.bShowPointer) calculateHistogram(); drawColorImage(&g_DrawConfig.ImageLocation, bDrawImagePointer ? &pointerInImage : NULL, imagePointerRed, imagePointerGreen, imagePointerBlue); drawDepth(&g_DrawConfig.DepthLocation, bDrawDepthPointer ? &pointerInDepth : NULL); printStatisticsInfo(); printRecordingInfo(); if (g_DrawConfig.bShowPointer) drawPointerMode(bDrawDepthPointer ? &pointerInDepth : NULL); drawUserInput(!bOverDepth && !bOverImage); drawUserMessage(); drawPlaybackSpeed(); if (g_DrawConfig.strErrorState != NULL) drawErrorState(); if (g_DrawConfig.bHelp) drawHelpScreen(); glutSwapBuffers(); }