직교 투영
투영 시 깊이 값에 따라 물체의 비율이 정해지지 않고,
고정된 비율을 가지고 투영시키는 것
2d 게임이나, 3d 게임의 2d UI로 사용 시 필요
window
height: h
width: w
z
far: f
near: n
=>
x: 2x / w
y: 2y / h
z: (z - n) / (f - n)
hlsl 컴파일러
비주얼 스튜디오 프로젝트에 fx나 hlsl 파일이 있을 경우
hlsl 컴파일러를 사용하여 쉐이더 문법 오류를 알 수 있음
기본적으로 UI를 찍는 직교 투영 카메라와
유저가 바라보는 게임 화면을 찍는 원근 투영 카메라 두 대를 이용하여
두 장면을 합성한다.
유니티에서는 UI 레이어를 가진 객체만 직교 투영 카메라가 찍게 된다.
임시적으로 Scene manager에서 layer들을 관리
gameObject 클래스에는 자신이 가질 layer를 구현
void Camera::FinalUpdate()
{
...
if (_type == PROJECTION_TYPE::PERSPECTIVE)
_matProjection = ::XMMatrixPerspectiveFovLH(_fov, width / height, _near, _far);
else
_matProjection = ::XMMatrixOrthographicLH(width * _scale, height * _scale, _near, _far);
...
}
void Camera::Render()
{
...
for (auto& gameObject : gameObjects)
{
...
if (IsCulled(gameObject->GetLayerIndex()))
continue;
...
gameObject->GetMeshRenderer()->Render();
}
}
camera 클래스에는 자신의 투영 타입을 설정하고 자신이 찍을 layer를 검사하도록 구현
shared_ptr<Scene> SceneManager::LoadTestScene()
{
...
{// UI camera
shared_ptr<GameObject> camera = make_shared<GameObject>();
...
camera->GetCamera()->SetProjectionType(PROJECTION_TYPE::ORTHOGRAPHIC);
uint8 layerIndex = GET_SINGLE(SceneManager)->LayerNameToIndex(L"UI");
camera->GetCamera()->SetCullingMaskAll();
camera->GetCamera()->SetCullingMaskLayerOnOff(layerIndex, false);
scene->AddGameObject(camera);
}
{// UI retangle
shared_ptr<GameObject> sphere = make_shared<GameObject>();
sphere->SetLayerIndex(GET_SINGLE(SceneManager)->LayerNameToIndex(L"UI"));
...
{
shared_ptr<Mesh> mesh = GET_SINGLE(Resources)->LoadRectangleMesh();
meshRenderer->SetMesh(mesh);
}
...
}
...
}
UI용 카메라는 UI 레이어를 가진 물체만을 투영하도록 설정하고
UI로 사용할 객체는 레이어를 UI로 설정
Swap Chain에서 사용하는 render target view buffer는 하나이기 때문에
카메라마다 렌더한 정보가 버퍼를 계속 덮어쓰게 됨