2

我的任务是修复医疗应用程序中的一个错误,除其他外,它可以从口腔内摄像机捕获快照。它使用 DirectShow SampleGrabber 来完成此任务。我必须声明我没有与 DirectShow 合作过,所以我正在努力跟上进度。我基本上了解各种组件如何协同工作。

无论如何,错误本身似乎微不足道,但我无法找到解决方法。由于该系统的模块化特性,预览窗口是一个单独的图表的一部分,而不是由 SampleGrabber 创建的图表(这是一个很长的故事,但这是由于遗留代码支持以前的设备)。当相机处于活动状态时,我们可以拍摄快照,一切都很开心。关闭相机时,SampleGrabber 拍摄暗帧,但 DirectShow 在释放预览模块中创建的 IAMStreamConfig 接口时崩溃(访问冲突)。由于某种原因,SampleGrabber 图似乎以某种方式破坏了预览模块中构建的图。由于此应用程序的性质,我无法在此处显示任何来源,但基本上这是我想要完成的:

我需要能够检测相机是否真的打开。我遇到的问题是,当相机插入(USB)时,它似乎看起来像系统打开并返回视频流,只是流不包含真实数据。当我使用 GetState 方法检查捕获过滤器的状态时,它声称它正在运行;当我检查视频格式属性时,它也会返回正确的属性。在我看来,相机上的按钮只是简单地打开/关闭相机传感器本身,但是当相机关闭时,设备仍然返回一个空白流。不过肯定有些不同,因为它不会在传感器实际打开并返回实时视频时崩溃。

有人知道我如何确定流是空白还是有实时视频?IE,我可以调用任何公开的接口或方法来确定这一点吗?我已经浏览了 MSDN 的 DirectShow 文档中的所有各种接口,但还没有找到一种方法来做到这一点。

4

4 回答 4

1

在源过滤器(或您可以访问的最早过滤器)之后连接的过滤器中,检查它通过receive()函数接收到的IMediaSample :

HRESULT Receive(IMediaSample *pSample);
于 2013-06-11T17:23:34.377 回答
1

如果您使用的是 ISampleGrabber,那么您应该使用ISampleGrabber::SetCallback设置它的回调函数

HRESULT SetCallback(
  ISampleGrabberCB *pCallback,
  long WhichMethodToCallback
);

这需要您实现一个类 extends ISampleGrabberCB。之后,您可以在功能SampleCB中检查您收到的样品

HRESULT SampleCB(
  double SampleTime,
  IMediaSample *pSample
);
于 2013-06-11T18:32:27.157 回答
1

没有通用的方法来判断相机是否已连接或流是否为空白。您通常有以下情况之一:

  1. 相机关闭时您停止接收任何样本
  2. 您会收到所有像素归零的样本,或者是全蓝色图片或类似的

有些相机有信号丢失通知,但它是特定于型号和通知方法的。

因此,在第一种情况下,您只需停止调用回调。要覆盖第二个,您需要检查框架是否完全填充了纯色。当您捕获原始视频(未压缩)时,这是一件相当简单的事情。

于 2013-06-11T18:56:33.030 回答
1

如果您不想调用采样采集器的回调函数,那么您可以考虑在采样采集器和源过滤器(或源过滤器之后)之间添加一个特殊的变换过滤器,以及这个变换过滤器的作用检查输入样本是否损坏并阻止那些损坏的样本。这基本上需要您实现自己的Transform()功能:

HRESULT CRleFilter::Transform(IMediaSample *pSource, IMediaSample *pDest)
于 2013-06-11T19:12:47.567 回答