From 68faafc9ed15bbc6471cfe8ae017dc2b5ef4dd79 Mon Sep 17 00:00:00 2001 From: Joao Carreira Date: Fri, 12 Apr 2019 03:35:42 +0100 Subject: [PATCH] Improve conversion to OpenCv Mat with more than 8 bits --- lib/CalypFrame.cpp | 24 +++++++++++++----------- lib/CalypFrame.h | 2 +- lib/StreamHandlerOpenCV.cpp | 30 +++++++++++++++++------------- 3 files changed, 31 insertions(+), 25 deletions(-) diff --git a/lib/CalypFrame.cpp b/lib/CalypFrame.cpp index 8002c49..7473b9a 100644 --- a/lib/CalypFrame.cpp +++ b/lib/CalypFrame.cpp @@ -33,6 +33,7 @@ #ifdef USE_OPENCV #include +#include #include #endif @@ -1096,7 +1097,7 @@ double CalypFrame::getHistogramValue( int channel, unsigned int bin ) ************************************************************** */ -bool CalypFrame::toMat( cv::Mat& cvMat, bool convertToGray, unsigned channel ) +bool CalypFrame::toMat( cv::Mat& cvMat, bool convertToGray, bool scale, unsigned channel ) { bool bRet = false; #ifdef USE_OPENCV @@ -1108,6 +1109,7 @@ bool CalypFrame::toMat( cv::Mat& cvMat, bool convertToGray, unsigned channel ) unsigned int cvPrecision = getBitsPel() > 8 ? CV_16U : CV_8U; unsigned numBytes = getBitsPel() > 8 ? 2 : 1; unsigned numChannels = getNumberChannels(); + unsigned scaleFactor = 1 << ( numBytes * 8 - getBitsPel() ); if( convertToGray ) { @@ -1126,18 +1128,18 @@ bool CalypFrame::toMat( cv::Mat& cvMat, bool convertToGray, unsigned channel ) unsigned char* cv_data = tmpMat.data; unsigned int cv_step = tmpMat.step; CalypPixel currPel; - for( unsigned int y = 0; y < imgHeight; y++ ) + for( unsigned y = 0; y < imgHeight; y++ ) { - for( unsigned int x = 0; x < imgWidth; x++ ) + for( unsigned x = 0; x < imgWidth; x++ ) { - currPel = getPixel( x, y ); + currPel = getPixel( x, y ) * scaleFactor; for( unsigned int ch = 0; ch < numChannels; ch++ ) - { for( unsigned b = 0; b < numBytes; b++ ) { - *( cv_data + y * cv_step + x * numChannels * numBytes + ch + b ) = currPel[ch] >> ( 8 * b ); + unsigned char pel = currPel[ch] >> ( 8 * b ); + //*( cv_data + y * cv_step + x * numChannels * numBytes + ch * numBytes + b ) = currPel[ch] >> ( 8 * b ); + *cv_data++ = pel; } - } } } if( getNumberChannels() >= 1 ) @@ -1155,11 +1157,11 @@ bool CalypFrame::toMat( cv::Mat& cvMat, bool convertToGray, unsigned channel ) { unsigned char* cv_data = cvMat.data; ClpPel* pel = getPelBufferYUV()[channel][0]; - for( unsigned int y = 0; y < imgHeight * imgWidth; y++ ) + for( unsigned y = 0; y < imgHeight * imgWidth; y++ ) { + ClpPel currPel = ( *pel++ ) * scaleFactor; for( unsigned b = 0; b < numBytes; b++ ) - *cv_data++ = ( *pel ) >> ( 8 * b ); - pel++; + *cv_data++ = currPel >> ( 8 * b ); } } bRet = true; @@ -1436,7 +1438,7 @@ double CalypFrame::getWSPNR( CalypFrame* Org, unsigned int component ) { int diff = int( *pPelYUV++ ) - int( *pOrgPelYUV++ ); double weight = cos( double( ( y + 0.5 - height / 2.0 ) * S_PI / height ) ); - ssd += (double)( diff * diff * 1000) * weight; + ssd += (double)( diff * diff * 1000 ) * weight; weight_sum += weight * 1000; } diff --git a/lib/CalypFrame.h b/lib/CalypFrame.h index ae3657f..e7b4670 100644 --- a/lib/CalypFrame.h +++ b/lib/CalypFrame.h @@ -347,7 +347,7 @@ public: /** * interface with OpenCV lib */ - bool toMat( cv::Mat& cvMat, bool convertToGray = false, unsigned channel = 0 ); + bool toMat( cv::Mat& cvMat, bool convertToGray = false, bool scale = true, unsigned channel = 0 ); bool fromMat( cv::Mat& cvMat, int iChannel = -1 ); /** diff --git a/lib/StreamHandlerOpenCV.cpp b/lib/StreamHandlerOpenCV.cpp index d4ff87b..9a8bf69 100644 --- a/lib/StreamHandlerOpenCV.cpp +++ b/lib/StreamHandlerOpenCV.cpp @@ -40,7 +40,8 @@ std::vector StreamHandlerOpenCV::supportedReadFormats() { INI_REGIST_CALYP_SUPPORTED_FMT; #if( CV_MAJOR_VERSION >= 3 ) - REGIST_CALYP_SUPPORTED_ABSTRACT_FMT( &StreamHandlerOpenCV::Create, "Device", "/dev/video*" ); + REGIST_CALYP_SUPPORTED_ABSTRACT_FMT( &StreamHandlerOpenCV::Create, "Device", + "/dev/video*" ); #endif END_REGIST_CALYP_SUPPORTED_FMT; } @@ -48,9 +49,12 @@ std::vector StreamHandlerOpenCV::supportedReadFormats() std::vector StreamHandlerOpenCV::supportedWriteFormats() { INI_REGIST_CALYP_SUPPORTED_FMT; - REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, "Portable Network Graphics", "png" ); - REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, "Joint Photographic Experts Group", "jpg" ); - REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, "Windows Bitmap", "bmp" ); + REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, + "Portable Network Graphics", "png" ); + REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, + "Joint Photographic Experts Group", "jpg" ); + REGIST_CALYP_SUPPORTED_FMT( &StreamHandlerOpenCV::Create, "Windows Bitmap", + "bmp" ); END_REGIST_CALYP_SUPPORTED_FMT; } @@ -80,19 +84,20 @@ bool StreamHandlerOpenCV::openHandler( ClpString strFilename, bool bInput ) m_strFormatName = "DEV"; m_strCodecName = "Raw Video"; pcVideoCapture = new VideoCapture( iDeviceId ); - #if CV_MAJOR_VERSION >= 4 +#if CV_MAJOR_VERSION >= 4 m_uiWidth = pcVideoCapture->get( cv::CAP_PROP_FRAME_WIDTH ); m_uiHeight = pcVideoCapture->get( cv::CAP_PROP_FRAME_HEIGHT ); - #else +#else m_uiWidth = pcVideoCapture->get( CV_CAP_PROP_FRAME_WIDTH ); m_uiHeight = pcVideoCapture->get( CV_CAP_PROP_FRAME_HEIGHT ); - #endif +#endif m_dFrameRate = 25; } else #endif { - m_strCodecName = m_strFormatName = clpUppercase( strFilename.substr( strFilename.find_last_of( "." ) + 1 ) ); + m_strCodecName = m_strFormatName = + clpUppercase( strFilename.substr( strFilename.find_last_of( "." ) + 1 ) ); Mat cvMat = cv::imread( m_cFilename ); m_uiWidth = cvMat.cols; m_uiHeight = cvMat.rows; @@ -156,10 +161,9 @@ bool StreamHandlerOpenCV::write( CalypFrame* pcFrame ) { bool bRet = false; Mat cvFrame; - bRet = pcFrame->toMat( cvFrame ); - if( bRet ) - { - bRet = cv::imwrite( m_cFilename, cvFrame ); - } + bRet = pcFrame->toMat( cvFrame, false, true ); + if( !bRet ) + return bRet; + bRet = cv::imwrite( m_cFilename, cvFrame ); return bRet; }