The DirectX SDK comes with quite a few nice samples, neatly organized in a sample browser. Quoting the documentation from the OptimizedMesh sample:
This OptimizedMesh Sample sample demonstrates the different types of meshes D3DX can load and optimize, as well as the different types of underlying primitives it can render. An optimized mesh has its vertices and faces reordered so that rendering performance can be improved.
Sadly, it turns out the code as is cannot load meshes with more than 64K vertices (much less optimize them). Now I’m sure somewhere in the SDK a disclaimer is buried, saying there’s no warranty, this isn’t production code, the usual yadda yadda. Still , seemed to me like optimizing meshes is a topic that is of interest mostly to an audience dealing with large meshes (certainly I was), so this really deserves a fix.
The sample browser comes with neat ‘feedback’ links, and I did communicate this to MS a while ago. They never did get back to me, so I thought someone out there might benefit from the fix online.
In the main source file, OptimizedMesh.cpp, make the following addition:
... // Load the mesh from the specified file hr = D3DXLoadMeshFromX( strMesh, D3DXMESH_SYSTEMMEM, pd3dDevice, ppAdjacencyBuffer, &pD3DXMtrlBuffer, NULL, &g_dwNumMaterials, &pMeshSysMem ); if( FAILED( hr ) ) goto End; if(pMeshSysMem->GetOptions() && D3DXMESH_32BIT) g_dwMemoryOptions |= D3DXMESH_32BIT; // Get the array of materials out of the returned buffer, and allocate a texture array d3dxMaterials = (D3DXMATERIAL*) pD3DXMtrlBuffer->GetBufferPointer(); ...
In a nutshell, the culprit is a tragic legacy of DirectX mesh files: by default, meshes allocate only 16 bit for a vertex index in the stored index buffer. Thus, meshes with more than 2^16 vertices require some explicit treatment – as listed here.