AVAssetWriterinputH.264直通到QuickTime(.mov) – 传入SPS / PPS来创buildavcCprimefaces?
我有一个由types1(P帧),5(I帧),7(SPS)和8(PPS)组成的H.264 / AVC NALstream。 我想把它们写入一个.mov文件而不用重新编码。 我试图使用AVAssetWriter
来做到这一点。 AVAssetWriterInput
的文档状态:
对outputSettings传递nil指示input通过附加采样,在写入输出文件之前不做任何处理。 例如,如果您正在追加已经处于所需压缩格式的缓冲区,这非常有用。 但是,只有在写入QuickTime影片文件(即AVAssetWriter用AVFileTypeQuickTimeMovie初始化)时才支持直通。 对于其他文件types,您必须指定非零输出设置。
我试图从这些NAL中创buildCMSampleBuffers并将它们附加到资产编写器input,但是我无法以产生格式正确的.mov文件的方式input数据,而且我无法在任何地方find任何线索如何做到这一点。
到目前为止,最好的结果是以附件B字节stream格式(以7 8 5 1 1 1 ….重复的顺序)传递NAL,并在VLC中播放结果。 因此,我知道NAL包含有效的数据,但由于.mov文件没有avcCprimefaces,mdatprimefaces填充了附件B字节stream,所以QuickTime不会播放video。
现在,我试图传入4个字节(由lengthSizeMinusOne
字段指定)长度字段而不是附件B分隔符的lengthSizeMinusOne
,这就是应该如何将它们打包到mdatprimefaces中,直到我知道。
我不知道如何让资产编写者写一个avcCprimefaces。 我追加的每个样本都被推入mdatprimefaces。
有谁知道我可以传递原始的H.264数据到AVAssetWriterInputconfiguration为通过(nil outputSettings)并让它生成一个正确形成的QuickTime文件?
我已经提交了苹果TSI,find了答案。 我希望这能节省一些时间。
CMSampleBuffers与它们关联了一个CMFormatDescription,它包含了样本缓冲区中数据的描述。
用于创build格式描述的函数原型如下所示:
OSStatus CMVideoFormatDescriptionCreate ( CFAllocatorRef allocator, CMVideoCodecType codecType, int32_t width, int32_t height, CFDictionaryRef extensions, CMVideoFormatDescriptionRef *outDesc );
我从苹果技术人员那里了解到,我可以使用扩展parameter passing包含avcCprimefaces数据的字典。
扩展词典应该是以下forms:
[kCMFormatDescriptionExtension_SampleDescriptionExtensionAtoms ---> ["avcC" ---> <avcC Data>]]
[]代表词典。 除了avcC之外,该字典还可能用于传递任意primefaces的数据。
这里是我用来创buildextensions
字典,我传入CMVideoFormatDescriptionCreate
:
const char *avcC = "avcC"; const CFStringRef avcCKey = CFStringCreateWithCString(kCFAllocatorDefault, avcC, kCFStringEncodingUTF8); const CFDataRef avcCValue = CFDataCreate(kCFAllocatorDefault, [_avccData bytes], [_avccData length]); const void *atomDictKeys[] = { avcCKey }; const void *atomDictValues[] = { avcCValue }; CFDictionaryRef atomsDict = CFDictionaryCreate(kCFAllocatorDefault, atomDictKeys, atomDictValues, 1, nil, nil); const void *extensionDictKeys[] = { kCMFormatDescriptionExtension_SampleDescriptionExtensionAtoms }; const void *extensionDictValues[] = { atomsDict }; CFDictionaryRef extensionDict = CFDictionaryCreate(kCFAllocatorDefault, extensionDictKeys, extensionDictValues, 1, nil, nil);
- 像素格式,CVPixelBufferRefs和glReadPixels
- 如何控制AVAssetWriter以正确的FPS写入
- OpenGL ES 2.0到iPad / iPhone上的video
- 使用AVAssetWriter录制和播放audio
- Swift Video Resizer AVAsset
- AVAssetWriter可以使用透明度编写文件吗?
- 使用AVCaptureVideoDataOutput和AVCaptureAudioDataOutput时的性能问题
- 为什么AVFoundation不能在iOS设备上接受我的平面像素缓冲区?
- AVAssetWriter如何创build没有压缩的movvideo?