0

我希望能够寻找 MPEG-2 文件中的任意帧(来自 DVD,我猜它被称为 MPEG-2 程序流)。到目前为止,我一直在使用 OpenCV 2.1 来访问这些帧,但这只能在逐帧的基础上工作(仅向前搜索)。后来,当我安装 OpenCV 2.3.1 时,这种可能性就消失了,即仅限于 AVI。无论如何,我想在没有 OpenCV 的情况下做到这一点。我设法寻找关键帧(我想)或每一个帧(例如每 12 帧)。现在,看VirtualDub 的帧精确寻找是可能的。它说:''解析交错的 MPEG-2 文件''。这到底是什么意思,我必须从哪里开始做同样的事情?它甚至合法吗,我记得在某处读过一些关于它的东西,但我真的不记得了。我正在使用directshow在C++中编程。据我所知,directshow 不会这样做。然后我在研究 CBaseFilter、streamtime 方法等,但在我深入那个复杂的话题之前,我想知道这是否是正确的方法。期待您的解答,谢谢!

@Geraint:过滤图的代码片段:

CoCreateInstance(CLSID_FilterGraph,NULL,CLSCTX_INPROC,IID_IGraphBuilder,(LPVOID *)&pGraphBuilder);
 CoCreateInstance(CLSID_MPEG2Demultiplexer,NULL,CLSCTX_INPROC,IID_IBaseFilter,(LPVOID *)&pib);
 CoCreateInstance(CLSID_CMPEG2VidDecoderDS,NULL,CLSCTX_INPROC,IID_IBaseFilter,(LPVOID *)&pib2);

 pGraphBuilder->AddFilter(pib,L"Sample Splitter");
 pGraphBuilder->AddFilter(pib2,L"Sample Decoder");

 ZeroMemory(&am_media_type, sizeof(am_media_type));
am_media_type.majortype = MEDIATYPE_Video;
am_media_type.subtype = MEDIASUBTYPE_MPEG2_VIDEO;
am_media_type.formattype = FORMAT_MPEG2Video;

pGraphBuilder->QueryInterface(IID_IMediaControl,(LPVOID *)&pMediaControl);
pGraphBuilder->QueryInterface(IID_IMediaSeeking, (void**)(&pMediaSeeking));
pGraphBuilder->QueryInterface(__uuidof(IVideoFrameStep), (PVOID *)&fst); 
pGraphBuilder->QueryInterface(IID_IMediaEvent, (void **)&imev);
pGraphBuilder->QueryInterface(IID_IBasicVideo,(LPVOID *)&ibv);

pGraphBuilder->RenderFile(FILENAME,0);

然后我使用 IMediaSeeking 来寻找视频。我也尝试过帧步进(因此上面的参考资料)。

4

1 回答 1

3

DirectShow 能够提供帧精确的搜索。但是,如果没有索引,这是基于从文件开始的时间偏移量,而不是帧数。

使用 IMediaSeeking 设置开始时间。解复用器将在此之前以某种方式开始传送压缩帧。解码器将从前一个关键帧开始解码,但会丢弃您选择的起点之前的任何帧。

G

于 2013-02-08T15:14:39.970 回答