래스터화기(1) - 렌더 상태

WanJu Kim·2022년 12월 29일

Direct3D

목록 보기
17/29

입력 조립기 단계에서 많이 봤듯이, 기본도형 위상구조, 입력 배치, 정점 버퍼, 색인 버퍼는 다른 것을 묶기전까지는 이전에 묶은 자료가 그대로 남아있다. 이와 비슷하게 다른 것들도 한 번 변경하기 전까지는 그대로 유지하는 것들이 있다. 그런 렌더링 파이프라인의 특정 측면의 구성(configuration)에 쓰이는 관련 상태들을 '렌더 상태(render state)'라고 부르는 상태 집합으로 묶어서 관리한다. 다음은 그 대표 인터페이스들이다.

  1. ID3D11RasterizerState : 이 인터페이스는 파이프라인의 래스터화기 단계를 구성하는 데 쓰이는 설정들을 묶은 상태 집합을 대표한다.
  2. ID3D11BlendState : 이 인터페이스는 혼합 연산을 구성하는 데 쓰이는 상태 집합을 대표한다.
  3. ID3D11DepthStencilState : 이 인터페이스는 깊이 판정과 스텐실 판정을 구성하는 데 쓰이는 상태 집합을 대표한다.

지금 관심있는 것은 1번이다. 2,3 번은 고급 기술이기 때문이다. 이 인터페이스를 생성하는 메서드는 다음과 같다.

HRESULT ID3D11Device::CreateRasterizerState(
	const D3D11_RASTERIZER_DESC *pRasterizerDesc,
    ID3D11RasterizerState **ppRasterizerState);

제1 매개변수는 생성하고자 하는 래스터화기 상태 집합을 서술하는 구조체이고, 제2 매개변수는 생성된 인터페이스를 가리키는 포인터이다.

D3D11_RASTERIZER_DESC 구조체의 정의는 다음과 같다.

struct D3D11_RASTERIZER_DESC {
	D3D11_FILL_MODE FillMode;	// 기본 값 : D3D11_FILL_SOLID.
    D3D11_CULL_MODE CullMode;	// 기본 값 : D3D11_CULL_BACK.
    BOOL FrontCounterClockwise;	// 기본 값 : false.
    INT DepthBias;				// 기본 값 : 0.
    FLOAT DepthBiasClamp;		// 기본 값 : 0.0f.
    FLOAT SlopeScaledDepthBias;	// 기본 값 : 0.0f.
    BOOL DepthClipEnable;		// 기본 값 : false.
    BOOL ScissorEnable;			// 기본 값 : false.
    BOOL MultisampleEnable;		// 기본 값 : false.
    BOOL AntialiasedLineEnable;	// 기본 값 : false.

왜 이런 식으로 모아뒀는지 아는가? 잘 안 쓰기 때문이다. 그래서 처음 세 개만 설명한다.

  1. FillMode : 와이어프레임 렌더링인 경우 D3D11_FILL_WIREFRAME을, 고형체(solid) 렌더링인 경우에는 D3D11_FILL_SOLID를 지정한다. 와이어프레임 렌더링이랑 면이 채워지지 않고 선만 그려진 것을 말한다.
  2. CullMode : 선별을 비활성화할면 D3D11_CULL_NONE을, 후면 삼각형을 선별해서 제외시키려면 D3D11_CULL_BACK을, 전면 삼각형을 선별 제외하면 D3D11_CULL_FRONT를 지정한다.
  3. FrontCounterClockwise : 시계방향으로 감긴 삼각형을 전면으로 간주하고 반시계방향으로 감긴 삼각형을 후면으로 간주하려면 false를 지정한다. 반시계방향으로 감긴 삼각형을 전면으로 간주하고 시계방향으로 감긴 삼각형을 후면으로 간주하려면 true를 지정한다.

ID3D11RasterizerState 객체를 생성했다면, 다음과 같은 호출을 통해서 장치의 새 상태 집합을 설정할 수 있다.

void ID3D11DeviceContext::RSSetState(
	ID3D11RasterizerState *pRasterizerState);

다음은 예시다.


D3D11_RASTERIZER_DESC rsDesc;
ZeroMemory(&rsDesc, sizeof(D3D11 RASTERIZER_DESC));	// 제1 매개변수를 제2 매개변수 크기만큼 초기화.
rsDesc.FillMode = D3D11_FILL_S0LID;
rsDesc.CullMode = D3D1l_CULL_NONE;
rsDesc.FrontCounterClockwise = false;
rsDesc.DepthClipEnable = true;

HR(md3dDevice->CreateRasterizerState(&rsDesc, &mNoCullRS));

특정 부분만 이 모드를 적용해서 그리고 싶다면 다음과 같은 방법으로 호출하면 된다.

ID3DllRasterizerState* mWireframeRS;
ID3DllRasterizerState* mSolidRS;

// 그리기 함수 안에서 렌더 상태 객체들을 번갈아 사용한다.
md3dImmediateContext->RSSetState(mSolidRS);
DrawObject();

md3dImmediateContext->RSSetState(mWireframeRS);
DrawObject();

만약 기본 기본 상태로 돌리고 싶다면 0으로 RSSetState를 호출하면 된다.

// 기본상태를복원한다.
md3dImmediateContext->RSSetState(0);
profile
Question, Think, Select

0개의 댓글