这里是SunshineBooming,GPU公司一枚小小的Driver工程师,主要工作是写DirectX12 Driver,我会持续更新这个DX12 Spec系列,可能比较冷门,但是都是干货和工作中的心得体会,有任何GPU相关的问题都可以在评论区互动,知无不言:
DirectX12 Spec 总目录
目录
- 1. 什么是IA?
- 2. IA如何工作?
- 2.1 Vertex Buffer & VBV
- 2.2 Index Buffer & IBV
1. 什么是IA?
- IA全称Input Assembly,是整个渲染管线的入口。IA阶段会从显存中读取几何数据,包括Vertex Data和Index Data,再将它们装配成几何图元(Geometric Primitive)(例如Triangle和Line这种构成图形的基本元素)。
- DirectX12整个渲染管线主要包括IA、VS、HS、TS、DS、GS(STO)、RS、PS、OM。
- IA即是整个渲染管线的入口,负责将渲染所需要的Vertex Buffer和Index Buffer中的数据给到管线中,然后经过各个渲染阶段,最后渲染好的数据从OM输出到Render Targets,也可以直接从STO输出所需要的数据。
2. IA如何工作?
- 关于IA的工作流程,需要关心以下几点:Vertex Buffer & VBV、Index Buffer & IBV、Input Layout以及Primitive Topology这几点,接下来我分别阐述各个点的细节。
2.1 Vertex Buffer & VBV
- 几何图形一般是由Triangle和Line这两种基本元素构成的,而Triangle和Line这两种基本元素都可以用Vertex的集合来表示,例如Triangle可以用3个Vertex的集合表示,同理Line可以用2个表示。
- 所以在DirectX12的IA阶段,用户输入Vertex Data,然后指定图元拓扑结构(Primitive Topology),在IA中就可以将这些数据装配成几何图形。
- 例如一个Triangle图形,由Ver0、Ver1、Ver2三个Vertex构成,我们就可以将每个Vertex的属性抽象成MyVertex结构体,然后把整个Vertex数据Copy到事先创建好的Vertex Buffer中:
// 自定义Vertex结构体
struct MyVertex
{
XMFLOAT3 Pos;
XMFLOAT4 Color;
}
// 自定义Ver0/1/2数据
Vertex vertices[] =
{
// Ver0
{ XMFLOAT3(0.0f, 0.0f, 0.0f), XMFLOAT4(Colors::Red) },
// Ver1
{ XMFLOAT3(1.0f, 1.0f, 0.0f), XMFLOAT4(Colors::Blue) },
// Ver2
{ XMFLOAT3(2.0f, 0.0f, 0.0f), XMFLOAT4(Colors::Yellow) },
};
// 创建好Vertex Buffer Resource, 并将vertices中的数据copy到VertexBuffer中
ComPtr<ID3D12Resource> VertexBuffer = ...
// 调用IASetVertexBuffers()设置Vertex Buffer
IASetVertexBuffers()
- 拿到Vertex Buffer之后,我们不能直接将它传给IA Stage,因为GPU不知道怎样去解析这段数据,这就要用到我们之前说的Descriptor的概念,我们将Vertex Buffer封装成VBV(Vertex Buffer View),将其指定到IA中,GPU就能按照我们指定的参数解析Vertex Buffer Data:
// VBV结构体参数
typedef struct D3D12_VERTEX_BUFFER_VIEW {
D3D12_GPU_VIRTUAL_ADDRESS BufferLocation;
UINT SizeInBytes;
UINT StrideInBytes;
} D3D12_VERTEX_BUFFER_VIEW;
// 结合我们前面定义的MyVertex结构体,我们可以这样填写VBV参数
D3D12_VERTEX_BUFFER_VIEW vbv = { 0 };
vbv.BufferLocation = VertexBuffer->GetGPUVirtualAddress();
vbv.StrideInBytes = sizeof(MyVertex);
vbv.SizeInBytes = 3 * sizeof(MyVertex);
// 最后我们可以把填写好的VBV指定到IA中,其包含了Vertex Buffer的所有信息
D3D12_VERTEX_BUFFER_VIEW vbvArray[1] = { vbv };
IASetVertexBuffers(0, 1, vbvArray);
- 当然以上流程只是说了个大概,还有许多DX12编程方面的细节没有提及,暂且不关心,目前只描述思路。
2.2 Index Buffer & IBV
- 未完待续