완성 결과
Pass
Pass는 오브젝트 렌더링 단위로 Pass 수만큼 오브젝트를 그려줍니다.
pass추가
Standard Surface Shader를 만들고 다음과 같이 수정했습니다.
CGPROGRAM ~ ENDCG 부분을 추가해주면 Pass가 추가됩니다.
똑같이 2번 그린 것이기 때문에 변화는 없습니다.
Vertex Shader
Surface Shader는 색을 제어하고 Vertex Shader는 말그대로 vertex(정점)를 제어할 수 있습니다.
vertex shader 추가
- #pragma에 vertex:(함수 이름)을 작성합니다.
- void (함수이름) (inout appdata_full v)로 함수를 작성합니다.
appdata full 구조체
- float4 vertex : POSITION;
- float4 tangent : TANGENT; //접선 방향
- float3 normal : NORMAL;
- float4 texcoord : TEXCOORD0; //첫 번째 UV 좌표
- float4 texcoord1 : TEXCOORD1;
- float4 texcoord2 : TEXCOORD2;
- float4 texcoord3 : TEXCOORD3;
- fixed4 color : COLOR; //버텍스 컬러
appdata_base : position, normal, texcoord
appdata_tan : position, tangent, normal, texcoord
appdata_full : position, tangent, normal, texcoord, texcoord1, texcoord2, texcoord3
외곽선 생성
코드 설명
cull front : 뒷면만 렌더링 합니다. (2번째 pass에서 앞면을 렌더링 //cull back 추가)
vert 함수 : vertex를 normal 방향으로 확장시켜줍니다.
단순히 검은색으로 만들기 때문에 가장 단순한 라이팅 구조로 만들고 surf함수를 비웠습니다.
Input 구조체에 값을 받지 않으면 오류가 나기 때문에 의미없는 값을 넣었습니다.
필요없는 환경광과 그림자를 없애줍니다.
외곽선 정리
바깥쪽에 있는 외곽선만 그리게 바꿔줍니다.
※여기서부터는 이것저것 해보다가 된거라서 실제 적용해도 문제없는지는 모르겠습니다.
zwrite를 off 하면 zbuffer에 깊이값을 기록하지 않습니다.
zbuffer는 깊이값을 0.0~1.0으로 기록한다. (카메라와 가장 가까우면 0.0, 가장 멀리있으면 1.0)
문제점
zwrite를 off로 하면 zbuffer에 1로 기록된다.
가장 멀리 있다고 판단하여 다른오브젝트에 가려지면 외곽선이 그려지지 않는다.
수정
RenderType과 Queue를 Transparent로 바꿔준다.
굵기, 색 추가
굵기와 색을 변경할 수 있게 코드를 추가해줍니다.
텍스쳐를 입혀주고 색, 굵기를 조정하면 완성!
완성 코드
Shader "Custom/OutLine"
{
Properties
{
_MainTex ("Albedo (RGB)", 2D) = "white" {}
_OutLineColor("OutLine Color", Color) = (0,0,0,0)
_OutLineWidth("OutLine Width", Range(0.001, 0.01)) = 0.01
}
SubShader
{
Tags { "RenderType"="Transparent" "Queue" = "Transparent"}
LOD 200
cull front
zwrite off
CGPROGRAM
#pragma surface surf NoLight vertex:vert noshadow noambient
#pragma target 3.0
float4 _OutLineColor;
float _OutLineWidth;
void vert(inout appdata_full v) {
v.vertex.xyz += v.normal.xyz * _OutLineWidth;
}
struct Input
{
float4 color;
};
void surf (Input IN, inout SurfaceOutput o)
{
}
float4 LightingNoLight(SurfaceOutput s, float3 lightDir, float atten) {
return float4(_OutLineColor.rgb, 1);
}
ENDCG
cull back
zwrite on
CGPROGRAM
#pragma surface surf Lambert
#pragma target 3.0
sampler2D _MainTex;
struct Input
{
float2 uv_MainTex;
};
void surf(Input IN, inout SurfaceOutput o)
{
fixed4 c = tex2D(_MainTex, IN.uv_MainTex);
o.Albedo = c.rgb;
o.Alpha = c.a;
}
ENDCG
}
FallBack "Diffuse"
}
'유니티 > 쉐이더' 카테고리의 다른 글
[Unity Shader] Custom PostProcessing(포스트 프로세싱) 직접 만들기 (노이즈 필터) (0) | 2022.06.10 |
---|---|
[Unity Shader] 비눗방울 쉐이더 만들기 (0) | 2022.03.25 |
[Unity Shader] 쉐이더로 애니메이션 재생 (1) | 2022.03.22 |
[Unity Shader] 커스텀 라이트 : Lambert, Half - Lambert (0) | 2022.02.08 |
[Unity Shader] 쉐이더 코드 설명 : Properties, SurfaceOutputstandard (0) | 2022.02.08 |