Version: 2020.1
언어: 한국어
섀도우 캐스케이드
라이팅 창

그림자 문제 해결

그림자 성능

실시간 그림자는 렌더링 오버헤드가 상당히 높습니다. 그림자를 드리울 수 있는 모든 게임 오브젝트는 먼저 섀도우 맵으로 렌더링됩니다. 그런 다음 해당 맵을 사용하여 그림자를 받을 수 있는 오브젝트를 렌더링합니다.

소프트 섀도우는 하드 섀도우보다 렌더링하는 데 리소스가 더 많이 사용되지만, GPU에만 영향을 미치고 추가 CPU 작업은 많이 유발하지 않습니다.

섀도우 애크니

광원이 직접 비춘 표면은 종종 그림자에 부분적으로 표시될 수 있습니다. 섀도우 맵에서 지정된 거리에 정확하게 존재해야 하는 픽셀이 종종 멀리 있는 것으로 간주되기 때문입니다(섀도우 맵에 저해상도 이미지나 섀도우 필터링을 사용한 결과입니다). 그 결과 비춰질 때 그림자에서 임의 패턴의 픽셀들이 나타나며 “섀도우 애크니”로 알려진 시각적 효과가 발생합니다.

잘못된 자체 그림자 결함의 섀도우 애크니
잘못된 자체 그림자 결함의 섀도우 애크니

Bias 프로퍼티

섀도우 애크니를 방지하기 위해 섀도우 맵에 Bias 값을 거리에 추가하여 경계선의 픽셀이 통과해야 하는 비교를 명확하게 하거나 섀도우 맵에 렌더링할 때 노멀을 따라 게임 오브젝트를 일부 삽입하도록 할 수 있습니다. 이 값들은 그림자가 활성화될 때 광원 인스펙터 창의 BiasNormal Bias 프로퍼티에 의해 설정됩니다.

경우에 따라 그림자를 캐스트하는 게임 오브젝트 근처에 그림자 주변 영역이 잘못 비춰지므로 Bias 값을 너무 높게 설정하지 말아야 합니다. 이렇게 하면 그림자가 분리되어 게임 오브젝트가 지면 위를 나는 것처럼 보이게 됩니다.

높은 Bias 값은 그림자가 게임 오브젝트에서 떨어진 것처럼 보이게 합니다.
높은 Bias 값은 그림자가 게임 오브젝트에서 “떨어진” 것처럼 보이게 합니다.

이와 유사하게, Normal Bias 값이 너무 높게 설정되면 게임 오브젝트의 그림자가 매우 좁게 표시됩니다.

높은 Normal Bias 값은 그림자 형태를 매우 좁게 만듭니다.
높은 Normal Bias 값은 그림자 형태를 매우 좁게 만듭니다.

경우에 따라 Normal Bias 로 인해 근처 지오메트리의 광원이 그림자가 캐스트되어야 하는 영역으로 번지는 “광원 번짐”이라 불리는 효과가 발생할 수 있습니다. 잠재적인 해결 방법은 게임 오브젝트의 메시 렌더러를 열고 Cast Shadows 프로퍼티를 Two Sided 로 변경합니다. 이 방법은 도움이 될 수도 있지만 더 많은 리소스가 필요하고, 씬을 렌더링할 때 성능 오버헤드가 증가할 수 있습니다.

원하지 않는 효과가 발생하지 않도록 하려면 광원용 바이어스 값을 미세 조정해야 합니다. 일반적으로 계산하기 보다 눈대중으로 적절한 값을 찾는 편이 더 수월합니다.

올바른 그림자 사용
올바른 그림자 사용

섀도우 팬케이킹

섀도우 애크니를 더욱 줄이기 위해 Shadow pancaking 이라는 기법이 사용됩니다. 이 기법은 광원의 방향과 나란히 섀도우 맵을 렌더링할 때 사용되는 광원 공백의 범위를 줄인다는 개념에 바탕을 두고 있습니다. 이렇게 하면 섀도우 맵의 정밀도가 높아져 섀도우 결함이 감소합니다.

섀도우 팬케이킹 원리를 나타내는 다이어그램
섀도우 팬케이킹 원리를 나타내는 다이어그램

위 다이어그램에서

  • 하늘색 동그라미는 섀도우 캐스터를 나타냅니다.
  • 파란색 사각형은 원래 광원 공백을 나타냅니다.
  • 초록색 선은 최적화된 근접 평면을 나타냅니다(뷰 절두체에서 보이지 않는 섀도우 캐스터 제외).

섀도우 캐스터를 최적화된 공백(버텍스 셰이더 내)의 근접 클립 평면에 고정시켜야 합니다. 이 방법은 일반적으로 효과적이지만, 근접 클립 평면을 지나는 매우 큰 삼각형에 결함이 생길 수 있습니다.

큰 삼각형 문제
큰 삼각형 문제

사례에서는 파란색 삼각형의 버텍스 하나만 근접 클립 평면 뒤에 있고 이 평면에 고정됩니다. 하지만 이렇게 하면 삼각형 모양이 변하여 올바르지 않은 섀도우가 생길 수 있습니다.

Quality 창에서 Shadow Near Plane Offset 프로퍼티를 미세 조정하여 이 문제를 방지할 수 있습니다. 이렇게 하면 근접 클립 평면이 뒤로 당겨집니다. 하지만 이 값을 매우 높게 설정하면 섀도우 맵이 광원 방향에서 처리해야 하는 범위가 증가하기 때문에 결국에는 섀도우 애크니가 발생합니다. 그 대신 그림자를 드리우는 문제가 있는 삼각형을 바둑판 모양으로 만들 수도 있습니다.

그림자가 나타나지 않음

하나 이상의 오브젝트가 그림자를 캐스트하지 않는다면 다음 사항을 확인해야 합니다.

  • Quality 창에서 실시간 그림자를 완전히 비활성화할 수 있습니다. 정확한 품질 레벨이 활성화되었고 해당 설정에서 그림자가 켜졌는지 확인해야 합니다.

  • 씬의 모든 메시 렌더러그림자 받기(Receive Shadows)그림자 드리우기(Cast Shadows) 를 올바르게 설정해야 합니다 둘 모두 기본적으로 활성화되어 있지만 의도치 않게 비활성화되지 않았는지 확인해야 합니다.

  • 불투명한 오브젝트만 그림자를 캐스트하고 받기 때문에 빌트인 투명 또는 파티클 셰이더를 사용하는 오브젝트는 그림자를 캐스트하거나 받지 않습니다. 일반적으로 펜스, 초목처럼 틈이 있는 오브젝트 대신 투명 컷아웃 셰이더를 사용할 수 있습니다. 커스텀 셰이더는 픽셀에서 조명을 받고 지오메트리 렌더 대기열을 사용해야 합니다.

  • 버텍스 릿(VertexLit) 셰이더를 사용하는 오브젝트는 그림자를 받을 수 없지만 캐스트할 수는 있습니다.

  • Unity는 “언릿” 타입 셰이더가 포함된 머티리얼이 있는 게임 오브젝트에 대해서는 그림자를 계산하지 않습니다. Unity는 조명을 지원하는 셰이더가 포함된 머티리얼의 그림자만 계산할 수 있습니다.

  • 빌트인 렌더 파이프라인의 포워드 렌더링 경로에서 일부 셰이더를 사용하는 경우(특히 4.x 버전 이후의 Unity 레거시 빌트인 셰이더를 사용하는 경우) 가장 밝은 방향 광원만 그림자를 캐스트할 수 있습니다. 그림자를 캐스트하는 광원을 하나 이상 원하는 경우, 디퍼드 셰이딩 렌더링 경로를 대신 사용해야 합니다. fullforwardshadows 표면 셰이더 명령을 사용하여 직접 작성한 셰이더가 “전체 그림자”를 지원하게 설정할 수 있습니다.

섀도우 캐스케이드
라이팅 창