iSampleGrabber,回调方法。代码有效,但可能需要一些爱吗?

时间:2013-05-15 10:20:34

标签: c++ directshow samplegrabber

好。所以我有我的isamplegrabber回调方法工作,我能够将数据转换为opencv。但由于这对我来说是全新的事实,我只是想得到一些反馈,如果代码是“正确的”,因为它似乎不是一个好的..

首先在我的代码中(来自互联网)我得到了:

#pragma region Formerly located in qedit.h in Windows SDK, now obsoleted and defined within project

void createDirectShowGraph(void);
struct __declspec(uuid("0579154a-2b53-4994-b0d0-e773148eff85"))
ISampleGrabberCB : IUnknown
{
    //
    // Raw methods provided by interface
    //

      virtual HRESULT __stdcall SampleCB (double SampleTime, struct IMediaSample * pSample ) = 0;
      virtual HRESULT __stdcall BufferCB (double SampleTime, unsigned char * pBuffer, long BufferLen ) = 0;
};
static const IID IID_ISampleGrabberCB = { 0x0579154A, 0x2B53, 0x4994, { 0xB0, 0xD0, 0xE7, 0x73, 0x14, 0x8E, 0xFF, 0x85 } };
struct __declspec(uuid("6b652fff-11fe-4fce-92ad-0266b5d7c78f"))
ISampleGrabber : IUnknown
{
    //
    // Raw methods provided by interface
    //
      virtual HRESULT __stdcall SetOneShot (long OneShot ) = 0;
      virtual HRESULT __stdcall SetMediaType (struct _AMMediaType * pType ) = 0;
      virtual HRESULT __stdcall GetConnectedMediaType (struct _AMMediaType * pType ) = 0;
      virtual HRESULT __stdcall SetBufferSamples (long BufferThem ) = 0;
      virtual HRESULT __stdcall GetCurrentBuffer (/*[in,out]*/ long * pBufferSize,
        /*[out]*/ long * pBuffer ) = 0;
      virtual HRESULT __stdcall GetCurrentSample (/*[out,retval]*/ struct IMediaSample * * ppSample ) = 0;
      virtual HRESULT __stdcall SetCallback (struct ISampleGrabberCB * pCallback,long WhichMethodToCallback ) = 0;
};

struct __declspec(uuid("c1f400a0-3f08-11d3-9f0b-006008039e37"))
SampleGrabber;
    // [ default ] interface ISampleGrabber

#pragma endregion

后来,在互联网的帮助下,我插入了这个:

class CFakeCallback : public ISampleGrabberCB 
{
public:
    //some variables and stuff... 
    STDMETHODIMP_(ULONG) AddRef()  { return 2; }
    STDMETHODIMP_(ULONG) Release() { return 1; }

    STDMETHODIMP QueryInterface(REFIID riid, void ** ppv)
    {
        //CheckPointer(ppv, E_POINTER);

        if (riid == IID_ISampleGrabberCB || riid == IID_IUnknown) 
        {
            *ppv = (void *) static_cast<ISampleGrabberCB *>(this);
            return NOERROR;
        }    
        return E_NOINTERFACE;
    }

    STDMETHODIMP SampleCB( double SampleTime, IMediaSample * pSample )
    { 
         //The data for grabbing the frames.
    }

    STDMETHODIMP BufferCB( double SampleTime, BYTE * pBuffer, long BufferLen )
    {

        return 0;
    }

};


CFakeCallback callbackF;

我用:

pSampleGrabber->SetCallback(&callbackF,0);

一切正常,但我想知道。 我是否需要为回调方法创建一个新类?我可以在“#pragma region ...”中看到所有方法。我不能将这些方法用于回调吗?

问题(S):

one:我是否需要为sampleCB / bufferCB方法设置该类“fakeCallback”?或者我可以在某种程度上使用第一个代码部分中的方法吗?

二:“虚拟” - 方法,意味着此方法可以“覆盖”?是我在创建类fakeCallback时所做的,使用方法sampleCB&amp; bufferCB?

谢谢!

1 个答案:

答案 0 :(得分:1)

如果您只是想通过回调从过滤器图形中获取一个帧,那么您需要实现ISampleGrabberCB接口。 您已经实现了使用ISampleGrabberCB接口所需的CFakeCallback。您可以使用BufferCB或SampleCB获取样本。因此,当您实现CFakeCallback时,您需要覆盖SampleCB和BufferCB。其中一个将包含自定义代码以获取样本,而另一个将仅返回S_OK(0)。在您的代码中,您正在使用正确的SampleCB。

但是,如果您不想使用回调方法,则Windows SDK中已存在SampleGrabber。您只需要在应用程序中包含qedit.h即可。