입력 조립기(input assembler : IA) 단계는 메모리에서 기하 자료(정점, 인덱스)를 읽어서 기하학적 기본 도형을 조립한다.
4가지 기능을 Get, Set 두 분류로 총 8개의 함수를 갖고 있다. PrimitiveTopology, InputLayout, VertexBuffer, IndexBuffer이다.
1.정점
정점(vertex)은 그저 기본도형(primitive)의 꼭짓점이라는 인상을 받는다. 하지만 Direct3D의 정점은 공간적 위치 이외의 정보도 담을 수 있으며, 이를 통해서 좀 더 복잡한 렌더링 효과를 낼 수 있다. 예를 들어 조명을 구현하기 위해 정점에 법선 벡터를 추가하여 구현할 수 있고, 텍스처를 적용하기 위해 정점에 텍스처 좌표를 추가할 수 있다.
Direct3D는 응용 프로그램이 정점의 성분들을 직접 정의할 수 있다.
2.기본도형 위상구조(primitive topology)
정점들은 정점 버퍼(Vertex Buffer)라고 하는 Direct3D 자료구조 안에 담겨서 렌더링 파이프라인에 묶인다. 정점 버퍼는 정점을 연속적인 메모리에 저장하는 자료구조이다. 정점 버퍼 자체는 그 정점들을 어떤 식으로 조합해서 기본도형을 형성할 것인지 알고 있지 않는다. 정점 버퍼가 기본도형의 정점이 형성하는 방식을 Direct3D에게 알려 주는 수단이 기본도형 위상구조(primitive topology)이다. 아래의 열거형은 d3dcommon.h에서 찾을 수 있다.
void ID3D11DeviceContext::IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY Topology);
typedef enum D3D_PRIMITIVE_TOPOLOGY
{
D3D_PRIMITIVE_TOPOLOGY_UNDEFINED = 0,
D3D_PRIMITIVE_TOPOLOGY_POINTLIST = 1,
D3D_PRIMITIVE_TOPOLOGY_LINELIST = 2,
D3D_PRIMITIVE_TOPOLOGY_LINESTRIP = 3,
D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST = 4,
D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP = 5,
D3D_PRIMITIVE_TOPOLOGY_LINELIST_ADJ = 10,
D3D_PRIMITIVE_TOPOLOGY_LINESTRIP_ADJ = 11,
D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST_ADJ = 12,
D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP_ADJ = 13,
D3D_PRIMITIVE_TOPOLOGY_1_CONTROL_POINT_PATCHLIST = 33,
D3D_PRIMITIVE_TOPOLOGY_2_CONTROL_POINT_PATCHLIST = 34,
D3D_PRIMITIVE_TOPOLOGY_3_CONTROL_POINT_PATCHLIST = 35,
D3D_PRIMITIVE_TOPOLOGY_4_CONTROL_POINT_PATCHLIST = 36,
D3D_PRIMITIVE_TOPOLOGY_5_CONTROL_POINT_PATCHLIST = 37,
D3D_PRIMITIVE_TOPOLOGY_6_CONTROL_POINT_PATCHLIST = 38,
D3D_PRIMITIVE_TOPOLOGY_7_CONTROL_POINT_PATCHLIST = 39,
D3D_PRIMITIVE_TOPOLOGY_8_CONTROL_POINT_PATCHLIST = 40,
D3D_PRIMITIVE_TOPOLOGY_9_CONTROL_POINT_PATCHLIST = 41,
D3D_PRIMITIVE_TOPOLOGY_10_CONTROL_POINT_PATCHLIST = 42,
D3D_PRIMITIVE_TOPOLOGY_11_CONTROL_POINT_PATCHLIST = 43,
D3D_PRIMITIVE_TOPOLOGY_12_CONTROL_POINT_PATCHLIST = 44,
D3D_PRIMITIVE_TOPOLOGY_13_CONTROL_POINT_PATCHLIST = 45,
D3D_PRIMITIVE_TOPOLOGY_14_CONTROL_POINT_PATCHLIST = 46,
D3D_PRIMITIVE_TOPOLOGY_15_CONTROL_POINT_PATCHLIST = 47,
D3D_PRIMITIVE_TOPOLOGY_16_CONTROL_POINT_PATCHLIST = 48,
D3D_PRIMITIVE_TOPOLOGY_17_CONTROL_POINT_PATCHLIST = 49,
D3D_PRIMITIVE_TOPOLOGY_18_CONTROL_POINT_PATCHLIST = 50,
D3D_PRIMITIVE_TOPOLOGY_19_CONTROL_POINT_PATCHLIST = 51,
D3D_PRIMITIVE_TOPOLOGY_20_CONTROL_POINT_PATCHLIST = 52,
D3D_PRIMITIVE_TOPOLOGY_21_CONTROL_POINT_PATCHLIST = 53,
D3D_PRIMITIVE_TOPOLOGY_22_CONTROL_POINT_PATCHLIST = 54,
D3D_PRIMITIVE_TOPOLOGY_23_CONTROL_POINT_PATCHLIST = 55,
D3D_PRIMITIVE_TOPOLOGY_24_CONTROL_POINT_PATCHLIST = 56,
D3D_PRIMITIVE_TOPOLOGY_25_CONTROL_POINT_PATCHLIST = 57,
D3D_PRIMITIVE_TOPOLOGY_26_CONTROL_POINT_PATCHLIST = 58,
D3D_PRIMITIVE_TOPOLOGY_27_CONTROL_POINT_PATCHLIST = 59,
D3D_PRIMITIVE_TOPOLOGY_28_CONTROL_POINT_PATCHLIST = 60,
D3D_PRIMITIVE_TOPOLOGY_29_CONTROL_POINT_PATCHLIST = 61,
D3D_PRIMITIVE_TOPOLOGY_30_CONTROL_POINT_PATCHLIST = 62,
D3D_PRIMITIVE_TOPOLOGY_31_CONTROL_POINT_PATCHLIST = 63,
D3D_PRIMITIVE_TOPOLOGY_32_CONTROL_POINT_PATCHLIST = 64
} D3D_PRIMITIVE_TOPOLOGY;
사실 메시든 도형이든 삼각형을 사용한다. 선을 쓴다면 쓸법하지만 포트폴리오가 FPS게임이 아니였기에 직선을 구현할 일이 없었다. 책에서도 주로 삼각형을 사용한다고 한다.
기본도형 위상구조 열거형들에 대해서 구분지어보자면 점, 선, 삼각형, 인접성 정보, 제어점 패치로 크게 5가지로 구분 지을 수 있다.
1.점
D3D_PRIMITIVE_TOPOLOGY_POINTLIST를 지정하면 점 목록(point list)이 적용된다. 기본도형 위상구조가 점 목록이면 모든 그리기 호출의 모든 정점은 개별적인 점으로 그려진다.

2.선
D3D_PRIMITIVE_TOPOLOGY_LINELIST과 D3D_PRIMITIVE_TOPOLOGY_LINESTRIP은 정점을 선분으로 그린다.
- D3D_PRIMITIVE_TOPOLOGY_LINELIST
그리기 호출의 매 정점 두 개가 개별적인 하나의 선분을 그린다. 2n개의 정점으로 n개의 선분이 만들어진다. - D3D_PRIMITIVE_TOPOLOGY_LINESTRIP
그리기 호출의 정점들이 차례로 이어서 일련의 선분들을 그린다. n개의 정점으로 n-1개의 선분이 만들어진다.
3.삼각형
D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST과 D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP은 정점으로 삼각형으로 그린다.
- D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST
그리기 호출의 매 정점 세 개가 하나의 개별적인 삼각형을 그린다. 3n개의 정점으로 n개의 삼각형이 만들어진다. - D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP
그리기 호출의 정점들을 인접한 인덱스의 정점들과 이어서 삼각형을 그린다. n개의 정점으로 n-2개의 삼각형이 만들어진다.

4.인접성 정보를 가진 기본도형
정점을 인접성(adjacency) 정보를 가진 형식으로 기하 셰이딩 알고리즘을 구현할 때 쓰인다. 기하 셰이더가 인접 정점에 접근하려면 인접한 정점들의 정보도 정점 버퍼와 인덱스 버퍼에 담아서 파이프라인에 제출해야 하며, D3D_PRIMITIVE_TOPOLOGY_LINELIST_ADJ, D3D_PRIMITIVE_TOPOLOGY_LINESTRIP_ADJ, D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST_ADJ, D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP_ADJ 중에 상황에 맞게 지정해야 한다. 인접 기본도형의 정점들은 오직 기하 셰이더의 입력으로만 쓰일 뿐, 실제로 그려지는 것은 아니다. 기하 셰이더가 아예 없는 경우에도 인접 기하도형을 그리지 않는다.

5.제어점 패치
D3D_PRIMITIVE_TOPOLOGY_N_CONTROL_POINT_PATCHLIST 위상구조는 정점 자료를 N개의 제어점들로 이루어진 패치 목록으로 해석해야 함을 뜻한다. 이 제어점 패치는 렌더링 기능의 테셀레이션 단계들에 쓰이는 것이다.
3.인덱스
수업에서 인덱스 버퍼라고 사용했던 것이다.
3차원 물체의 기본 구축 요소는 삼각형이다. 예를 들어 사각형 하나와 팔각형 하나를 D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST로 구현한다고 가정해보자.

이 도형을 정점 버퍼에 담는다면
Vertex quad[6] =
{
v0, v1, v2, //삼각형 0
v0, v2, v3, //삼각형 1
};
Vertex octagon[24] =
{
v0, v1, v2, //삼각형 0
v0, v2, v3, //삼각형 1
v0, v3, v4, //삼각형 2
v0, v4, v5, //삼각형 3
v0, v5, v6, //삼각형 4
v0, v6, v7, //삼각형 5
v0, v7, v8, //삼각형 6
v0, v8, v1, //삼각형 7
}
정점 버퍼의 정점은 위 코드처럼 구현할 것이다. 딱봐도 정점들의 중복이 많다는 것을 알 수 있다. 정점들의 중복이 바람직하지 않는 이유는 크게 두 가지이다.
- 메모리 요구량이 증가한다.
- 그래픽 하드웨어의 처리량이 증가한다.
중복을 방지하는 방법으로 D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP을 사용할 수 있지만 내가 써 봤을 때 이 방법은 머리가 좀 아프다. 정점이 계속 연결되어 있기 때문에 예상치도 못하게 나올 때가 종종 발생하기 때문이다.
D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST에서 중복 정점들을 제거하는 방법으로 인덱스(index)를 사용하는 것이다. 고유한 정점들로 정점 목록을 만들어 두고, 어떤 정점들을 어떤 순서로 사용해서 도형을 형성하는지는 그 정점들의 새깅ㄴ들을 적절히 나열함으로써 지정하는 것이다.
위 코드를 인덱스을 사용한다면
Vertex v[4] = { v0, v1,v2, v3 };
UINT indexList[6] =
{
0, 1, 2, //삼각형 0
0, 2, 3 //삼각형 1
};
Vertex v[9] = { v0, v1, v2, v3, v4, v5, v6, v7, v8 };
UINT indexList[24] =
{
0, 1, 2, //삼각형 0
0, 2, 3, //삼각형 1
0, 3, 4, //삼각형 2
0, 4, 5, //삼각형 3
0, 5, 6, //삼각형 4
0, 6, 7, //삼각형 5
0, 7, 8, //삼각형 6
0, 8, 1 //삼각형 7
};
그래픽 카드는 고유한 정점 목록의 고유한 정점들을 처리한 후, 인덱스 목록을 이용해서 정점들을 조합해 삼각형을 형성한다. 정점들에서 중복이 없어진 대신 인덱스들에 중복이 생겼지만 두 가지 이유로 큰 문제가 되지 않는다.
- 인덱스은 정수이므로 완전한 정점 구조체보다 적은 양의 메모리를 차지한다.
- 정점 캐시 순서가 좋은 경우 그래픽 하드웨어는 중복된 정점들을 자주 처리하지 않아도 된다.
'서적 정리 > DirectX11을 이용한 3D 게임 프로그래밍 입문' 카테고리의 다른 글
38.절단(clipping) (0) | 2022.01.25 |
---|---|
37.기하 셰이더(Geometry Shader : GS) 단계 (0) | 2022.01.25 |
36.테셀레이션(Tessellation) 단계 (0) | 2022.01.25 |
35.정점 셰이더(Vertex Shader : VS) 단계 (0) | 2022.01.23 |
33.렌더링 파이프라인의 개요 (0) | 2022.01.21 |
32.색상 표현의 기초 (0) | 2022.01.20 |
31.모형의 표현 (0) | 2022.01.20 |
30.3차원의 환상 (0) | 2022.01.20 |
댓글