多次拓扑切换后 Windows Media 视频播放速度变慢

发布于 2025-01-10 21:58:02 字数 1195 浏览 0 评论 0原文

Win64,C++ 中的 Windows Media Foundation 应用程序。我有一些拓扑和一个媒体会话。该应用程序在拓扑之间切换:

TheSession->SetTopology(MFSESSION_SETTOPOLOGY_IMMEDIATE, NextTopology);
PROPVARIANT v;
InitPropVariantFromInt64(0, &v);
TheSession->Start(&GUID_NULL, &v);

通常可以正常工作。但我注意到一段时间后,视频播放变得很慢,它会跳帧。这台机器有足够的CPU。跳帧持续了至少一分钟,并不是一时的侥幸。一段时间后,所有视频都会出现跳帧现象。我对这种情况有一个半可靠的重现。当您在该状态下切换拓扑时,它会在短时间内(约 30 秒)运行良好,然后速度变慢。减速期间 CPU 利用率不会飙升 - 这不是 CPU。有一些资源耗尽,但CPU没有耗尽。

当我这样切换拓扑时,之前的拓扑不会显式停止。被逐出的拓扑的某些处理是否仍在运行,即使它不再在会话中?如果是这样,如何停止断开连接的拓扑上的处理?我想到的唯一想法是在被逐出的拓扑的媒体源上调用 Stop。

停止并开始会话似乎可以消除这种情况。

另外,我能否以某种方式确认我对无关处理的预感是正确的?我可以看到拓扑对象上没有任何状态。

我正在向所有拓扑提供相同的音频和视频渲染器,不确定这是否重要。

作为解决方法,我实现了以下逻辑:在视频切换时,会话停止,代码等待停止事件,然后加载并启动拓扑。在测试中我无法再重现跳帧。现在,我会接受这个好消息。


UPD:我创建了一个最小的示例,没有示例视频文件: https://gist.github。 com/sevaa/88754eafffd68d8671ec593dc310faec

它依赖于两个视频文件,c:\Temp\SlowPlayer\a.m4v 和 c:\Temp\SlowPlayer\b.m4v(随意更改路径)。如果您尝试重现,您甚至可以在那里使用同一视频的两个副本,只要您可以观察视频切换即可。使用 Visual Studio 2022 编译为 Windows 桌面项目。

在我的测试中,跳帧在开关#10 左右开始明显,在#15 左右变得非常糟糕。

Win64, Windows Media Foundation app in C++. I have a handful of topologies and a single media session. The app switches between topologies:

TheSession->SetTopology(MFSESSION_SETTOPOLOGY_IMMEDIATE, NextTopology);
PROPVARIANT v;
InitPropVariantFromInt64(0, &v);
TheSession->Start(&GUID_NULL, &v);

It generally works. But I've noticed after some time of this, video playback becomes slow, it skips frames. The machine has CPU aplenty. Frame skipping lasted for at least a minute, wasn't a momentary fluke. After a while, frame skipping is observed on all videos. I have a semi-reliable repro on this condition. When you switch topologies in that state, it goes fine for a short while (~30sec), then slows down. The CPU utilization during the slowdown doesn't spike - it's not CPU. There is some resource exhaustion, but not CPU.

When I switch topologies like that, the previous topology is not explicitly stopped. Could it be that some processing for the evicted topology is still running, even though it's not in the session anymore? If so, how does one stop the processing on a disconnected topology? The only idea that comes to mind is calling Stop on the media source of the evicted topology.

Stopping and starting the session seems to clear up the condition.

Also, can I somehow confirm that my hunch about extraneous processing is correct to begin with? There is no state on the topology object that I can see.

I'm feeding the same audio and video renderer to all topologies, not sure if it matters.

As a workaround, I've implemented the logic where on video switch, the session is stopped, the code waits for the stopped event, then the topology is loaded and started. On testing I can't reproduce the frame skipping any longer. For now, I'll take the good news.


UPD: I've created a minimal example, sans the sample video files: https://gist.github.com/sevaa/88754eafffd68d8671ec593dc310faec

It relies on two video files, c:\Temp\SlowPlayer\a.m4v and c:\Temp\SlowPlayer\b.m4v (feel free to change the paths). If you try to reproduce, you could even use two copies of the same video there, as long as you can observe the video switching. Compile with Visual Studio 2022 as a Windows desktop project.

The frame skipping in my testing starts being visible around switch #10, gets really bad around #15.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文