IOS硬解码流程笔记

IOS硬解码:

流程步骤:

1初始化:CMVideoFormatDescriptionCreateFromH264ParameterSets

注意SPSPPS不要携带冗余,携带冗余可能导致无法某些手机无法正常解码

  size_t  ParameterSetSizes[2]    = {(size_t)FrameInfo->nSpsLen,

                                                (size_t)FrameInfo->nPpsLen};

        

  const uint8_t* const ParameterSetPointers[2] = {( uint8_t*)FrameInfo->pSpsStart,

                                                ( uint8_t*)FrameInfo->pPpsStart};

               

  CMVideoFormatDescriptionCreateFromH264ParameterSets(NULL,

                                                             2,

                                                        ParameterSetPointers,

                                                        ParameterSetSizes,

                                                           4,

                                                         &FormatDesc);

 

size_t ParameterSetSizes[3] = {(size_t)FrameInfo->nVpsLen,

                                              (size_t)FrameInfo->nSpsLen,

                                              (size_t)FrameInfo->nPpsLen};

        

 uint8_t* const nParameterSetPointers[3] = {(const uint8_t*)FrameInfo->pVpsStart,

                                      (const uint8_t*)FrameInfo->pSpsStart,

                                      (const uint8_t*)FrameInfo->pPpsStart};

        

#ifdef __IPHONE_11_0

        if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 11.0)

        {

            nStatus = CMVideoFormatDescriptionCreateFromHEVCParameterSets(NULL,

                                                                          3,

                                                                  ParameterSetPointers,

                                                                  ParameterSetSizes,

                                                                          4,

                                                                          NULL,

                                                                          &FormatDesc);

        }

#endif

设置pixelbuffer属性

CFMutableDictionaryRef  PixelBufferAttributes =

CFDictionaryCreateMutable(NULL,0,&kCFTypeDictionaryKeyCallBacks,&kCFTypeDictionaryValueCallBacks);

3设置解码参数:这里设置的宽高可以让硬解码按照你设置的分辨率解码。

 SInt32 nPixelType = kCVPixelFormatType_420YpCbCr8BiPlanarFullRange;

    CFDictionarySetValue(PixelBufferAttributes,

                         kCVPixelBufferPixelFormatTypeKey,

                         CFNumberCreate(NULL, kCFNumberSInt32Type, &PixelType));

    CFDictionarySetValue(PixelBufferAttributes,

                         kCVPixelBufferWidthKey,

                         CFNumberCreate(NULL, kCFNumberSInt32Type, &Width));

    CFDictionarySetValue(PixelBufferAttributes,

                         kCVPixelBufferHeightKey,

                         CFNumberCreate(NULL, kCFNumberSInt32Type, &Height));

 CFMutableDictionaryRef pDecoderParameters = CFDictionaryCreateMutable(NULL,

                                                                          0,                                                                    &kCFTypeDictionaryKeyCallBacks,

&kCFTypeDictionaryValueCallBacks);

 

 

4设置解码回调(异步的时候需要设置,同步的时候不需要设置)

const VTDecompressionOutputCallbackRecord stCallBack = {HWDecompressionOutputCallback, this};

    nStatus = VTDecompressionSessionCreate(NULL,

                                           FormatDesc,

                                           NULL,

                                           PixelBufferAttributes,

                                           &stCallBack,

                                           &DecSession);

5 初始化结束后进行属性的释放

CFRelease(PixelBufferAttributes);

CFRelease(DecParameters);

输入的解码数据转换成CMBlockBufferRef

 CMBlockBufferCreateWithMemoryBlock(NULL,

                                                           Data,

                                                           Len,

                                                           kCFAllocatorNull,

                                                           NULL,

                                                           0,

                                                           Len,

                                                           0,

                                                           &BlockBufferRefobj);

7 blockbuf转成CMSampleBufferRef

CMSampleBufferCreate(NULL,

                                   BlockBufferRefobj,

                                   true,

                                   0,

                                   0,

                                   FormatDesc,

                                   1,

                                   0,

                                   NULL,

                                   0,

                                   NULL,

                                   &SampleBufferRef);

8 硬解码;之后释放samplebufref 和 blockbufferref

VTDecompressionSessionDecodeFrame(DecSession,

                                                SampleBufferRef,

                                                0,

                                                pDecodeInfo,

                                                0);

回调函数中拿YUV

CVPixelBufferLockBaseAddress(pixbuf, kCVPixelBufferLock_ReadOnly) 

YUV处理

CVPixelBufferUnlockBaseAddress(pixbuf, kCVPixelBufferLock_ReadOnly);

posted on   邗影  阅读(177)  评论(0编辑  收藏  举报

相关博文:
阅读排行:
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· 单线程的Redis速度为什么快?
· 展开说说关于C#中ORM框架的用法!
· Pantheons:用 TypeScript 打造主流大模型对话的一站式集成库
< 2025年3月 >
23 24 25 26 27 28 1
2 3 4 5 6 7 8
9 10 11 12 13 14 15
16 17 18 19 20 21 22
23 24 25 26 27 28 29
30 31 1 2 3 4 5

导航

统计

点击右上角即可分享
微信分享提示