IsampleGrabberFilter一次一个框架步骤

ISampleGrabberFilter one frame step at a time

本文关键字:框架 一个 一次 IsampleGrabberFilter      更新时间:2023-10-16

i有一个图形端点,其中是 samplegrabber 我使用回调函数获取所有帧的未压缩数据。

在我的顶级接口代码中,我想要一个函数 readnextframe()在图中获取下一个帧的数据(直到到达文件的末尾)。

通过性能不好的实现将是将 NextFrameIndex 传递给GrabberCB类,以指定我目前想要哪个帧。因此,我的回调功能会跳过所有其他帧,只选择我想要的框架。这是昂贵的,因为该图必须通过整个文件来选择单个帧数据。

我注意到有一个 ivideoframestep 接口,这是我想要的。但是看来该界面与样本抓取器不兼容,并且文档说:

在Microsoft下实施帧准确寻求的解码 DirectShow必须实现AM_KSPROPSETID_FRAMESTEP属性, 与ivideoframestep接口一起使用。

我尝试将其连接到我的图形,但 ivideoframestep :: canstep()函数返回false for Me for Me for for Me,这意味着我无法将其与sample Grabber一起使用。

所以我的问题是:是否有一个简单且性能的好解决方案,以便我可以使用我的图表来保持当前状态,然后将单个帧向前进行,然后使用示例抓取器获取数据?

您发现IVideoFrameStep有某些工作要求,其背后的想法是整个滤镜图确实会弹奏状态过渡,运行和暂停。

要使用示例抓手来一次获取所有帧,您可以实现一种更简单的方法,这没有任何特殊要求。

  1. 让您的过滤器图运行;从图表中删除时钟是很有意义的 - 请参阅IMediaFilter::SetSyncSource(NULL)
  2. 使用SampleCB回调
  3. 有一个样本抓取者
  4. 执行了SampleCB后,请使用数据进行操作,并指示运行图形的更高级别代码的框架
  5. 在上面的SampleCB和#3内完成时,请勿从该方法返回,而要等待事件,这表明您准备继续
  6. 高级应用程序代码将处理帧并设置上面#4的事件,允许SampleCB退出并进一步努力获得新的帧;使用新框架,您将在上面的#3中重复。

也就是说,您的 SampleCB等待是锁定整个管道,以保留其状态的所需时间,让您在方便的速度下按框架进行处理。

SampleCB的伪代码将是(带有手动设置/重置事件):

data m_Data;
event m_DataAvailability;
event m_NextFrameRequest;
void SampleCB(Frame)
{
  m_Data = Frame.GetData();
  m_DataAvailability.Set();
  m_NextFrameRequest.WaitFor(); // Sleeping here until signaled to continue
  m_NextFrameRequest.Reset();
}
data ReadNextFrame()
{
  m_DataAvailability.WaitFor();
  data Data = m_Data;
  m_DataAvailability.Reset(); // Current data processed, we need next portion
  m_NextFrameRequest.Set(); // Indicate that we allow next callback call
  return Data; // Make captured frame available
}