locked
DirectShow Mobile5.0 bad RenderStream use to connect video filter to renderer filter RRS feed

  • 问题

  • Hi!


         I'm now trying to realize my own video capture using directshow under wince. I write my own renderer filter to get video sample. When I code as follows,

    Code Snippet
    m_pCaptureGraphBuilder->RenderStream(&PIN_CATEGORY_PREVIEW, &MEDIATYPE_Video, m_pVideoCaptureFilter, NULL, m_pVRFilter)

    it returns E_FAIL.(But I get this right under xp.)


    But when I use this function,

    Code Snippet
    m_pCaptureGraphBuilder->RenderStream(&PIN_CATEGORY_PREVIEW, &MEDIATYPE_Video, m_pVideoCaptureFilter, NULL, NULL);

     

    it returns S_OK.


    So, I think video filter (m_pVideoCaptureFilter)is right, but why video filter can not connect to renderer filter(m_pVRFilter)?And why I use RenderStream under xp to connect to My Renderer filter (m_pVRFilter), it's OK?

     

    My Renderer Filter's source code as follows:

     

    // IVRControl.h

    Code Snippet

    static const GUID CLSID_wkVideoRenderer =
    { 0xf81331db, 0x2e46, 0x43e7, { 0x87, 0x9, 0xbe, 0x57, 0x20, 0x5d, 0x89, 0x14 } };


    #ifndef __IVRCONTROL__
    #define __IVRCONTROL__

     

    #ifdef __cplusplus
    extern "C" {
    #endif

     

    // {244DF760-7E93-4cf0-92F4-DCB79F646B7E}
    static const GUID IID_IVRControl =
    {0x244df760, 0x7e93, 0x4cf0, {0x92, 0xf4, 0xdc, 0xb7, 0x9f, 0x64, 0x6b, 0x7e}};

    DECLARE_INTERFACE_(IVRControl, IUnknown)
    {

    STDMETHOD(GetBmpInfo) (THIS_
    BITMAPINFO** ppBmpInfo
    ) PURE;


    STDMETHOD(GetPointer) (THIS_
    BYTE** ppb
    ) PURE;

    };

     

    #ifdef __cplusplus
    }
    #endif

    #endif // __IVRCONTROL__

     

     

     

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    //VR.h

    Code Snippet

    #include
    #include "IVRControl.h"

    class CVideoRenderer : public CBaseVideoRenderer, public IVRControl
    {
    public:

    static CUnknown * WINAPI CreateInstance(LPUNKNOWN, HRESULT *);

    CVideoRenderer(LPUNKNOWN pUnk,HRESULT* phr);
    ~CVideoRenderer();

    public:

    HRESULT CheckMediaType(const CMediaType* pmt);

    HRESULT SetMediaType(const CMediaType* pmt);

    HRESULT DoRenderSample(IMediaSample* pMediaSample);


    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, void ** ppv);


    DECLARE_IUNKNOWN;
    STDMETHODIMP GetBmpInfo(BITMAPINFO** ppBmpInfo);
    STDMETHODIMP GetPointer(BYTE** ppb);

    private:

    BITMAPINFO m_bmpInfo;
    BYTE* m_pCopyBuffer;
    UINT m_pixelNum;

    };

     

     


    /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    //VR.cpp

    Code Snippet

    #include "VR.h"
    #pragma comment(lib,"strmbase.lib")
    #pragma comment(lib,"strmiids.lib")
    #pragma comment(lib,"mmtimer.lib")

    // Setup data

    const AMOVIESETUP_MEDIATYPE sudIpPinTypes =
    {

    &MEDIATYPE_Video, // MajorType
    &MEDIASUBTYPE_NULL // MinorType

    };

     

    const AMOVIESETUP_PIN sudIpPin =
    {

    L"Input", // The Pins name
    FALSE, // Is rendered
    FALSE, // Is an output pin
    FALSE, // Allowed none
    FALSE, // Allowed many
    &CLSID_NULL, // Connects to filter
    NULL, // Connects to pin
    1, // Number of types
    &sudIpPinTypes // Pin details

    };

     

    const AMOVIESETUP_FILTER sudVRAx =
    {

    &CLSID_wkVideoRenderer, // Filter CLSID /**/
    L"lwVideoRenderer", // String name /**/
    MERIT_NORMAL, // Filter merit
    1, // Number of pins
    &sudIpPin // Pin details

    };


    // List of class IDs and creator functions for the class factory. This
    // provides the link between the OLE entry point in the DLL and an object
    // being created. The class factory will call the static CreateInstance
    // function when it is asked to create a CLSID_VideoRenderer object

    CFactoryTemplate g_Templates[] = {

    { L"lwVideoRenderer" /**/
    , &CLSID_wkVideoRenderer /**/
    , CVideoRenderer::CreateInstance
    , NULL
    , &sudVRAx },

    };


    int g_cTemplates = sizeof(g_Templates) / sizeof(g_Templates[0]);


    STDAPI DllRegisterServer()
    {

    return AMovieDllRegisterServer2( TRUE );

    }

     

    STDAPI DllUnregisterServer()
    {

    return AMovieDllRegisterServer2( FALSE );

    }

     

    extern "C" BOOL WINAPI DllEntryPoint(HINSTANCE, ULONG, LPVOID);

    BOOL APIENTRY DllMain(HANDLE hModule, DWORD dwReason, LPVOID lpReserved)
    {

    return DllEntryPoint((HINSTANCE)(hModule), dwReason, lpReserved);

    }


    CVideoRenderer::CVideoRenderer(LPUNKNOWN pUnk,HRESULT *phr) : CBaseVideoRenderer(CLSID_wkVideoRenderer,L"lw Video Renderer",pUnk,phr)
    {

    m_pCopyBuffer = NULL;
    m_pixelNum = 0;

    }


    //================================================== =========
    CVideoRenderer::~CVideoRenderer()
    {

    if(this->m_pCopyBuffer){
    delete [] m_pCopyBuffer;

    }

    }

     

    //================================================== =========
    CUnknown* WINAPI CVideoRenderer::CreateInstance(LPUNKNOWN pUnk,HRESULT* phr)
    {

    return new CVideoRenderer(pUnk,phr);

    }

     

    //================================================== =========
    HRESULT CVideoRenderer::CheckMediaType(const CMediaType* pmt)
    {

    VIDEOINFO *pvi;

    //
    if( *pmt->FormatType() != FORMAT_VideoInfo ) {

    return E_INVALIDARG;

    }

    // RGB24
    pvi = (VIDEOINFO *)pmt->Format();
    if(IsEqualGUID( *pmt->Type(),MEDIATYPE_Video) && IsEqualGUID( *pmt->Subtype(),MEDIASUBTYPE_RGB24)){
    return S_OK;
    }

    return E_INVALIDARG;

    }


    //================================================== =========
    HRESULT CVideoRenderer::SetMediaType(const CMediaType* pmt)
    {

    VIDEOINFO *pviBmp; // Bitmap info header
    pviBmp = (VIDEOINFO *)pmt->Format();
    memset(&m_bmpInfo,0,sizeof(BITMAPINFO)); //
    m_bmpInfo.bmiHeader = pviBmp->bmiHeader;
    m_bmpInfo.bmiHeader.biBitCount = 32; // 32bit
    m_bmpInfo.bmiHeader.biSizeImage = m_bmpInfo.bmiHeader.biSizeImage * 4 / 3;
    if(m_pCopyBuffer){

    delete [] m_pCopyBuffer;
    m_pCopyBuffer = NULL;

    }
    m_pCopyBuffer = new BYTE[m_bmpInfo.bmiHeader.biSizeImage]; //
    m_pixelNum = m_bmpInfo.bmiHeader.biWidth * m_bmpInfo.bmiHeader.biHeight;
    return S_OK;

    }


    //================================================== =========
    HRESULT CVideoRenderer :: DoRenderSample(IMediaSample* pMediaSample)
    {

    BYTE* pb = NULL;
    pMediaSample->GetPointer(&pb);

    if(!pb){
    return E_FAIL;

    }


    CAutoLock cAutoLock(&this->m_RendererLock);
    BYTE* pb32 = m_pCopyBuffer;

    // 24bit-->> 32bit
    for(UINT i = 0; i < m_pixelNum; i ++){
    pb32[0] = pb[0];
    pb32[1] = pb[1];
    pb32[2] = pb[2];
    pb32[3] = 0xff;
    pb += 3;
    pb32 += 4;
    }


    return S_OK;

    }


    //================================================== =========
    STDMETHODIMP CVideoRenderer::NonDelegatingQueryInterface(REFIID riid,void** ppv)
    {

    CheckPointer(ppv,E_POINTER);

    if(riid == IID_IVRControl){
    return GetInterface((IVRControl*) this,ppv);
    }else{
    return CBaseVideoRenderer::NonDelegatingQueryInterface(ri id,ppv);
    }

    }

     

    //================================================== =========

    STDMETHODIMP CVideoRenderer::GetBmpInfo(BITMAPINFO** ppBmpInfo)
    {

    *ppBmpInfo = &this->m_bmpInfo;
    return S_OK;
    }

     

    STDMETHODIMP CVideoRenderer::GetPointer(BYTE** ppb)
    {

    *ppb = m_pCopyBuffer;
    return S_OK;
    }

     

     

    2008年8月6日 2:57