[Unity] ShaderGraph로 높이 단위로 색상 입히기

del dero
del dero
∙∙조회 15
[Unity] ShaderGraph로 높이 단위로 색상 입히기

 

그려질 픽셀의 position에 따라 출력을 변경하는 법을 익히기 위해서, 높이를 기준으로 다른 색상을 적용하는 ShaderGraph를 만들어 보겠습니다.

시작

 

먼저 Scene에 높낮이를 확인하기 좋은 GameObject를 배치하고, URP Lit ShaderGraph를 생성합니다

 

색상 변경을 위해 최종적으로 BaseColor에 연결될 노드를 작성해야합니다.

 

<색상표>

높이에 따라 입힐 색상을 결정합니다

방법 1 : CustomFunction노드 사용

높이에 따른 색상 분기를 기본 노드만 가지고 12단계를 표현하기에는 노드가 복잡해집니다. CustomFunction노드를 통해 하나의 노드로 표현하는 방식입니다.

CustomFunction노드를 생성합니다. Inputs에는 높이를 받을 float, Outputs에는 출력할 색인 Vector3를 넣습니다. Type을 String으로 설정하고 입력 높이에 따라 다른 색상을 출력하도록 작성합니다.

코드를 생성하기 위해 사용한 프롬프트

(GPT5.5 / 색상표 이미지 첨부)

이미지로 제공된 색상표를 바탕으로 유니티 ShaderGraph에서 CustomFunction 노드에 쓸 string 코드 작성

  • 입력은 float height / 출력은 색상을 표현할 float3
  • 입력 값에 따라 색상표에 맞는 float3를 출력
  • 클립보드로 복사 할 수 있도록 텍스트 형태로 제공

AI 답변

float h = clamp(height, 0.0, 10.0);

float3 colors[11] = { float3(0.121569, 0.305882, 0.470588), // 0 float3(0.152941, 0.682353, 0.376471), // 1 float3(0.180392, 0.800000, 0.443137), // 2 float3(0.509804, 0.878431, 0.666667), // 3 float3(0.956863, 0.815686, 0.247059), // 4 float3(0.831373, 0.674510, 0.050980), // 5 float3(0.960784, 0.690196, 0.254902), // 6 float3(0.921569, 0.596078, 0.305882), // 7 float3(0.862745, 0.462745, 0.200000), // 8 float3(0.627451, 0.250980, 0.000000), // 9 float3(0.431373, 0.172549, 0.000000) // 10 };

int index = (int)round(h); Out = colors[index];

의도와 일치하지 않는 부분은 추가 질문 없이 직접 수정해서 마무리했습니다

Custom Function 노드 body에 작성한 스크립트

scss
float h = clamp(floor(In) + 1.0, 0.0, 11.0);

float3 colors[12] = {
    float3(0.121569, 0.305882, 0.470588), // 0
    float3(0.152941, 0.682353, 0.376471), // 1
    float3(0.180392, 0.800000, 0.443137), // 2
    float3(0.509804, 0.878431, 0.666667), // 3
    float3(0.956863, 0.815686, 0.247059), // 4
    float3(0.831373, 0.674510, 0.050980), // 5
    float3(0.960784, 0.690196, 0.254902), // 6
    float3(0.921569, 0.596078, 0.305882), // 7
    float3(0.862745, 0.462745, 0.200000), // 8
    float3(0.627451, 0.250980, 0.000000), // 9
    float3(0.431373, 0.172549, 0.000000), //10
    float3(0.2431373, 0.1058824, 0.0) 	  //11
};

int index = (int)h;
Out = colors[index];

 

float을 받아서 색상을 출력하는 CustomFunction 노드가 완성되었습니다.

  • In이 0 이하면 colors[0]의 색상을 출력합니다
  • In이 0~11 사이의 값이라면 In의 버림값의 +1을 한 인덱스의 colors가 출력됩니다.
  • In이 11 보다 크다면 colors[11]의 색상을 출력합니다

블랙보드에서 색상이 출력되는 간격을 조절할 Float을 추가하고, WorldPositon의 Y값과 곱한 다음 CustomFunction노드의 입력에 연결합니다.
저장한 다음 머테리얼을 생성해서 오브젝트에 적용합니다.

<프로퍼티로 설정한 Scale값의 조절에 따라 간격이 다르게 표현됩니다>

기존 오브젝트를 유지한 상태로 카메라의 CullingMask를 구분해서 미니맵 등을 위한 Render Texture에 활용할 수 있겠습니다.

방법 2 : 텍스쳐 UV 좌표 변경

색상표를 텍스쳐로 사용하고, 높이에 맞춰 UV좌표를 변경하여 그리는 방식입니다. 최적화를 위해 색상표를 새로 준비할 수 있지만, 이전에 사용한 색상표를 그대로 사용하겠습니다.

 

  • GenerateMipmap을 해체하는 이유 : 픽셀 계산 중 값이 튈 때 다른 텍스처가 적용되는 것을 방지하는 목적

uv좌표는 0과1사이로 되어있습니다. uv의 x좌표가 될 높이값을 먼저 0에서 11 사이의 정수만 나오도록 정규화하겠습니다.

 

x좌표에 쓸 수 있는 값이 되도록 12로 나누면서 색상표 내의 경계선에 걸리지 않도록 값을 살짝 조정합니다. 그리고 Combine 노드를 통해 x좌표와 y좌표(0.5)를 Vector2로 조합합니다

 

SampleTexture2D노드에 준비한 이미지를 Texture로 설정하고, UV에 앞선 노드를 연결하여 노드를 완성합니다

 

마무리

픽셀의 world position을 바탕으로 다른 색상을 적용해보는 테스트를 해보았습니다. 색상에 해당하는 float3를 직접 사용하는 방법과 UV 맵의 좌표를 통해 2D텍스처에서 색상을 고르는 법을 배웠습니다.

world position의 높이를 기준으로만 실험해보았지만, 필요한 기능에 따라 다른 position을 사용할 수 있습니다. BaseColor가 아닌 다른 곳에 연결하여 다른 연출도 가능할 것으로 보입니다.