例子见:Microsoft DirectX SDK basic compute11
shader代码:
-
struct BufType{ int i; float f;};StructuredBuffer
Buffer0 : register(t0);StructuredBuffer Buffer1 : register(t1);RWStructuredBuffer BufferOut : register(u0);[numthreads(1, 1, 1)]void CSMain( uint3 DTid : SV_DispatchThreadID ){ BufferOut[DTid.x].i = Buffer0[DTid.x].i + Buffer1[DTid.x].i; BufferOut[DTid.x].f = Buffer0[DTid.x].f + Buffer1[DTid.x].f;}
c++代码:
// 构造并初始化Buffer0和Buffer1; g_vBuf0和g_vBuf1为BufType数组,数量为Num_Elements = 1024 CreateStructuredBuffer( g_pDevice, sizeof(BufType), NUM_ELEMENTS, &g_vBuf0[0], &g_pBuf0 ); CreateStructuredBuffer( g_pDevice, sizeof(BufType), NUM_ELEMENTS, &g_vBuf1[0], &g_pBuf1 ); CreateStructuredBuffer( g_pDevice, sizeof(BufType), NUM_ELEMENTS, NULL, &g_pBufResult ); // 构造ShaderResourceView作为input buffer, UnorderedAccessView作为outputBuffer printf( "Creating buffer views..." ); CreateBufferSRV( g_pDevice, g_pBuf0, &g_pBuf0SRV ); CreateBufferSRV( g_pDevice, g_pBuf1, &g_pBuf1SRV ); CreateBufferUAV( g_pDevice, g_pBufResult, &g_pBufResultUAV ); // 设置deviceContext具体状态:g_pCS为computeShader指针 printf( "Running Compute Shader..." ); ID3D11ShaderResourceView* aRViews[2] = { g_pBuf0SRV, g_pBuf1SRV }; RunComputeShader( g_pContext, g_pCS, 2, aRViews, NULL, NULL, 0, g_pBufResultUAV, NUM_ELEMENTS, 1, 1 ); // 子函数 //-------------------------------------------------------------------------------------- // Create Structured Buffer //-------------------------------------------------------------------------------------- HRESULT CreateStructuredBuffer( ID3D11Device* pDevice, UINT uElementSize, UINT uCount, VOID* pInitData, ID3D11Buffer** ppBufOut ) { *ppBufOut = NULL; D3D11_BUFFER_DESC desc; ZeroMemory( &desc, sizeof(desc) ); desc.BindFlags = D3D11_BIND_UNORDERED_ACCESS | D3D11_BIND_SHADER_RESOURCE; desc.ByteWidth = uElementSize * uCount; desc.MiscFlags = D3D11_RESOURCE_MISC_BUFFER_STRUCTURED; desc.StructureByteStride = uElementSize; if ( pInitData ) { D3D11_SUBRESOURCE_DATA InitData; InitData.pSysMem = pInitData; return pDevice->CreateBuffer( &desc, &InitData, ppBufOut ); } else return pDevice->CreateBuffer( &desc, NULL, ppBufOut ); } //-------------------------------------------------------------------------------------- // Create Shader Resource View for Structured or Raw Buffers //-------------------------------------------------------------------------------------- HRESULT CreateBufferSRV( ID3D11Device* pDevice, ID3D11Buffer* pBuffer, ID3D11ShaderResourceView** ppSRVOut ) { D3D11_BUFFER_DESC descBuf; ZeroMemory( &descBuf, sizeof(descBuf) ); pBuffer->GetDesc( &descBuf ); D3D11_SHADER_RESOURCE_VIEW_DESC desc; ZeroMemory( &desc, sizeof(desc) ); desc.ViewDimension = D3D11_SRV_DIMENSION_BUFFEREX; desc.BufferEx.FirstElement = 0; if ( descBuf.MiscFlags & D3D11_RESOURCE_MISC_BUFFER_STRUCTURED ) { // This is a Structured Buffer desc.Format = DXGI_FORMAT_UNKNOWN; desc.BufferEx.NumElements = descBuf.ByteWidth / descBuf.StructureByteStride; } else { return E_INVALIDARG; } return pDevice->CreateShaderResourceView( pBuffer, &desc, ppSRVOut ); } //-------------------------------------------------------------------------------------- // Create Unordered Access View for Structured or Raw Buffers //-------------------------------------------------------------------------------------- HRESULT CreateBufferUAV( ID3D11Device* pDevice, ID3D11Buffer* pBuffer, ID3D11UnorderedAccessView** ppUAVOut ) { D3D11_BUFFER_DESC descBuf; ZeroMemory( &descBuf, sizeof(descBuf) ); pBuffer->GetDesc( &descBuf ); D3D11_UNORDERED_ACCESS_VIEW_DESC desc; ZeroMemory( &desc, sizeof(desc) ); desc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; desc.Buffer.FirstElement = 0; if ( descBuf.MiscFlags & D3D11_RESOURCE_MISC_BUFFER_STRUCTURED ) { // This is a Structured Buffer desc.Format = DXGI_FORMAT_UNKNOWN; // Format must be must be DXGI_FORMAT_UNKNOWN, when creating a View of a Structured Buffer desc.Buffer.NumElements = descBuf.ByteWidth / descBuf.StructureByteStride; } else { return E_INVALIDARG; } return pDevice->CreateUnorderedAccessView( pBuffer, &desc, ppUAVOut ); } //-------------------------------------------------------------------------------------- // Run CS //-------------------------------------------------------------------------------------- void RunComputeShader( ID3D11DeviceContext* pd3dImmediateContext, ID3D11ComputeShader* pComputeShader, UINT nNumViews, ID3D11ShaderResourceView** pShaderResourceViews, ID3D11Buffer* pCBCS, void* pCSData, DWORD dwNumDataBytes, ID3D11UnorderedAccessView* pUnorderedAccessView, UINT X, UINT Y, UINT Z ) { pd3dImmediateContext->CSSetShader( pComputeShader, NULL, 0 ); pd3dImmediateContext->CSSetShaderResources( 0, nNumViews, pShaderResourceViews ); pd3dImmediateContext->CSSetUnorderedAccessViews( 0, 1, &pUnorderedAccessView, NULL ); pd3dImmediateContext->Dispatch( X, Y, Z ); // 通知显卡执行 pd3dImmediateContext->CSSetShader( NULL, NULL, 0 ); ID3D11UnorderedAccessView* ppUAViewNULL[1] = { NULL }; pd3dImmediateContext->CSSetUnorderedAccessViews( 0, 1, ppUAViewNULL, NULL ); ID3D11ShaderResourceView* ppSRVNULL[2] = { NULL, NULL }; pd3dImmediateContext->CSSetShaderResources( 0, 2, ppSRVNULL ); ID3D11Buffer* ppCBNULL[1] = { NULL }; pd3dImmediateContext->CSSetConstantBuffers( 0, 1, ppCBNULL ); }