环境

  • OSX优胜美地
  • xcode 6.4
  • C++

  • 用例
    给定一个由单个关键帧和多个对应的增量帧组成的h264 GOP,对GOP进行解码,然后对单个 4.2Mbit 关键帧进行编码
    问题描述
    我能够解码GOP并对关键帧进行编码,但是,生成的关键帧的质量较低(低比特率),也就是说,尽管我专门将比特率设置为4.2Mbit(这可以可以在下面的代码中看到),记住我只需要一个单个关键帧,有什么方法可以设置VideoToolBox编码器以输出高比特率关键帧?
    const CMVideoCodecType  fourcc  = (CMVideoCodecType)CMVideoFormatDescriptionGetCodecType(fmt);
    
    // Else, generate a h264 KeyFrame
    
    CFObjectSmartPtr< CFMutableDictionaryRef >  dictEncSpec;
    dictEncSpec.Attach(CFDictionaryCreateMutable(NULL, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks));
    //dictEncSpec.Attach(CFDictionaryCreateMutable(NULL, 0, 0, 0));
    // CFDictionarySetNumVal(dictEncSpec, kVTVideoEncoderSpecification_RequireHardwareAcceleratedVideoEncoder, TRUE);
    CFDictionarySetValue(dictEncSpec, kVTCompressionPropertyKey_ProfileLevel, kVTProfileLevel_H264_High_3_2);
    // CFDictionarySetValue(dictEncSpec, kVTCompressionPropertyKey_RealTime, kCFBooleanTrue);
    
    // CFDictionarySetValue(dictEncSpec, kVTCompressionPropertyKey_H264EntropyMode, kVTH264EntropyMode_CABAC);
    
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_AverageBitRate, 4200000);
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_Quality, 1.0f);
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_MaxFrameDelayCount, 0);
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_MaxKeyFrameIntervalDuration, 1);
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_ExpectedDuration, 1);
    CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_ExpectedFrameRate, 10);
    // CFDictionarySetNumVal(dictEncSpec, kVTCompressionPropertyKey_SourceFrameCount, 1);
    CFDictionarySetNumVal(dictEncSpec, kVTVideoEncoderSpecification_EnableHardwareAcceleratedVideoEncoder, TRUE);
    
    CFObjectSmartPtr< VTCompressionSessionRef > sessionCompression;
    status = VTCompressionSessionCreate(0, res.width, res.height, fourcc, (CFDictionaryRef)dictEncSpec, 0, 0, CompressionCallback, &ctx, &sessionCompression);
    if (noErr != status)
        return HRESULT_FROM_ERRNO(status);
    if (noErr != (status = VTCompressionSessionEncodeFrame(sessionCompression, ctx.yuvFrame, timestamp, timestamp, 0, 0, 0)))
        return HRESULT_FROM_ERRNO(status);
    if(noErr != (status = VTCompressionSessionCompleteFrames(sessionCompression, timestamp)))
        return HRESULT_FROM_ERRNO(status);
    if (0 == ctx.keyFrame) {
        assert(false);
        return E_UNEXPECTED;
    }
    
    ctx.keyFrame 最终质量很低

    最佳答案

    创建VTCompressionSession之后,还需要考虑另一个因素,您需要在VTCompressionSessionEncodeFrame中正确设置帧时间戳。

    关于c++ - OSX,VideoToolbox,压缩 session ,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/31567639/

    10-11 18:09