Unity/그래픽스프로그래밍

0507_Diffuse Warping 만들어보기

minquu 2021. 5. 7. 16:14
반응형

"Warped diffuse" 는 팀포2에서 만든것

빛 공식으로 쓰이는 노멀과 
라이트 벡터의 내적을 UV 사용한다.

 

-----

 

텍스쳐 한장을 받는 스크립터를 만들어준다.

 

그리고 Warp 이라는 커스텀 라이팅을 만드어준다.

 

 

Shader "Custom/Test"
{
    Properties
    {

        _MainTex ("Albedo (RGB)", 2D) = "white" {}

    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM

        #pragma surface surf _Warp noambient


        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;
        }
        float4 Lighting_Warp(SurfaceOutput s,float3 lightDir, float atten){
            float ndotl = dot(s.Normal, lightDir);
            return ndotl;
        }
        ENDCG
    }
    FallBack "Diffuse"

 

 

 

----

 

 

Warp를 할려면 특수한 텍스쳐 한장이 필요하다.

 

Ramp Texture가 필요함

 

 

 

밝은 곳 어두운 곳을 정해줄 수 있다.

 

이미지하나를 구하고

 

이미지가 들어갈 프로퍼티를 하나 더 만들어준다.

 

라이팅 커스텀에서 이미지를 넣을수 있다. 일단 숫자를 넣어봄

 

이제 ndotl 를 넣어준다.

 

 

U 값만 바꿔줌 

 

즉, 텍스쳐링의 uv를 ndotl를 써서 쓰는 기법임 

 

Shader "Custom/Test"
{
    Properties
    {

        _MainTex ("Albedo (RGB)", 2D) = "white" {}
        _RampTex ("RampTex (RGB)", 2D) = "white" {}

    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM

        #pragma surface surf _Warp noambient


        sampler2D _MainTex;
        sampler2D _RampTex;

        struct Input
        {
            float2 uv_MainTex;
            float2 uv__RampTex;
        };

        void surf (Input IN, inout SurfaceOutput o)
        {
  
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex);
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        float4 Lighting_Warp(SurfaceOutput s,float3 lightDir, float atten){
            float ndotl = dot(s.Normal, lightDir) * 0.5+ 0.5;
            float4 ramp = tex2D(_RampTex, 1 - float2(ndotl, 0.5));

            return ramp;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

 

 

-

왠만해서는 텍스쳐를 

 

 

Repeat 말고 클램프로 하기

 

----

나머지 노멀 , 알베도도 넣어서 확인해보자

 

Shader "Custom/Test"
{
    Properties
    {

        _MainTex ("Albedo (RGB)", 2D) = "white" {}
        _Normal ("Normal (RGB)", 2D) = "white" {}
        _RampTex ("RampTex (RGB)", 2D) = "white" {}

    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM

        #pragma surface surf _Warp noambient


        sampler2D _MainTex;
        sampler2D _RampTex;
        sampler2D _Normal;
        struct Input
        {
            float2 uv_MainTex;
            float2 uv__RampTex;
            float2 uv_Normal;
        };

        void surf (Input IN, inout SurfaceOutput o)
        {
  
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex);
            o.Normal = UnpackNormal(tex2D(_Normal, IN.uv_Normal));
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        float4 Lighting_Warp(SurfaceOutput s,float3 lightDir, float atten){
            float ndotl = dot(s.Normal, lightDir) * 0.5+ 0.5;
            float4 ramp = tex2D(_RampTex, 1 - float2(ndotl, 0.5));

            float4 final;
            final.rgb = s.Albedo * ramp.rgb;
            final.a = s.Alpha;
            return final;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

 

 

 

----

스펙큘러 추가하기

 

U는 ndotl 으로 쓰고 

V 를 스펙큘러로 쓸것이다.

 

 

 

            float4 ramp = tex2D(_RampTex, float2(ndotl, spec));

 

V에 spec를 넣어준다.

 

 

Shader "Custom/Test"
{
    Properties
    {
        _MainTex ("Albedo (RGB)", 2D) = "white" {}
        _Normal ("Normal (RGB)", 2D) = "white" {}
        _RampTex ("RampTex (RGB)", 2D) = "white" {}
    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM
        #pragma surface surf _Warp noambient
        #pragma target 3.0

        sampler2D _MainTex;
        sampler2D _RampTex;
        sampler2D _Normal;

        struct Input
        {
            float2 uv_MainTex;
            float2 uv_RampTex;
            float2 uv_Normal;
        };

        void surf (Input IN, inout SurfaceOutput o)
        {
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex);
            o.Normal = UnpackNormal(tex2D(_Normal, IN.uv_Normal));
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        float4 Lighting_Warp(SurfaceOutput s, float3 lightDir,float3 viewDir, float atten){
            float ndotl = dot(s.Normal, lightDir) * 0.5 + 0.5 ;

            //스펙큘러 만드는 공식 
            float H = normalize(lightDir + viewDir);
            float spec = dot(s.Normal, H);


            float4 ramp = tex2D(_RampTex, float2(ndotl, spec));

            float4 final;
            final.rgb = s.Albedo * ramp.rgb;
            final.a = s.Alpha;
            return final;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

 

확 티가 나지 않으니깐, 몇개를 더 넣어보자

 

위에 화이트가 없어서 스펙큘러가 안 튐

 

 

 

이런 맵을 사용해주자

 

Shader "Custom/Test"
{
    Properties
    {
        _MainTex ("Albedo (RGB)", 2D) = "white" {}
        _Normal ("Normal (RGB)", 2D) = "white" {}
        _RampTex ("RampTex (RGB)", 2D) = "white" {}
    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM
        #pragma surface surf _Warp noambient
        #pragma target 3.0

        sampler2D _MainTex;
        sampler2D _RampTex;
        sampler2D _Normal;

        struct Input
        {
            float2 uv_MainTex;
            float2 uv_RampTex;
            float2 uv_Normal;
        };

        void surf (Input IN, inout SurfaceOutput o)
        {
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex);
            o.Normal = UnpackNormal(tex2D(_Normal, IN.uv_Normal));
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        float4 Lighting_Warp(SurfaceOutput s, float3 lightDir, float3 viewDir, float atten){
            float ndotl = dot(s.Normal, lightDir) * 0.5 + 0.5 ;

            //스펙큘러 만드는 공식 
            float H = normalize(lightDir + viewDir);
            float spec = dot(s.Normal, H);


            float4 ramp = tex2D(_RampTex, float2(ndotl, spec));
            //float4 final;
            //final.rgb = (s.Albedo.rgb * ramp.rgb) + (ramp.rgb * 0.1);
            //final.a = s.Alpha;
            return ramp;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

 

 

기존 텍스쳐링이 방해가 되니깐 ramp만 출력해서 봐보자

 

 

 

----

 

텍스쳐링 적용 시키면

 

Shader "Custom/Test"
{
    Properties
    {
        _MainTex ("Albedo (RGB)", 2D) = "white" {}
        _Normal ("Normal (RGB)", 2D) = "white" {}
        _RampTex ("RampTex (RGB)", 2D) = "white" {}
    }
    SubShader
    {
        Tags { "RenderType"="Opaque" }
        LOD 200

        CGPROGRAM
        #pragma surface surf _Warp noambient
        #pragma target 3.0

        sampler2D _MainTex;
        sampler2D _RampTex;
        sampler2D _Normal;

        struct Input
        {
            float2 uv_MainTex;
            float2 uv_RampTex;
            float2 uv_Normal;
        };

        void surf (Input IN, inout SurfaceOutput o)
        {
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex);
            o.Normal = UnpackNormal(tex2D(_Normal, IN.uv_Normal));
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        float4 Lighting_Warp(SurfaceOutput s, float3 lightDir, float3 viewDir, float atten){
            float ndotl = dot(s.Normal, lightDir) * 0.5 + 0.5 ;

            //스펙큘러 만드는 공식 
            float H = normalize(lightDir + viewDir);
            float spec = dot(s.Normal, H);


            float4 ramp = tex2D(_RampTex, float2(ndotl, spec));
            float4 final;
            final.rgb = (s.Albedo.rgb * ramp.rgb) + (ramp.rgb * 0.1);
            final.a = s.Alpha;
            return final;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

 

 

 

반응형