在 Directx11 上实现硬件实例化

Implement hardware instancing on Directx11

本文关键字:硬件 实例化 实现 Directx11      更新时间:2023-10-16

我是Directx/3D编程的初学者。我需要有关在 Directx 11 上实现硬件实例化的帮助。我正在尝试在屏幕上渲染多个立方体,以创建某种 Minecraft 风格的体素引擎。问题是,我不知道从哪里开始实现这一目标。这是我的"渲染帧"函数的外观:

void RenderFrame(void)
{
D3DXMATRIX matView, matProjection;
D3DXMATRIX matFinal;
// create a view matrix
D3DXMatrixLookAtLH(&matView,
&D3DXVECTOR3(0.0f, 9.0f, 24.0f),   // the camera position
&D3DXVECTOR3(0.0f, 0.0f, 0.0f),    // the look-at position
&D3DXVECTOR3(0.0f, 1.0f, 0.0f));   // the up direction
// create a projection matrix
D3DXMatrixPerspectiveFovLH(&matProjection,
(FLOAT)D3DXToRadian(45),                    // field of view
(FLOAT)SCREEN_WIDTH / (FLOAT)SCREEN_HEIGHT, // aspect ratio
1.0f,                                       // near view-plane
100.0f);                                    // far view-plane
// create the final transform
matFinal = matView * matProjection;
// clear the back buffer to a deep blue
devcon->ClearRenderTargetView(backbuffer, D3DXCOLOR(0.0f, 0.2f, 0.4f, 1.0f));
// clear the depth buffer
devcon->ClearDepthStencilView(zbuffer, D3D11_CLEAR_DEPTH, 1.0f, 0);
// select which vertex buffer to display
UINT stride = sizeof(VERTEX);
UINT offset = 0;
devcon->IASetVertexBuffers(0, 1, &pVBuffer, &stride, &offset);
devcon->IASetIndexBuffer(pIBuffer, DXGI_FORMAT_R32_UINT, 0);
// select which primtive type we are using
devcon->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
// draw the Hypercraft
devcon->UpdateSubresource(pCBuffer, 0, 0, &matFinal, 0, 0);
devcon->DrawIndexed(24, 0, 0);
// switch the back buffer and the front buffer
swapchain->Present(0, 0);
}

请注意,有一个顶点缓冲区包含多维数据集的顶点,索引缓冲区包含其输入。我想在一次绘制调用中一次在屏幕上呈现许多 (5000+) 多维数据集,而不会出现性能问题,所以我知道实例化是要走的路,但我不知道如何在我的代码中实现它。我需要对代码进行哪些更改才能显示多维数据集的多个实例?

提前感谢!

DX11 中有几个步骤。 但这些是高级笔记。

您将需要更新顶点着色器
  1. 签名以包含其他实例字段,在我的头顶上,您基本上将它们设置为插槽 1 而不是 0,并以类似于创建顶点着色器顶点定义的方式对齐字节。 这里需要特别注意的是,如果你输入一个矩阵,你知道它的列还是行是主要的。
  2. 更新顶点着色器以反映您在签名中定义的其他实例字段。
  3. 将实例缓冲区设置为插槽 1 或您为实例定义的任何 n 值。 您设置的槽必须与您的定义匹配,这一点很重要。
  4. 从外观上看,您将需要调用DrawIndexInstanced,并传入实例计数。

注意:如果需要对齐多维数据集,请使用矩阵。 您将招致平局惩罚,不是在 CPU 端,而是在 GPU 上,这是它的正当生活。 但这是迄今为止最有效的通话方式。