2017-02-28 73 views
2

我正在学习Windows媒体基础。
我测试了Windows SDK中提供的几个示例应用程序。
我有从相机和视频播放文件的视频捕获示例应用程序。合并两个视频流在一个流中,如画中画(WMF)

我想存档的是将这两个视频源组合在一个视频源中,然后生成一个视频流,如画中画。 Windows媒体基础如何做到这一点?

我已阅读有关MFCreateAggregateSource
https://msdn.microsoft.com/en-us/library/windows/desktop/dd388085(v=vs.85).aspx

MFCreateAggregateSource在这种情况下使用,或者它只是用于混合音频和视频流?

我想在全屏模式下放置一个视频,然后在小窗口的第一个视频的右上角显示另一个视频流。

这是如何使用媒体基础完成的?

** **更新

我更多的关注,利用WMF其解码并随后将它们混合,然后重新编码它们,然后写入文件读取两个视频流。而不是在屏幕上渲染它们。

回答

2

MFCreateAggregateSource不会进行视频混合。它将仅从两个来源创建一个来源,例如,可由MediaSession使用(通过拓扑和拓扑节点)。

如果你只是想显示两个视频,你可以使用Enhanced Video Renderer

您可以使用MFCreateAggregateSource每个流连接EVR。如果你不想处理时间戳/解码器等等,你还需要使用媒体会话(IMFMediaSesion)。

+0

这就是我所做的,但现在我正努力在一个窗口中分别显示两个视频。我试图使用'm_pVideoMixerControl-> SetStreamOutputRect(0,&rect)',但它不起作用。如何做到这一点。 – User7723337

+0

你通过什么值。 rect在0.0到1.0的范围内。例如MFVideoNormalizedRect rcHalf = {0.0,0.0,0.5,0.5};同时使用m_pStreamSink-> GetIdentifier检查流的标识符是否正确。 – mofo77

1

您的任务非常不寻常,并且没有任何媒体基础组件允许将两个视频流合并为一个。然而,'IMFMediaSesion'支持通过'MFCreateAggregateSource'在一个源中处理两个视频流。这意味着像'LEGO'这样的媒体基金会可以让您自行撰写解决方案,将两个视频流合并为一个像画中画一样的视频流,但它本身并不支持这种功能。

问候。

P.S.我想建议阅读'开发微软媒体基础应用程序' '安东波林格'(Developing Microsoft® Media Foundation Applications) - 它包含了很多例子的一个流,但它包含了'WaterMarkTransform'的代码 - 用于注入图像的代码Media Foundation Transform进入视频流 - 为您的解决方案启动此类代码凸轮 - 将一个视频流注入另一个视频流。

P.S.我有一个错误 - 我看到你只想显示画中画 - 所以EVR - 默认的视频渲染器支持16个视频流 - 一个参考和15个额外的 - 你需要通过'MFCreateVideoRendererActivate'创建'VideoRenderer',然后创建每个视频流(对于两个流中的每一个,你的情况)TopologyNode,为每个TopologyNode设置已经通过设置'SetObject'创建的'VideoRenderer' - 结果许多视频流将使用ONE'VideoRenderer'。BY设置SetUINT32TopologyNode'MF_TOPONODE_STREAMID',您必须选择哪个流将参考 - '背景图片' - 通过设置0,以及哪个流将为'MF_TOPONODE_STREAMID'大于0(例如1)的additional Pictureadditional Picture的位置可以通过IMFVideoMixerControl来控制 - 它包括下列方法: GetStreamOutputRect - 检索合成矩形内视频流的位置。

GetStreamZOrder - 检索视频流的z顺序。

SetStreamOutputRect - 设置合成矩形内视频流的位置。

SetStreamZOrder - 设置视频流的z顺序。

+0

嗨@Evgeny Pereguda:感谢您发布此详细信息,这非常有帮助。所以根据最新的更新,可以使用Windows媒体基础混合两个视频流。如果你有任何实现这个或任何文档的例子,可以描述它是如何实现的,这将有助于我理解流程。另外我对拓扑有点困惑,它在实现时如何使用。再次感谢您的帮助。 – User7723337

+0

嗨@Evgeny Pereguda:同样如果我们想将混合视频(画中画)保存到一个文件中,那么该怎么做? – User7723337

+0

我可以推荐阅读'Anton Polinger'开发的'开发Microsoft®Media Foundation应用程序'一书 - 它是解释Media Foundation Topology概念的一本书。我有这本书的代码示例 - 。此外,您可以研究我的项目om Media Foundation [在Windows 7和Windows 8上从网络摄像机捕捉实时视频](https://www.codeproject.com/articles/776058/捕获实时视频 - 从网络摄像头在Windows上) - 这个项目有与网络摄像头一起工作的代码 - 它包括了在实时视频中注入图像的例子 - 'WaterMark'。 –

1

MFCreateAggregateSource甚至序列发生器可能对视频混合工作正常,但为了更好地控制过程,在我参与的项目中,我使用了多个MFSourceReaders来MFSinkWriter方法。这样,如果我将EVR附加到接收器写入器,或者将输出视频存储在文件中,我都可以显示混合视频内容。在我正在开发的项目中,要求仅输出到mp4,但稍后我将不得不添加预览支持。为此,我打算使用两个接收器作家 - 一个用于EVR(或DX11VideoRenderer),一个用于MP4接收器。实施工作非常稳定。它有一个视频混合线程,可以从每个源读取器读取,匹配时间戳,混合视频样本,并将混合视频样本或音频样本(仅一个)输出到接收器写入器。希望这可以帮助。

+0

是否可以提供更多关于这个或任何涉及混合两个视频流的组件示例的详细信息。目前,我并不担心显示混合流,但是,1.阅读两个流,2.混合然后写入文件。所以我会读流使用WMF API解码它们,然后混合它们,然后重新编码它们,然后写入文件。 – User7723337

+1

这个想法是为每个源(文件,捕获)创建一个IMFSourceReader。为其中的每一个实现一个IMFSourceReaderCallback,以便异步接收样本并将每个样本放入一个队列中。然后在一个单独的线程中取出样本并混合视频样本(例如使用directx)。您可以使用从EVR获取或由您创建的DirectX管理器(DX设备)配置IMFSourceReaders。您可以通过IMFSinkWriter对象将混合视频样本提供给EVR。或者您可以检查MFCaptureD3D样本,了解如何直接使用DX绘制混合样本。 – VuVirt

+0

感谢您的详细信息。我们如何使用DirectX来混合两个流样本?当我们混合采样时,我们如何配置EVR进行显示。 – User7723337

相关问题