728x90
🎨 렌더링 파이프라인
파이프라인이라는 것은 한 정점이 어떤 과정을 거쳐서 렌더링 될 수 있는지(그려지는지)를 나타낸 과정이다.
IA → VS → RS → PS → OM
🔸 IA (Input Assembly, 입력 조립)
- 렌더링 할 데이터를 집어넣는 과정으로 정점(Vertex Buffer)과 Primitive Topology 설정한다.
- GPU가 CPU로부터 정점 데이터를 전달 받아서 프리미티브(삼각형)들을 만든다.
- 정점 데이터를 CPU에서 GPU로 운반하기 위한 자료구조를 정점 버퍼(Vertex Buffer)라고 한다.
- 정점 버퍼는 Position, Normal, Color, UV 정보를 직렬화된 배열 형태로 담고 있다.
- GPU에서는 미리 전달받은 정점 버퍼의 정점들을 모아서 정점 데이터로 조립하는 것이 아닌, 삼각형과 같은 기본 도형(Primitive)로 조립해주기 때문에 입력 조립 단계라고 칭한다.
- 이렇게 조립된 프리미티브가 정점 쉐이더의 입력(Input)이 된다.
🔸 VS (Vertex Shader, 정점 쉐이더)
- 정점 데이터를 입력 받아 공간 변환을 수행한다.
- Object Space에서 Clip Space까지 정점들의 공간 변환을 수행한다.
🔀 공간변환
- 공간 변환은 각각 행렬 연산을 통해 이루어지는데, 변환 행렬은 Model(World), View, Projection 총 3가지이다.
- M, V, P는 변환 행렬의 이름이자, 변환 자체를 가리킨다.
✔ M (Model)
- 오브젝트 공간(Model Space, Object Space) -> 월드 공간(World Space)
- 각 오브젝트마다 자신의 피벗 위치를 원점(0, 0, 0)으로 하는 좌표 공간을 갖고 있다.
- 모델 변환은 각 오브젝트의 좌표 공간을 변환하여 하나의 월드 공간에 통합하는 과정이다.
- 이 과정에서 이동(Translate), 회전(Rotate), 크기(Scale)변환이 이루어진다.
- 이 세가지 변환은 각각 행렬을 통해 수행되고, 이를 하나의 행렬로 만든 것을 TRS 행렬이라고 한다.
- TRS 행렬은 좌측부터 우측으로 S, R, T 순서로 곱해진다.
✔ V (View)
- 월드 공간(World Space) -> 카메라 공간(View Space)
- 카메라 공간은 카메라의 위치가 원점(0, 0, 0)이고, 카메라가 바라보는 방향이 +Z축인 공간을 의미한다.
- 뷰 변환은 모든 오브젝트를 화면에 그려내기 쉽도록 카메라 기준으로 공간을 변환하는 과정이다.
- 언리얼과 DirectX의 좌표축은 다르기 때문에 헷갈리지 말자!
✔ P (Projection)
- 카메라 공간(View Space) -> 클립 공간(Clip Space)
- 카메라 기준의 정점 위치를 화면에 보이기 위한 정점 위치로 변환한다.
- 화면에 렌더링될 수 있는 영역을 나타내는 절두체(Frustum)가 정의된다.
- 절두체는 Near Clipping Plane, Far Clipping Plane, Field of View를 통해 정의한다.
- 절두체를 완전히 벗어나는 폴리곤들은 모두 버려지고 절두체의 경계에 걸쳐 있는 폴리곤들은 일단 유지한다.
- 원근감이 없는 직교 투영(Orthographic Projection) 또는 원근감이 있는 원근 투영(Perspective Projection)이 행해진다.
- 클립 공간의 좌표계는 사실 3D가 아닌 4D이다.
- 클립 공간의 모든 X, Y 좌표는 -1 ~ 1 범위에 존재하며, Z 좌표는 0 ~ 1 범위에 존재한다.
🔸 RS (Rasterizer, 래스터라이저)
- 3D 공간을 2D로 변환하는 것
- Clip Space의 정점 데이터를 Viewport로 변환하고, 정점 데이터를 기반으로 보간된 프래그먼트(픽셀 데이터)를 생성한다.
- 클립 스페이스의 정점 데이터를 전달받아 프래그먼트를 구성하고, 화면에 출력할 픽셀들을 찾아낸다.
- 픽셀 색상 등의 데이터는 정점의 데이터를 기준으로 보간된다.
- 프래그먼트(Fragnemt)?
- 픽셀 하나의 색상을 화면에 그려내기 위한 정보를 담고 있는 데이터
- 래스터라이저에서는 클립 스페이스 좌표의 모든 요소를 w값으로 나누면서 모든 원근법이 구현이 완료되며 이를 원근 분할이라고 한다.
- 원근 분할을 마친 좌표계가 바로 NDC 좌표계이다.
- 3D NDC 공간 상의 좌표를 2D 스크린 좌표로 변환하는 뷰포트 변환 과정을 수행한다.
- -1 ~ 1 범위였던 (x, y)좌표를 화면 해상도 범위로 변환한다.
🔸 PS (Pixel Shader, 픽셀 쉐이더)
- 변화된 공간을 Pixel 쉐이더로 처리하는 것
- 픽셀 쉐이더는 모델이 화면에서 차지하는 픽셀의 개수만큼 실행된다.
- 프래그먼트를 입력 받아 화면에 그려질 모든 픽셀의 색상과 깊이 값을 출력한다.
- 쉐이더를 통해 색상을 변화시키는 것은 모두 픽셀 쉐이더의 역할이라고 보면 된다.
- 투명도를 결정 하는 것도 픽셀 쉐이더, 라이팅과 그림자를 적용하는 것도 픽셀 쉐이더, 텍스쳐 색상을 메시에 입히는 것도 모두 픽셀 쉐이더에서 하는 역할이다.
- 픽셀 쉐이더는 각 픽셀들의 색상과 깊이 값을 출력으로 전달한다.
- 깊이 값은 Z-Buffer에, 색상 값은 Color Buffer에 저장된다.
- 그리고 이런 버퍼들을 통칭하여 스크린 버퍼(Screen Buffer)라고 한다.
🔸 OM (Output Merge, 출력 병합)
- 픽셀들을 화면에 출력하기 위한 마지막 연산들을 수행한다.
- Z-Test
- Stencil Test
- Alpha Blending
- 출력 병합 단계에서는 이렇게 겹치는 픽셀들을 연산 및 판단하여 픽셀의 최종적인 색상을 결정한다.
참조
https://rito15.github.io/posts/rendering-pipeline/
렌더링 파이프라인 간단 정리
렌더링 파이프라인 구조 요약(DirectX 9 기준)
rito15.github.io
728x90
'🎨DirectX' 카테고리의 다른 글
[DX] World행렬 (크기 변환 행렬) (0) | 2023.02.04 |
---|---|
[DX] 사각형 그리기, Index Buffer (0) | 2023.02.04 |
[DX] 컴퓨터 구조(CPU-RAM/GPU-VRAM), PrimitiveTopology (기본 도형 위상 구조) (0) | 2023.02.04 |
[DX] Shader Code, 쉐이더 기초 작성 (정점 출력 쉐이더 코드) (0) | 2023.02.04 |
[DX] 정점(Vertex), NDC좌표계 (0) | 2023.02.04 |