双指针函数参数和CComPtr

Double pointer function argument and CComPtr

本文关键字:CComPtr 参数 函数 指针      更新时间:2023-10-16

我不确定在函数内部使用CComPtr的这种方式,该函数的参数表示为双指针:

HRESULT D3DPresentEngine::CreateD3DSample(
    IDirect3DSwapChain9 *pSwapChain, 
    IMFSample **ppVideoSample
    )
{
    // Caller holds the object lock.
    D3DCOLOR clrBlack = D3DCOLOR_ARGB(0xFF, 0x00, 0x00, 0x00);
    CComPtr< IDirect3DSurface9 > pSurface;
    CComPtr< IMFSample > pSample;
    // Get the back buffer surface.
    ReturnIfFail( pSwapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &pSurface ) );
    // Fill it with black.
    ReturnIfFail( m_pDevice->ColorFill(pSurface, NULL, clrBlack));
    // Create the sample.
    ReturnIfFail( MFCreateVideoSampleFromSurface(pSurface, &pSample));
    // Return the pointer to the caller.
    *ppVideoSample = pSample;
    (*ppVideoSample)->AddRef();
    return S_OK;
}

我对最后一个赋值+ AddRef调用有疑问。

它们适合你吗?

Thanks in advance

可以,但可以简化:

HRESULT D3DPresentEngine::CreateD3DSample(
    IDirect3DSwapChain9 *pSwapChain, 
    IMFSample **ppVideoSample
    )
{
    // Caller holds the object lock.
    D3DCOLOR clrBlack = D3DCOLOR_ARGB(0xFF, 0x00, 0x00, 0x00);
    CComPtr< IDirect3DSurface9 > pSurface;
    // Get the back buffer surface.
    ReturnIfFail( pSwapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &pSurface ) );
    // Fill it with black.
    ReturnIfFail( m_pDevice->ColorFill(pSurface, NULL, clrBlack));
    // Create the sample.
    ReturnIfFail( MFCreateVideoSampleFromSurface(pSurface, ppVideoSample));
    return S_OK;
}

在你的代码中,AddRef是必要的,因为当pSample超出作用域时,它会替换Release

更习惯的版本是

// Transfer the pointer to our caller.
*ppVideoSample = pSample.Detach();

如果你想复制语义而不是传输,你可以使用

pSample.CopyTo(ppVideoSample);

AddRef()的赋值解引用是正确的

当调用MFCreateVideoSampleFromSurface()时,它的第二个参数是指向接口的指针应该存储的位置。使用&pSample获取要传递给函数的地址。这与所需的IMFSample **类型匹配。注意,通过CComPtrBase<>CComPtr<>执行&运算符返回正确的类型。

CComPtrBase::,operator @ MSDN

ppVideoSample也是类型IMFSample **,这需要*操作符对接口指针解引用。这将产生一个类型为IMFSample *的指针,您可以使用->操作符调用它来访问AddRef()和接口上的其他函数。