Cross-API Rendering: An Aside
14 Oct
Written By Roderick Kennedy
Just as an aside, an insight into why I need to wrapper-up some perfectly serviceable rendering API's. Suppose I want to create a structured buffer to be used in a compute shader, for both read-only and read-write usage.
Here's how I want to declare it:
simul::crossplatform::StructuredBuffer tempBuffer;
Here's how I'd like to initialize it:
tempBuffer.RestoreDeviceObjects(renderPlatform,num_elements,true);
- where passing "true" in the third element means "make it writeable by compute shaders".
Now in DirectX 11, I'd declare it like this:
ID3D11Buffer *pBuffer_Tmp; ID3D11UnorderedAccessView *pUAV_Tmp; ID3D11ShaderResourceView *pSRV_Tmp;
And initialize it like so (get ready):
D3D11_BUFFER_DESC buf_desc; buf_desc.ByteWidth = sizeof(float) * 2 * num_elements; buf_desc.Usage = D3D11_USAGE_DEFAULT; buf_desc.BindFlags = D3D11_BIND_UNORDERED_ACCESS | D3D11_BIND_SHADER_RESOURCE; buf_desc.CPUAccessFlags = 0; buf_desc.MiscFlags = D3D11_RESOURCE_MISC_BUFFER_STRUCTURED; buf_desc.StructureByteStride = sizeof(float) * 2;
renderPlatform->AsD3D11Device()->CreateBuffer(&buf_desc, NULL, &pBuffer_Tmp); assert(pBuffer_Tmp);
// Temp undordered access view D3D11_UNORDERED_ACCESS_VIEW_DESC uav_desc; uav_desc.Format = DXGI_FORMAT_UNKNOWN; uav_desc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; uav_desc.Buffer.FirstElement = 0; uav_desc.Buffer.NumElements =num_elements; uav_desc.Buffer.Flags = 0;
renderPlatform->AsD3D11Device()->CreateUnorderedAccessView(pBuffer_Tmp, &uav_desc, &pUAV_Tmp);
// Temp shader resource view D3D11_SHADER_RESOURCE_VIEW_DESC srv_desc; srv_desc.Format = DXGI_FORMAT_UNKNOWN; srv_desc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER; srv_desc.Buffer.FirstElement = 0; srv_desc.Buffer.NumElements =num_elements;
renderPlatform->AsD3D11Device()->CreateShaderResourceView(pBuffer_Tmp, &srv_desc, &pSRV_Tmp);
So, that was a bit longer; with a lot of redundant "match-up" values - you can't create an unordered access view of pBuffer_Tmp unless it was created with BindFlags containing D3D11_BIND_UNORDERED_ACCESS, for example. Now I know you can do clever things like create a view into a specific part of a buffer, and so on, but let's at least make a neat interface for the 99% case.
Update (19/9/2021): see https://github.com/simul/Platform for full source code.

