Search code examples
directx-11d3dxid3dxmeshdxut

Get ID3DXMesh from CDXUTSDKMesh


In a DirectX 11 demo application, I use a CDXUTSDKMesh for my static geometry. It is loaded and already displayed.

I'm doing some experiments related to Precomputed Radiance Transfer in this application. The ID3DXPRTEngine would be a pretty handy tool for the job. Unfortunately, D3DX and DXUT don't seem to be very compatible there.

ID3DXPRTEngine requires a single ID3DXMesh (multiple meshes can be concatenated with D3DXConcatenateMeshes no problem). Is there an easy way to 'convert' CDXUTSDKMesh to one or multiple ID3DXMesh instances?


Solution

  • Short Answer: No.

    Long answer: It can be done, but it requires that you be able to read the raw vertex data, convert it to the Direct3D 9 FVF system (the old fixed shader pipeline), and write the new data back.

    Basically what you're trying to do is inter-operate two different versions of the Direct3D API: version 9.0 and version 11.0. In order to do this, you need to do the following:

    1. Confirm your verticies contain no custom semantics (i.e. D3D11 allows a semantic like RANDOM_EYE_VEC, whereas D3D9 does not).

    2. Confirm you have the ability to read your vertex and face information into a byte buffer (i.e. a char pointer).

    3. Create a Direct3D 9 Device and a Direct3D 11 device.

    4. Open your mesh, pull the data into a byte buffer, and create an ID3DXMesh object from that data. If you have more than 2^16 faces, you will need to split the mesh into two or more meshes.

    5. Create the PRT Engine from the mesh(es), and run your PRT calculations.

    6. Read the new information from the mesh(es) using ID3DXBaseMesh::GetVertexBuffer() (not sure if this step is entirely correct as I've never actually used the PRT engine).

    7. Write the new data back into the CDXUTSDKMesh.

    As you may be able to tell, this process is long, prone to error, and very slow. If you're doing this for an offline tool, it may be OK, but if this is to be used in real time, you're probably better off writing your own PRT engine.

    Additionally, if your mesh has any custom semantics (i.e. you use a shader that expects some data that wasn't a part of the D3D9 world) then this algorithm will fail. The PRT engine uses the fixed function pipeline, so any new meshes that take advantage of D3D11 features that didn't exist back then are not going to work here.