Reputation: 461
Im trying to gain access to my applications Vertex Buffers (and there vertices) using the below method:
//access vertex buffers
UINT* Stride = new UINT[32];
UINT* veBufferOffset = new UINT[32];
ID3D11Buffer** veBuffer = new ID3D11Buffer * [32];
pContext->IAGetVertexBuffers(0, 32, veBuffer, Stride, veBufferOffset);
std::ostream& operator<<(std::ostream & out, const ID3D11Buffer& buff); // my attempt at overloading...
for (int i = 0; i < 32; i++)
{
ID3D11Buffer* buff = veBuffer[i];
for (int e = 0; e < 50; e++) {
out << buff[e] << std::endl;
return out;
}
}
I can loop through veBuffer no problem, however I haven't had any success in gaining access to the vertices (buff[e]). I have done quite a bit of reading on this, and I'm still not entirely sure where to go from here.
I'm also aware of what can be done using the Stream Output stage: https://learn.microsoft.com/en-us/windows/win32/direct3d11/d3d10-graphics-programming-guide-output-stream-stage?redirectedfrom=MSDN
Where it states that you can get vertex Buffers from the Geometry Shader. From what I understand though, the Geometry Shader is fed one primitive (triangle or a line) at a time. Where I'm looking to get buffers per model.
I found this article on reading back data from the GPU: https://learn.microsoft.com/en-us/windows/win32/direct3d12/readback-data-using-heaps
Unfortunatley for me, it's for DirectX 12. Is there an equivalent DirectX 11 method?
Upvotes: 1
Views: 1751
Reputation: 21956
Here’s one way to do that.
Get the ID3D11Buffer
pointer like you’re doing. Ideally use something like std::vector<CComPtr<ID3D11Buffer>>
instead of new/delete but that’s not too important, at least not for small projects.
Call ID3D11Buffer::GetDesc
to get size and other parameters of the buffer you wanna read.
Adjust the description of the buffer, set usage to D3D11_USAGE_STAGING
, bind flags to zero, and CPU access flags to D3D11_CPU_ACCESS_READ
.
Create another temporary buffer using the modified description, by calling ID3D11Device::CreateBuffer
. Don’t specify initial data, pass nullptr
there.
Copy the source buffer into the newly created temporary one, by calling ID3D11DeviceContext::CopyResource
Now you can use ID3D11DeviceContext::Map/Unmap to read vertex data from the temporary buffer you created on step 4.
P.S. If you wanna read back index buffer, or any other resource type really, the workflow is the same: create a temporary staging resource, copy, and read from the staging resource.
Upvotes: 3