Refactor and add new support in LibAvHandler
Refactor list of pixel formats Add support for custom pixel formats by converting it to YUV444p
This commit is contained in:
6 files changed
+170
-100
No files matched your search
@@ -51,7 +51,7 @@ std::vector<String> PlaYUVerFrame::supportedPixelFormatListNames()
|
||||
std::vector<String> formatsList;
|
||||
for( Int i = 0; i < NUMBER_PEL_FORMATS; i++ )
|
||||
{
|
||||
formatsList.push_back( g_PlaYUVerPixFmtDescriptorsList[i].name );
|
||||
formatsList.push_back( g_PlaYUVerPixFmtDescriptorsMap.at( i ).name );
|
||||
}
|
||||
return formatsList;
|
||||
}
|
||||
@@ -61,8 +61,8 @@ std::vector<String> PlaYUVerFrame::supportedPixelFormatListNames( Int colorSpace
|
||||
std::vector<String> formatsList;
|
||||
for( Int i = 0; i < NUMBER_PEL_FORMATS; i++ )
|
||||
{
|
||||
if( g_PlaYUVerPixFmtDescriptorsList[i].colorSpace == colorSpace )
|
||||
formatsList.push_back( g_PlaYUVerPixFmtDescriptorsList[i].name );
|
||||
if( g_PlaYUVerPixFmtDescriptorsMap.at( i ).colorSpace == colorSpace )
|
||||
formatsList.push_back( g_PlaYUVerPixFmtDescriptorsMap.at( i ).name );
|
||||
}
|
||||
return formatsList;
|
||||
}
|
||||
@@ -71,7 +71,7 @@ Int PlaYUVerFrame::findPixelFormat( const String& name )
|
||||
{
|
||||
for( Int i = 0; i < NUMBER_PEL_FORMATS; i++ )
|
||||
{
|
||||
if( g_PlaYUVerPixFmtDescriptorsList[i].name == name )
|
||||
if( g_PlaYUVerPixFmtDescriptorsMap.at( i ).name == name )
|
||||
return i;
|
||||
}
|
||||
return -1;
|
||||
@@ -180,7 +180,7 @@ struct PlaYUVerFramePrivate
|
||||
throw PlaYUVerFailure( "PlaYUVerFrame", "Cannot create a PlYUVerFrame of this type" );
|
||||
}
|
||||
|
||||
m_pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsList[pel_format] );
|
||||
m_pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsMap.at( pel_format ) );
|
||||
|
||||
m_bHasRGBPel = false;
|
||||
if( m_pcPelFormat->colorSpace == PlaYUVerPixel::COLOR_GRAY )
|
||||
@@ -259,7 +259,7 @@ PlaYUVerFrame::PlaYUVerFrame( const PlaYUVerFrame* other )
|
||||
PlaYUVerFrame::PlaYUVerFrame( const PlaYUVerFrame& other, UInt x, UInt y, UInt width, UInt height )
|
||||
: d( new PlaYUVerFramePrivate )
|
||||
{
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsList[other.getPelFormat()] );
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsMap.at( other.getPelFormat() ) );
|
||||
if( pcPelFormat->log2ChromaWidth )
|
||||
{
|
||||
if( x % ( 1 << pcPelFormat->log2ChromaWidth ) )
|
||||
@@ -287,7 +287,7 @@ PlaYUVerFrame::PlaYUVerFrame( const PlaYUVerFrame* other, UInt posX, UInt posY,
|
||||
if( !other )
|
||||
return;
|
||||
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsList[other->getPelFormat()] );
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsMap.at( other->getPelFormat() ) );
|
||||
if( pcPelFormat->log2ChromaWidth )
|
||||
{
|
||||
if( posX % ( 1 << pcPelFormat->log2ChromaWidth ) )
|
||||
@@ -415,7 +415,7 @@ UInt64 PlaYUVerFrame::getBytesPerFrame()
|
||||
|
||||
UInt64 PlaYUVerFrame::getBytesPerFrame( UInt uiWidth, UInt uiHeight, Int iPixelFormat, UInt bitsPixel )
|
||||
{
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsList[iPixelFormat] );
|
||||
const PlaYUVerPixFmtDescriptor* pcPelFormat = &( g_PlaYUVerPixFmtDescriptorsMap.at( iPixelFormat ) );
|
||||
UInt bytesPerPixel = ( bitsPixel - 1 ) / 8 + 1;
|
||||
UInt64 numberBytes = uiWidth * uiHeight;
|
||||
if( pcPelFormat->numberChannels > 1 )
|
||||
|
||||
+1
-1
@@ -53,8 +53,8 @@ public:
|
||||
{
|
||||
NO_FMT = -1,
|
||||
YUV420p = 0,
|
||||
YUV444p,
|
||||
YUV422p,
|
||||
YUV444p,
|
||||
YUYV422,
|
||||
GRAY,
|
||||
RGBp,
|
||||
|
||||
@@ -198,113 +198,137 @@ Void fillARGB32bufferYUV420p( Pel*** in, UChar* out, UInt width, UInt height, UI
|
||||
}
|
||||
#endif
|
||||
|
||||
const PlaYUVerPixFmtDescriptor g_PlaYUVerPixFmtDescriptorsList[PlaYUVerFrame::NUMBER_PEL_FORMATS] = {
|
||||
const std::map<int, PlaYUVerPixFmtDescriptor> g_PlaYUVerPixFmtDescriptorsMap = {
|
||||
{
|
||||
"YUV420p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
1,
|
||||
1,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV420P ),
|
||||
PlaYUVerFrame::YUV420p,
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
"YUV420p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
1,
|
||||
1,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV420P ),
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"YUV422p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV422P ),
|
||||
PlaYUVerFrame::YUV422p,
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
"YUV422p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV422P ),
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"YUV444p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV444P ),
|
||||
PlaYUVerFrame::YUV444p,
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
"YUV444p",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
3,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUV444P ),
|
||||
{
|
||||
{0, 0, 1}, /* Y */
|
||||
{1, 0, 1}, /* U */
|
||||
{2, 0, 1}, /* V */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"YUYV422",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
1,
|
||||
1,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUYV422 ),
|
||||
PlaYUVerFrame::YUYV422,
|
||||
{
|
||||
{0, 1, 1}, /* Y */
|
||||
{0, 3, 2}, /* U */
|
||||
{0, 3, 4}, /* V */
|
||||
"YUYV422",
|
||||
PlaYUVerPixel::COLOR_YUV,
|
||||
3,
|
||||
1,
|
||||
1,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_YUYV422 ),
|
||||
{
|
||||
{0, 1, 1}, /* Y */
|
||||
{0, 3, 2}, /* U */
|
||||
{0, 3, 4}, /* V */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"GRAY",
|
||||
PlaYUVerPixel::COLOR_GRAY,
|
||||
1,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_GRAY8 ),
|
||||
{{0, 0, 1}}, /* Y */
|
||||
},
|
||||
{
|
||||
"RGBp",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
3,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_NONE ),
|
||||
PlaYUVerFrame::GRAY,
|
||||
{
|
||||
{0, 0, 1}, /* R */
|
||||
{1, 0, 1}, /* G */
|
||||
{2, 0, 1}, /* B */
|
||||
"GRAY",
|
||||
PlaYUVerPixel::COLOR_GRAY,
|
||||
1,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_GRAY8 ),
|
||||
{{0, 0, 1}}, /* Y */
|
||||
},
|
||||
},
|
||||
{
|
||||
"RGB",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_RGB24 ),
|
||||
PlaYUVerFrame::RGBp,
|
||||
{
|
||||
{0, 2, 1}, /* R */
|
||||
{0, 2, 2}, /* G */
|
||||
{0, 2, 3}, /* B */
|
||||
"RGBp",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
3,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_NONE ),
|
||||
{
|
||||
{0, 0, 1}, /* R */
|
||||
{1, 0, 1}, /* G */
|
||||
{2, 0, 1}, /* B */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"BGR",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_BGR24 ),
|
||||
PlaYUVerFrame::RGB24,
|
||||
{
|
||||
{0, 2, 3}, /* B */
|
||||
{0, 2, 1}, /* R */
|
||||
{0, 2, 2}, /* G */
|
||||
"RGB",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_RGB24 ),
|
||||
{
|
||||
{0, 2, 1}, /* R */
|
||||
{0, 2, 2}, /* G */
|
||||
{0, 2, 3}, /* B */
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
PlaYUVerFrame::BGR24,
|
||||
{
|
||||
"BGR",
|
||||
PlaYUVerPixel::COLOR_RGB,
|
||||
3,
|
||||
1,
|
||||
0,
|
||||
0,
|
||||
ADD_FFMPEG_PEL_FMT( AV_PIX_FMT_BGR24 ),
|
||||
{
|
||||
{0, 2, 3}, /* R */
|
||||
{0, 2, 2}, /* G */
|
||||
{0, 2, 1}, /* B */
|
||||
},
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -29,6 +29,8 @@
|
||||
#include "PlaYUVerFrame.h"
|
||||
#include "PlaYUVerPixel.h"
|
||||
|
||||
#include <map>
|
||||
|
||||
#define CHROMA_RESAMPLING( X ) ( ( ( X + 1 ) >> 1 ) << 1 )
|
||||
|
||||
#define CHROMARATIO( SIZE, RATIO ) ( RATIO > 1 ? ( ( SIZE + 1 ) / RATIO ) : SIZE )
|
||||
@@ -109,6 +111,6 @@ typedef struct PlaYUVerPixFmtDescriptor
|
||||
|
||||
#define MAX_NUMBER_PLANES 3
|
||||
|
||||
extern const PlaYUVerPixFmtDescriptor g_PlaYUVerPixFmtDescriptorsList[];
|
||||
extern const std::map<int, PlaYUVerPixFmtDescriptor> g_PlaYUVerPixFmtDescriptorsMap;
|
||||
|
||||
#endif // __PLAYUVERFRAMEPIXELFORMATS_H__
|
||||
@@ -164,8 +164,6 @@ Bool StreamHandlerLibav::openHandler( String strFilename, Bool bInput )
|
||||
m_uiHeight = m_cStream->codec->height;
|
||||
|
||||
#endif
|
||||
m_uiFrameBufferSize = av_image_get_buffer_size( AVPixelFormat( m_ffPixFmt ), m_uiWidth, m_uiHeight, 1 );
|
||||
|
||||
m_strFormatName = uppercase( strFilename.substr( strFilename.find_last_of( "." ) + 1 ) );
|
||||
const char* name = avcodec_get_name( m_cCodedCtx->codec_id );
|
||||
m_strCodecName = name;
|
||||
@@ -174,8 +172,9 @@ Bool StreamHandlerLibav::openHandler( String strFilename, Bool bInput )
|
||||
m_uiBitsPerPixel = 8;
|
||||
|
||||
/**
|
||||
* Auxiliar conversation to re-use similar pixfmt
|
||||
*/
|
||||
* Auxiliar conversation to re-use similar pixfmt
|
||||
*/
|
||||
m_bRequiresConvertion = false;
|
||||
Int auxPixFmt = m_ffPixFmt;
|
||||
switch( m_ffPixFmt )
|
||||
{
|
||||
@@ -202,7 +201,7 @@ Bool StreamHandlerLibav::openHandler( String strFilename, Bool bInput )
|
||||
m_iPixelFormat = PlaYUVerFrame::NO_FMT;
|
||||
for( Int i = 0; i < PlaYUVerFrame::NUMBER_PEL_FORMATS; i++ )
|
||||
{
|
||||
if( g_PlaYUVerPixFmtDescriptorsList[i].ffmpegPelFormat == auxPixFmt )
|
||||
if( g_PlaYUVerPixFmtDescriptorsMap.at( i ).ffmpegPelFormat == auxPixFmt )
|
||||
{
|
||||
m_iPixelFormat = i;
|
||||
break;
|
||||
@@ -210,8 +209,11 @@ Bool StreamHandlerLibav::openHandler( String strFilename, Bool bInput )
|
||||
}
|
||||
if( m_iPixelFormat == PlaYUVerFrame::NO_FMT )
|
||||
{
|
||||
throw PlaYUVerFailure( "Cannot open file using FFmpeg libs - unsupported pixel format" );
|
||||
return false;
|
||||
Int newPelFmt = PlaYUVerFrame::findPixelFormat( "YUV444p" );
|
||||
m_iPixelFormat = newPelFmt;
|
||||
m_bRequiresConvertion = true;
|
||||
//throw PlaYUVerFailure( "StreamHandlerLibav", "Cannot open file using FFmpeg libs - unsupported pixel format" );
|
||||
//return false;
|
||||
}
|
||||
|
||||
Double fr = 30;
|
||||
@@ -248,6 +250,34 @@ Bool StreamHandlerLibav::openHandler( String strFilename, Bool bInput )
|
||||
return false;
|
||||
}
|
||||
|
||||
if( m_bRequiresConvertion )
|
||||
{
|
||||
AVPixelFormat newAvFmt = AVPixelFormat( g_PlaYUVerPixFmtDescriptorsMap.at( m_iPixelFormat ).ffmpegPelFormat );
|
||||
|
||||
/* create scaling context */
|
||||
m_ScalerCtx = sws_getContext( m_uiWidth, m_uiHeight, AVPixelFormat( m_ffPixFmt ),
|
||||
m_uiWidth, m_uiHeight, newAvFmt,
|
||||
SWS_BILINEAR, NULL, NULL, NULL );
|
||||
|
||||
m_cConvertedFrame = av_frame_alloc();
|
||||
if( !m_cConvertedFrame )
|
||||
{
|
||||
closeHandler();
|
||||
return false;
|
||||
}
|
||||
|
||||
if( av_image_alloc( m_cConvertedFrame->data, m_cConvertedFrame->linesize,
|
||||
m_uiWidth, m_uiHeight, newAvFmt, 1 ) < 0 )
|
||||
{
|
||||
closeHandler();
|
||||
return false;
|
||||
}
|
||||
|
||||
m_ffPixFmt = newAvFmt;
|
||||
}
|
||||
|
||||
m_uiFrameBufferSize = av_image_get_buffer_size( AVPixelFormat( m_ffPixFmt ), m_uiWidth, m_uiHeight, 1 );
|
||||
|
||||
/* initialize packet, set data to NULL, let the demuxer fill it */
|
||||
av_init_packet( &m_cPacket );
|
||||
m_cPacket.data = NULL;
|
||||
@@ -357,8 +387,16 @@ Bool StreamHandlerLibav::read( PlaYUVerFrame* pcFrame )
|
||||
|
||||
if( bGotFrame )
|
||||
{
|
||||
av_image_copy_to_buffer( m_pStreamBuffer, m_uiFrameBufferSize, m_cFrame->data, m_cFrame->linesize,
|
||||
AVPixelFormat( m_ffPixFmt ), m_uiWidth, m_uiHeight, 1 );
|
||||
AVFrame* decFrame = m_cFrame;
|
||||
if( m_bRequiresConvertion )
|
||||
{
|
||||
sws_scale( m_ScalerCtx, (const uint8_t* const*)decFrame->data, decFrame->linesize, 0,
|
||||
decFrame->height, (uint8_t* const*)m_cConvertedFrame->data, m_cConvertedFrame->linesize );
|
||||
|
||||
decFrame = m_cConvertedFrame;
|
||||
}
|
||||
av_image_copy_to_buffer( m_pStreamBuffer, m_uiFrameBufferSize, decFrame->data,
|
||||
decFrame->linesize, AVPixelFormat( m_ffPixFmt ), m_uiWidth, m_uiHeight, 1 );
|
||||
|
||||
pcFrame->frameFromBuffer( m_pStreamBuffer, m_iEndianness );
|
||||
m_uiCurrFrameFileIdx++;
|
||||
|
||||
@@ -42,6 +42,7 @@ extern "C" {
|
||||
#include <libavutil/avutil.h>
|
||||
#include <libavutil/imgutils.h>
|
||||
#include <libavutil/samplefmt.h>
|
||||
#include <libswscale/swscale.h>
|
||||
}
|
||||
|
||||
#include "PlaYUVerDefs.h"
|
||||
@@ -78,6 +79,8 @@ private:
|
||||
AVStream* m_cStream;
|
||||
Int m_iStreamIdx;
|
||||
|
||||
struct SwsContext* m_ScalerCtx;
|
||||
|
||||
AVCodecContext* m_cCodedCtx;
|
||||
|
||||
Int m_ffPixFmt;
|
||||
@@ -89,6 +92,9 @@ private:
|
||||
|
||||
UInt64 m_uiSecs;
|
||||
UInt64 m_uiMicroSec;
|
||||
|
||||
Bool m_bRequiresConvertion;
|
||||
AVFrame* m_cConvertedFrame;
|
||||
};
|
||||
|
||||
#endif // __STREAMHANDLERLIBAV_H__
|
||||
Reference in new issue
Block a user