gpt4 book ai didi

c++ - Media Foundation 设置视频隔行扫描和解码

转载 作者:行者123 更新时间:2023-11-30 05:14:18 25 4
gpt4 key购买 nike

我有一个 MOV 文件,我想对其进行解码并将所有帧作为单独的图像。

所以我尝试通过以下方式配置未压缩的媒体类型:

// configure the source reader
IMFSourceReader* m_pReader;
MFCreateSourceReaderFromURL(filePath, NULL, &m_pReader);

// get the compressed media type
IMFMediaType* pFileVideoMediaType;
m_pReader->GetCurrentMediaType(MF_SOURCE_READER_FIRST_VIDEO_STREAM, &pFileVideoMediaType);

// create new media type for uncompressed type
IMFMediaType* pTypeUncomp;
MFCreateMediaType(&pTypeUncomp);

// copy all settings from compressed to uncompressed type
pFileVideoMediaType->CopyAllItems(pTypeUncomp);

// set the uncompressed video attributes
pTypeUncomp->SetGUID(MF_MT_SUBTYPE, MFVideoFormat_RGB8);
pTypeUncomp->SetUINT32(MF_MT_ALL_SAMPLES_INDEPENDENT, TRUE);
pTypeUncomp->SetUINT32(MF_MT_INTERLACE_MODE, MFVideoInterlace_Progressive);

// set the new uncompressed type to source reader
m_pReader->SetCurrentMediaType(MF_SOURCE_READER_FIRST_VIDEO_STREAM, 0, pTypeUncomp);

// get the full uncompressed media type
m_pReader->GetCurrentMediaType(MF_SOURCE_READER_FIRST_VIDEO_STREAM, &pTypeUncomp);

我注意到,即使我将 MF_MT_INTERLACE_MODE 显式设置为 MFVideoInterlace_Progressive,最终配置仍配置为旧模式 MFVideoInterlace_MixedInterlaceOrProgressive

然后,我遍历所有样本并查看它们的大小:

IMFSample* videoSample = nullptr;
IMFMediaBuffer* mbuffer = nullptr;
LONGLONG llTimeStamp;
DWORD streamIndex, flags;

m_pReader->ReadSample(
MF_SOURCE_READER_FIRST_VIDEO_STREAM,
0, // Flags.
&streamIndex, // Receives the actual stream index.
&flags, // Receives status flags.
&llTimeStamp, // Receives the time stamp.
&videoSample) // Receives the sample or NULL.

videoSample->ConvertToContiguousBuffer(&mbuffer);

BYTE* videoData = nullptr;
DWORD sampleBufferLength = 0;

mbuffer->Lock(&videoData, nullptr, &sampleBufferLength);
cout << sampleBufferLength << endl;

我得到的样本大小非常不同:从 31 字节到 18000 字节。即使将格式更改为 MFVideoFormat_RGB32 也不会影响样本大小。

This问题似乎有同样的问题,但解决方案并未解决。

关于为什么我不能更改隔行扫描以及如何正确解码视频帧和从样本中获取图像数据的任何帮助?

非常感谢。

最佳答案

为了使 SourceReader 将样本转换为 RGB,您需要像这样创建它:

IMFAttributes* pAttr = NULL;
MFCreateAttributes(&pAttr, 1);
pAttr->SetUINT32(MF_READWRITE_ENABLE_HARDWARE_TRANSFORMS, TRUE);
pAttr->SetUINT32(MF_SOURCE_READER_ENABLE_VIDEO_PROCESSING, TRUE);

IMFSourceReader* m_pReader;
throwIfFailed(MFCreateSourceReaderFromURL(filePath, pAttr, &m_pReader), Can't create source reader from url");
pAttr->Release();

稍后,当 MF_SOURCE_READERF_CURRENTMEDIATYPECHANGED 发生时,您不应该中断循环。现在您将拥有相同大小的所有样本。否则,您可以使用 MFVideoFormat_NV12 子类型,然后在创建读取器时无需指定 MF_SOURCE_READER_ENABLE_VIDEO_PROCESSING 属性。

关于c++ - Media Foundation 设置视频隔行扫描和解码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43507393/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com