使用 DirectShow 将字幕文件与 MPEG 视频进行帧精确同步
这是我已经处理了一段时间的问题,并且一直无法得到很好的答案(即使是来自微软)。 我正在使用通用转储过滤器将硬件压缩的 MPEG 文件写入磁盘。 在图中,我还有一个 SampleGrabber 过滤器,它在每一帧上都会被调用。 从 SampleGrabber 回调中,我获得一个字幕以及 DirectShow 时间戳,并将它们写入 SAMI (.smi) 字幕文件。 这一切似乎都有效,因为 SAMI 文件包含每个帧的正确字幕。 但是,我有一些问题:
前几个(通常是 3 或 4 个)DirectShow 时间戳都是 0。如果我从 SampleGrabber 收到回调,这些时间戳不应该递增吗?
当我开始播放时,显示的第一个时间戳是 SAMI 文件中大约 10-20 个字幕。 我假设第一帧将显示文件中的第一个时间戳。
这可能与#2 有关,但字幕未同步到文件中的相应帧。 它们有时可能会延迟最多 40 帧。
我通过 C++ 使用 DirectShow,在 Windows XP SP3(使用最新驱动程序 09/08/2008)下使用 Hauppauge HVR-1800 进行捕获,并在 Media Player Classic 6.4.9.0 下播放。 欢迎任何想法。
This is a problem I have been dealing with for a while, and haven't been able to get a good answer (even from Microsoft). I'm using the generic dump filter to write hardware compressed MPEG files out to disk. In the graph, I also have a SampleGrabber filter that gets called on every frame. From the SampleGrabber callback, I get a subtitle, along with the DirectShow timestamp and write them out to a SAMI (.smi) subtitle file. This all seems to be working, as the SAMI file contains the correct subtitles for every frame. However, I have a few problems:
The first few (usually 3 or 4) DirectShow timestamps are all 0. If I'm getting callbacks from the SampleGrabber, shouldn't these timestamps be incrementing?
When I begin playback, the first timestamp shown is about 10-20 subtitles into the SAMI file. I'd assume the first frame would show the first timestamp in the file.
This is probably related to #2, but the subtitles are not synchronized to the appropriate frames in the file. They can sometimes be up to 40 frames late.
I'm using DirectShow via C++, capturing with a Hauppauge HVR-1800 under Windows XP SP3 (with latest drivers 09/08/2008), and playing back under Media Player Classic 6.4.9.0. Any ideas are welcome.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
您使用的是获取传入的 IMediaSample 的 GetTime 还是 GetMediaTime。 GetTime 是您想要的,因为它代表流演示时间。
请务必检查传入的 IMediaSample 的 isPreRoll功能。 应忽略预卷样本,因为它们将在播放期间再次输出。 我要做的另一件事是确保您的样本采集器尽可能位于过滤器图表的下游。 最好在任何解复用器和渲染器之后。
另请参阅有关 时间戳 的文章DirectShow 文档。 它概述了使用时间戳的其他注意事项。
当然,即使了解了上述所有提示,仍然无法绝对保证特定 DirectShow 过滤器的行为方式。
Are you using getting the incoming IMediaSample's GetTime or GetMediaTime. GetTime is what you want as it respresents the streams presentations time.
Be sure to also check the incoming IMediaSample's isPreRoll function. Preroll samples should be ignored as they will be output again during playback. Another thing I would do is make sure that your sample grabber is as far downstream in your filtergraph as it can be. Preferably after any demuxer's and renderers.
Also see the article on TimeStamps in the DirectShow documentation. It outlines the other caveats of using timestamps.
Of course, even after all of the tips above, there is still no absolute guarantee as to how a particular DirectShow filter is going to behave.