예제 #1
0
//////////////////////////////////////////////////////////////////////////////
//
// CGargle::Clone
//
HRESULT CGargle::Clone(IMediaObjectInPlace **ppCloned) 
{
    if (!ppCloned)
        return E_POINTER;

    HRESULT hr = S_OK;
    CGargle * pNewGargle = new CComObject<CGargle>;
    if( !pNewGargle )
        hr = E_OUTOFMEMORY;

    hr = pNewGargle->Init();

    IMediaObject * pCloned = NULL;
    if( SUCCEEDED( hr ) )
    {
        IUnknown *pUnk;
        hr = pNewGargle->QueryInterface( IID_IUnknown, (void **) &pUnk );
        if( SUCCEEDED( hr ) )
        {
            hr = pUnk->QueryInterface( IID_IMediaObject, (void **) &pCloned );
            pUnk->Release();
        }
    }
    else
    {
        return hr;
    }

    //
    // Copy parameter control information
    //
    if (SUCCEEDED(hr))
        hr = pNewGargle->CopyParamsFromSource((CParamsManager *) this);

    // Copy current parameter values
    GargleFX params;
    if (SUCCEEDED(hr))
        hr = GetAllParameters(&params);

    if (SUCCEEDED(hr))
        hr = pNewGargle->SetAllParameters(&params);

    if (SUCCEEDED(hr))
    {
        // Copy the input and output types
        DMO_MEDIA_TYPE mt;
        DWORD cInputStreams = 0;
        DWORD cOutputStreams = 0;
        GetStreamCount(&cInputStreams, &cOutputStreams);

        for (DWORD i = 0; i < cInputStreams && SUCCEEDED(hr); ++i)
        {
            hr = GetInputCurrentType(i, &mt);
            if (hr == DMO_E_TYPE_NOT_SET)
            {
                hr = S_OK; // great, don't need to set the cloned DMO
            }
            else if (SUCCEEDED(hr))
            {
                hr = pCloned->SetInputType(i, &mt, 0);
                MoFreeMediaType( &mt );
            }
        }

        for (i = 0; i < cOutputStreams && SUCCEEDED(hr); ++i)
        {
            hr = GetOutputCurrentType(i, &mt);
            if (hr == DMO_E_TYPE_NOT_SET)
            {
                hr = S_OK; // great, don't need to set the cloned DMO
            }
            else if (SUCCEEDED(hr))
            {
                hr = pCloned->SetOutputType(i, &mt, 0);
                MoFreeMediaType( &mt );
            }
        }

        if (SUCCEEDED(hr))
            hr = pCloned->QueryInterface(IID_IMediaObjectInPlace, (void**)ppCloned);

        // Release the object's original ref.  If clone succeeded (made it through QI) then returned pointer
        // has one ref.  If we failed, refs drop to zero, freeing the object.
        pCloned->Release();
    }
    return hr;
}
예제 #2
0
/////////////////////
//
//  IMediaObjectInPlace::Clone
//
//  The Clone method creates a copy of the DMO in its current state.
//
//  Parameters
//
//      ppMediaObject
//          [out] Address of a pointer to receive the new DMO's
//          IMediaObjectInPlace interface.
//
//  Return Value
//      Returns S_OK if successful. Otherwise, returns an HRESULT value
//      indicating the cause of the error.
//
//  If the method succeeds, the IMediaObjectInPlace interface that it returns
//  has an outstanding reference count. Be sure to release the interface when
//  you are finished using it.
//
HRESULT CHXAudioDeviceHookBase::Clone(IMediaObjectInPlace **ppMediaObject)
{
    // Check the input pointer
    if (!ppMediaObject)
    {
        return E_POINTER;
    }

    // This will be cleaned up when client releases the newly created object
    // or if there's some error along the way
    CHXAudioDeviceHookBase * pNewHXAudioDeviceHook = new CComObject<CHXAudioDeviceHookBase>;
    if( !pNewHXAudioDeviceHook )
    {
        return E_OUTOFMEMORY;
    }

    HRESULT hr = S_OK;

    hr = pNewHXAudioDeviceHook->UpdateStatesInternal();

    IMediaObject * pCloned = NULL;
    if( SUCCEEDED( hr ) )
    {
        IUnknown *pUnk;
        hr = pNewHXAudioDeviceHook->QueryInterface( IID_IUnknown, (void **) &pUnk );
        if( SUCCEEDED( hr ) )
        {
            hr = pUnk->QueryInterface( IID_IMediaObject, (void **) &pCloned );
            HX_RELEASE(pUnk);
        }
    }


    // Copy the input and output types
    if (SUCCEEDED(hr))
    {
        DMO_MEDIA_TYPE mt;
        DWORD cInputStreams = 0;
        DWORD cOutputStreams = 0;
        GetStreamCount(&cInputStreams, &cOutputStreams);

        for (DWORD i = 0; i < cInputStreams && SUCCEEDED(hr); ++i)
        {
            hr = GetInputCurrentType(i, &mt);
            if (hr == DMO_E_TYPE_NOT_SET)
            {
                hr = S_OK; // great, don't need to set the cloned DMO
            }
            else if (SUCCEEDED(hr))
            {
                hr = pCloned->SetInputType(i, &mt, 0);
                MoFreeMediaType( &mt );
            }
        }

        for (DWORD i = 0; i < cOutputStreams && SUCCEEDED(hr); ++i)
        {
            hr = GetOutputCurrentType(i, &mt);
            if (hr == DMO_E_TYPE_NOT_SET)
            {
                hr = S_OK; // great, don't need to set the cloned DMO
            }
            else if (SUCCEEDED(hr))
            {
                hr = pCloned->SetOutputType(i, &mt, 0);
                MoFreeMediaType( &mt );
            }
        }

        if (SUCCEEDED(hr))
        {
            hr = pCloned->QueryInterface(IID_IMediaObjectInPlace, (void**)ppMediaObject);
        }

        // Release the object's original ref.  If clone succeeded (made it through QI) then returned pointer
        // has one ref.  If we failed, refs drop to zero, freeing the object.
        HX_RELEASE(pCloned);
    }

    // Something went wrong, clean up for client
    if (FAILED(hr))
    {
        delete pNewHXAudioDeviceHook;
    }

    return hr;
}
void dmo_GetOutputType_decoder_inset_(REFGUID clsidEnc, REFGUID clsidDec, REFGUID guidRaw, const vector<GUID> &expected)
{
	HRESULT hr;
	IMediaObject *pObj;
	vector<GUID> outTypes;
	DMO_MEDIA_TYPE mt;
	VIDEOINFOHEADER *pvih;

	DWORD fccIn = DirectShowFormatToVCMFormat(guidRaw);

	hr = CoCreateInstance(clsidEnc, NULL, CLSCTX_INPROC_SERVER, IID_IMediaObject, (LPVOID*)&pObj);
	BOOST_REQUIRE(hr == S_OK);
	BOOST_REQUIRE(pObj != NULL);

	memset(&mt, 0, sizeof(mt));
	MoInitMediaType(&mt, sizeof(VIDEOINFOHEADER));
	pvih = (VIDEOINFOHEADER*)mt.pbFormat;
	memset(pvih, 0, sizeof(VIDEOINFOHEADER));

	mt.majortype = MEDIATYPE_Video;
	mt.subtype = guidRaw;
	mt.bFixedSizeSamples = TRUE;
	mt.bTemporalCompression = FALSE;
	mt.lSampleSize = 10000000; /* XXX */
	mt.formattype = FORMAT_VideoInfo;
	pvih->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
	pvih->bmiHeader.biWidth = TEST_WIDTH;
	pvih->bmiHeader.biHeight = TEST_HEIGHT;
	pvih->bmiHeader.biPlanes = 1;
	pvih->bmiHeader.biBitCount = FCC2BitCount(fccIn);
	pvih->bmiHeader.biCompression = FCC2Compression(fccIn);
	pvih->bmiHeader.biSizeImage = 10000000; /* XXX */

	hr = pObj->SetInputType(0, &mt, 0);
	BOOST_REQUIRE(hr == S_OK);

	MoFreeMediaType(&mt);

	hr = pObj->GetOutputType(0, 0, &mt);
	BOOST_REQUIRE(hr == S_OK);

	pObj->Release();


	hr = CoCreateInstance(clsidDec, NULL, CLSCTX_INPROC_SERVER, IID_IMediaObject, (LPVOID*)&pObj);
	BOOST_REQUIRE(hr == S_OK);
	BOOST_REQUIRE(pObj != NULL);

	hr = pObj->SetInputType(0, &mt, 0);
	BOOST_REQUIRE(hr == S_OK);

	for (DWORD idx = 0; (hr = pObj->GetOutputType(0, idx, &mt)) == S_OK; ++idx)
	{
		BOOST_CHECK(mt.majortype == MEDIATYPE_Video);
		BOOST_CHECK(mt.bFixedSizeSamples == TRUE);
		BOOST_CHECK(mt.bTemporalCompression == FALSE);
		BOOST_CHECK(mt.formattype == FORMAT_VideoInfo);
		DWORD fccOut = DirectShowFormatToVCMFormat(mt.subtype);
		pvih = (VIDEOINFOHEADER*)mt.pbFormat;
		BOOST_CHECK(pvih->bmiHeader.biSize >= sizeof(BITMAPINFOHEADER));
		BOOST_CHECK(pvih->bmiHeader.biWidth == TEST_WIDTH);
		BOOST_CHECK(pvih->bmiHeader.biHeight == TEST_HEIGHT);
		BOOST_CHECK(pvih->bmiHeader.biPlanes == 1);
		BOOST_CHECK(pvih->bmiHeader.biBitCount == FCC2BitCount(fccOut));
		BOOST_CHECK(pvih->bmiHeader.biCompression == FCC2Compression(fccOut));
		outTypes.push_back(mt.subtype);
		MoFreeMediaType(&mt);
	}
	BOOST_CHECK(hr == DMO_E_NO_MORE_ITEMS);

	BOOST_CHECK_EQUAL(outTypes, expected);

	pObj->Release();
}