Version: 5.3
빌트인 셰이더 변수
GLSL Shader Programs

여러 셰이더 프로그램 배리언트 만들기

셰이더 코드 조각 대부분을 고정시키되 약간 다른 셰이더 “배리언트”가 생성될 수 있게 하면 편리합니다. 일반적으로 “메가 셰이더” 또는 “우버 셰이더”라고 하며, 각 경우마다 다른 프리프로세서 명령으로 셰이더 코드를 여러 번 컴파일할 수 있습니다.

Unity에서는 #pragma multi_compile 또는 #pragma shader_feature 명령을 셰이더 스니핏에 추가하여 이렇게 할 수 있습니다. 표면 셰이더에서도 가능합니다.

런타임 시 적절한 셰이더 배리언트는 머티리얼 키워드(Material.EnableKeyword 및 DisableKeyword) 또는 전역 셰이더 키워드(Shader.EnableKeyword 및 DisableKeyword)에서 선택됩니다.

multi\_compile 작동 방식

명령은 다음과 같습니다.

#pragma multi_compile FANCY_STUFF_OFF FANCY_STUFF_ON

하나는 FANCY_STUFF_OFF가 정의되고 다른 하나는 FANCY_STUFF_ON이 정의된 두 가지 셰이더 배리언트를 생성합니다. 머티리얼 및 전역 셰이더 키워드에 따라 런타임 시점에 둘 중 하나가 활성화됩니다. 두 키워드가 모두 활성화되지 않는 경우 전자(“off”)가 사용됩니다.

multi\_compile 줄에 키워드가 두 개보다 많을 수 있습니다. 예를 들어, 다음은 네 가지 셰이더 배리언트를 생성합니다.

#pragma multi_compile SIMPLE_SHADING BETTER_SHADING GOOD_SHADING BEST_SHADING

모두 밑줄 처리된 이름이 있으면 프리프로세서 매크로가 정의되지 않은 셰이더 배리언트가 생성됩니다. 이 배리언트는 일반적으로 셰이더 기능에 사용하여 키워드 2개를 모두 소진하는 것을 방지합니다(키워드 제한에 대한 아래 참고 사항 참조). 예를 들어, 다음은 셰이더 배리언트를 아무 것도 정의되지 않은 것과 FOO_ON이 정의된 것을 하나씩 포함해 총 2개 생성하는 명령입니다.

#pragma multi_compile __ FOO_ON

shader\feature와 multi\compile의 차이

#pragma shader_feature#pragma multi_compile과 매우 유사하고 shader\feature 셰이더의 사용되지 않는 배리언트가 게임 빌드에 포함되지 않는다는 유일한 차이점이 있습니다. 따라서 shader\feature는 머티리얼에 설정되는 키워드에 가장 적합하고 multi\_compile은 코드에서 전역으로 설정되는 키워드에 적합합니다.

또한 키워드가 하나뿐인 짧은 표기도 있습니다.

#pragma shader_feature FANCY_STUFF

이 표기는 #pragma shader_feature _ FANCY_STUFF의 단축키로, 두 셰이더 배리언트로 확장됩니다(첫 번째는 정의가 없고 두 번째는 정의가 있음).

여러 multi\_compile 줄 결합

여러 multi_compile 줄이 제공될 수 있고, 결과 셰이더가 가능한 모든 줄 조합에 대해 컴파일됩니다.

#pragma multi_compile A B C
#pragma multi_compile D E

첫 번째 줄에서 세 가지 배리언트가 생성되고, 두 번째 줄에서 두 가지 배리언트가 생성되어 총 여섯 가지의 셰이더 배리언트(A+D, B+D, C+D, A+E, B+E, C+E)가 생성됩니다.

각 multi\compile 줄이 셰이더 “기능” 하나를 제어한다고 생각하면 가장 이해하기 쉽습니다. 이 방법을 사용하면 전체 셰이더 배리언트 수가 매우 빠르게 증가합니다. 예를 들어, 옵션이 각각 두 개인 multi\compile “기능”이 열 개가 있으면 셰이더 배리언트가 총 1,024개 생성됩니다.

키워드 제한

When using shader variants, you should bear in mind that there is a limit of 128 keywords in Unity and a few of these are used internally and therefore subtract from the limit. Also, the keywords are enabled globally throughout a particular Unity project so you should be careful not to exceed the limit when multiple keywords are defined in several different shaders.

빌트인 multi\_compile 단축키

여러 셰이더 배리언트를 컴파일하는 데 사용되는 “단축키” 표기가 몇 개 있으며, 주로 Unity의 다양한 광원, 섀도우, 라이트맵을 처리하는 데 사용됩니다. 자세한 내용은 렌더링 파이프라인을 참조하십시오.

  • multi_compile_fwdbaseForwardBase(포워드 렌더링 베이스) 패스 타입에 필요한 모든 배리언트를 컴파일합니다. 각 배리언트는 다양한 라이트맵 타입과 섀도우가 켜지거나 꺼진 주 방향 광원을 처리합니다.
  • multi_compile_fwdaddForwardAdd(포워드 렌더링 추가) 패스 타입의 배리언트를 컴파일합니다. 방형광, 스폿 광원 또는 점 광원 타입과 쿠키 텍스처가 있는 각각의 배리언트를 처리하도록 배리언트를 컴파일합니다.
  • multi_compile_fwdadd_fullshadows - 위와 동일하지만, 광원이 실시간 섀도우를 표시하는 기능도 포함합니다.
  • multi_compile_fog는 다양한 안개 타입(off/linear/exp/exp2)을 처리하는 여러 배리언트로 확장됩니다.

Most of the built-in shortcuts result in quite many shader variants. It is possible to skip compiling some of them if you know they are not neeeded, by using #pragma skip_variants. For example:

#pragma multi_compile_fwdadd
// will make all variants containing
// "POINT" or "POINT_COOKIE" be skipped
#pragma skip_variants POINT POINT_COOKIE

셰이더 하드웨어 배리언트

One common reason to need shader variants is to create fallbacks or simplified shaders to be able to efficiently run on both high and low end hardware within a single target platform - such as OpenGL ES. To provide a specially optimised set of variants for different levels of hardware capability, you can use shader hardware variants.

셰이더 하드웨어 배리언트 생성을 활성화하려면 #pragma hardware_tier_variants renderer를 추가합니다. 여기서 renderer셰이더 프로그램 pragma에 사용 가능한 렌더링 플랫폼 중 하나입니다. 이#pragma로 다른 키워드에 관계없이 셰이더 배리언트가 각 셰이더마다 3개씩 생성됩니다. 각 배리언트에는 다음 중 하나가 정의됩니다.

UNITY_HARDWARE_TIER1
UNITY_HARDWARE_TIER2
UNITY_HARDWARE_TIER3

위 정의를 사용하여 조건부 폴백이나 로우엔드 또는 하이엔드용 추가 기능을 작성할 수 있습니다. 에디터에서 각 티어 간에 전환할 수 있는 그래픽스 에뮬레이션 메뉴를 사용하여 티어를 테스트할 수 있습니다.

To help keep the impact of these variants as small as possible, only one set of shaders is ever loaded in the player. In addition, any shaders which end up identical - for example if you only write a specialised version for TIER1 and all others are the same - then these shaders will not take up any extra space on disk.

At load time Unity will examine the GPU that it is using and auto-detect a tier value, with a default fallback to the highest tier if the GPU is not auto-detected. You can override this tier value by setting Shader.globalShaderHardwareTier, however this must be done before any shaders you want to vary are loaded - once the shaders are loaded they will have selected their set of variants and this value will have no effect. A good place to set this would be in a pre-load scene before you load your main scene.

이런 셰이더 하드웨어 티어는 플레이어의 품질 설정과 관련이 없고, 전적으로 플레이어를 실행하는 GPU의 상대적인 성능을 통해 인식됩니다.

참고 항목

빌트인 셰이더 변수
GLSL Shader Programs