<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Unlit Archives - 어제와 내일의 나 그 사이의 이야기</title>
	<atom:link href="https://lycos7560.com/tag/unlit/feed/" rel="self" type="application/rss+xml" />
	<link></link>
	<description>생각의 흐름을 타고 다니며 만드는 블로그</description>
	<lastBuildDate>Sat, 07 Sep 2024 05:55:13 +0000</lastBuildDate>
	<language>ko-KR</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=7.0</generator>

<image>
	<url>https://lycos7560.com/wp-content/uploads/2022/11/cropped-cropped-cropped-log-1-150x150-1-80x80.png</url>
	<title>Unlit Archives - 어제와 내일의 나 그 사이의 이야기</title>
	<link></link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>URP_Unlit_Grayscale / Hue Shader &#8211; HLSL</title>
		<link>https://lycos7560.com/unity/urp_unlit_grayscale-hue-shader-hlsl/38278/</link>
					<comments>https://lycos7560.com/unity/urp_unlit_grayscale-hue-shader-hlsl/38278/#respond</comments>
		
		<dc:creator><![CDATA[lycos7560]]></dc:creator>
		<pubDate>Sat, 07 Sep 2024 00:27:56 +0000</pubDate>
				<category><![CDATA[Unity]]></category>
		<category><![CDATA[UnityShader]]></category>
		<category><![CDATA[Fragment]]></category>
		<category><![CDATA[Grayscale]]></category>
		<category><![CDATA[HLSL]]></category>
		<category><![CDATA[HLSL Shader]]></category>
		<category><![CDATA[Hue]]></category>
		<category><![CDATA[Opaque]]></category>
		<category><![CDATA[Shader]]></category>
		<category><![CDATA[ShaderLab]]></category>
		<category><![CDATA[UniversalPipeline]]></category>
		<category><![CDATA[Unlit]]></category>
		<category><![CDATA[URP]]></category>
		<category><![CDATA[Vertex]]></category>
		<guid isPermaLink="false">https://lycos7560.com/?p=38278</guid>

					<description><![CDATA[<p>Grayscale_URP_Unlit.shader Grayscale 변환 원리 : 주어진 코드에서 색상을 흑백으로 변환하는 원리는 색상의 밝기(휘도, Luminance)를 계산하는 것에 기반합니다. 인간의 눈은 색상마다 민감도가 다르기 때문에, 각 RGB 채널에 가중치를 부여하여 밝기를 계산합니다. RGB를 Grayscale로 변환하는 원리 인간의 눈은 각각의 색상 성분(R, G, B)에 대해 감도가 다르다. 일반적으로 녹색(G) 성분에 가장 민감하고, 빨간색(R) 성분에 중간 정도로 민감하며, 파란색(B) [&#8230;]</p>
<p>The post <a href="https://lycos7560.com/unity/urp_unlit_grayscale-hue-shader-hlsl/38278/">URP_Unlit_Grayscale / Hue Shader &#8211; HLSL</a> appeared first on <a href="https://lycos7560.com">어제와 내일의 나 그 사이의 이야기</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph"><strong>Grayscale_URP_Unlit.shader</strong></p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">Shader "Unlit/lycos/Grayscale_URP_Unlit"
{
    Properties
    {
        [MainTexture] _BaseMap("Texture", 2D) = "white" {}
        _GrayscaleIntensity("Grayscale Intensity", Range(0, 1)) = 1.0 // 흑백 효과 강도 (0: 원본 색상, 1: 완전 흑백)
    }
    SubShader
    {
        Tags { "RenderType" = "Opaque" "Queue" = "Geometry" "RenderPipeline" = "UniversalPipeline" }

        Pass
        {
            Name  "Grayscale_URP_Unlit"
            Tags {"LightMode" = "SRPDefaultUnlit"} // 이 Pass는 Unlit(조명이 없는) 모드로 작동함을 선언

            HLSLPROGRAM
            #pragma target 4.5 // Shader 모델 4.5를 대상
            #pragma vertex vert // vertex shader 선언 (vert 함수)
            #pragma fragment frag // fragment shader 선언 (frag 함수)
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
            // Constant Buffer 
            // Unity의 각 Material 상수를 정의
            CBUFFER_START(UnityPerMaterial) 
                float4 _BaseMap_ST; // TEXTURE UV 좌표 변환에 사용되는 정보 (offset, tiling)
                float _GrayscaleIntensity; // 흑백 효과 강도
            CBUFFER_END
            TEXTURE2D(_BaseMap);  // TEXTURE2D 선언
            SAMPLER(sampler_BaseMap); // SAMPLER 선언
            // vertex shader의 입력 구조체 
            struct Attributes
            {
                float4 positionOS : POSITION;  // 모델 공간에서의 정점 위치 (float3, float4)
                float2 uv : TEXCOORD0;   // 첫 번째 UV 텍스처 좌표 (float2, float3, float4)
                float4 color : COLOR;  // 정점 별 색상  (float4)
            };
            // Varyings 구조체 정의
            // 출력 구조체로, fragment Shader에서 사용할 데이터(예: 변환된 위치, UV 좌표 등)를 포함
            struct Varyings
            {
                float4 positionCS : SV_POSITION;
                float2 uv : TEXCOORD0;
                float4 color : COLOR;
            };
            // vertex shader가 Attributes를 사용
            Varyings vert(Attributes input)
            {
                // 출력 변수를 정의
                Varyings output = (Varyings)0; // Varyings 초기화, 모든 필드에 기본값을 할당
                float4 positionOS = input.positionOS; // 모델 공간에서의 정점 위치를 float4 형태로 저장
                float3 positionWS = TransformObjectToWorld(positionOS.xyz); // 모델 공간에서 월드 공간으로의 변환을 수행
                float4 positionCS = TransformWorldToHClip(positionWS); // 월드 공간에서 클립 공간으로의 변환을 수행
                output.positionCS = positionCS; // 변환된 클립 공간 위치를 출력 구조체 output에 저장
                output.uv = input.uv; // 입력으로 받은 UV 좌표를 출력 구조체 output에 저장
                output.color = input.color;
                return output;
            }
            // 프래그먼트 셰이더(fragment shader) 
            // 픽셀 단위로 호출되며, 각 픽셀의 최종 색상을 계산해 화면에 출력
            // 기본적으로 입력된 UV 좌표를 이용해 텍스처 색상을 샘플링하고, 
            // 최종적으로 머티리얼의 색상과 결합하여 픽셀의 색상을 반환하는 역할
            float4 frag(Varyings input) : SV_Target
            {
                // UV 좌표 변환을 위한 계산
                float2 baseMapUV = input.uv.xy * _BaseMap_ST.xy + _BaseMap_ST.zw;
                // SAMPLE_TEXTURE2D 함수를 사용하여 텍스처를 샘플링합니다.
                float4 texColor = SAMPLE_TEXTURE2D(_BaseMap, sampler_BaseMap, baseMapUV);
                // Grayscale 변환
                float gray = dot(texColor.rgb, float3(0.299, 0.587, 0.114));
                // 흑백 효과의 강도를 적용
                // lerp 함수를 사용하여 texColor와 변환된 흑백 색상 사이에서 _GrayscaleIntensity 값을 기반으로 색상을 보간합니다.
                float4 finalColor = lerp(texColor, float4(gray, gray, gray, texColor.a), _GrayscaleIntensity);

                // 최종 계산된 색상을 출력합니다. SV_Target은 이 값이 픽셀 셰이더의 출력으로 화면에 렌더링된다는 것을 의미합니다.
                return finalColor;
            }
            ENDHLSL
        }
    }
}
</pre>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<figure class="wp-block-video"><video height="1440" style="aspect-ratio: 2560 / 1440;" width="2560" controls muted src="https://lycos7560.com/wp-content/uploads/2024/09/녹화_2024_09_07_09_00_02_758.mp4"></video></figure>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h2 class="wp-block-heading">Grayscale 변환 원리 :</h2>



<p class="wp-block-paragraph">주어진 코드에서 색상을 흑백으로 변환하는 원리는 색상의 밝기(휘도, Luminance)를 계산하는 것에 기반합니다. </p>



<p class="wp-block-paragraph">인간의 눈은 색상마다 민감도가 다르기 때문에, 각 RGB 채널에 가중치를 부여하여 밝기를 계산합니다.</p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">// Grayscale 변환
float gray = dot(texColor.rgb, float3(0.299, 0.587, 0.114));
</pre>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading">RGB를 Grayscale로 변환하는 원리</h3>



<p class="wp-block-paragraph">인간의 눈은 각각의 색상 성분(R, G, B)에 대해 감도가 다르다.</p>



<p class="wp-block-paragraph">일반적으로 <strong>녹색(G)</strong> 성분에 가장 민감하고, <strong>빨간색(R)</strong> 성분에 중간 정도로 민감하며, <strong>파란색(B)</strong> 성분에 가장 덜 민감하다. </p>



<p class="wp-block-paragraph">따라서, 각 색상 성분에 적절한 가중치를 부여하여 이를 반영한 값을 계산해야 더 자연스러운 Grayscale 변환이 된다.</p>



<p class="wp-block-paragraph">그래서 RGB 값에서 <strong>Grayscale</strong> 값을 구하는 공식은 각 성분의 가중치를 적용한 합으로 나타낸다.</p>



<figure class="wp-block-image size-full"><img decoding="async" width="385" height="40" src="https://lycos7560.com/wp-content/uploads/2024/09/image-7.png" alt="" class="wp-image-38284" srcset="https://lycos7560.com/wp-content/uploads/2024/09/image-7.png 385w, https://lycos7560.com/wp-content/uploads/2024/09/image-7-300x31.png 300w" sizes="(max-width: 385px) 100vw, 385px" /></figure>



<p class="wp-block-paragraph">이 가중치는 인간의 시각적 감도를 반영한 표준 가중치라고 할 수 있다.</p>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading">내적(Dot Product) 사용 이유</h3>



<p class="wp-block-paragraph">내적은 두 벡터 간의 대응되는 성분을 곱한 후 더하는 연산입니다. </p>



<p class="wp-block-paragraph">RGB 값을 각각의 가중치와 곱한 후 더하는 이 과정을 <strong>내적</strong>을 통해 쉽게 계산할 수 있습니다. </p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">float gray = dot(texColor.rgb, float3(0.299, 0.587, 0.114));</pre>



<p class="wp-block-paragraph">이 공식을 내적 연산을 사용하여 간결하게 표현한 것입니다.</p>



<div style="height:100px" aria-hidden="true" class="wp-block-spacer"></div>



<p class="wp-block-paragraph"><strong>HueAdjustment_URP_Unlit.shader</strong></p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">Shader "Unlit/lycos/HueAdjustment_URP_Unlit"
{
    Properties
    {
        [MainTexture] _BaseMap("Texture", 2D) = "white" {} // 기본 텍스처
        _HueAdjustment("Hue Adjustment", Range(-1, 1)) = 0.0 // 색조 조정 값 (-1: -180도, 1: 180도)
    }
    SubShader
    {
        Tags { "RenderType" = "Opaque" "Queue" = "Geometry" "RenderPipeline" = "UniversalPipeline" }

        Pass
        {
            Name  "HueAdjustment_URP_Unlit"
            Tags {"LightMode" = "SRPDefaultUnlit"} // 이 Pass는 Unlit(조명이 없는) 모드로 작동함을 선언

            HLSLPROGRAM
            #pragma target 4.5 // Shader 모델 4.5를 대상으로 함
            #pragma vertex vert // vertex shader 선언
            #pragma fragment frag // fragment shader 선언
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"

            // Constant Buffer
            // Unity의 각 Material 상수를 정의
            CBUFFER_START(UnityPerMaterial) 
                float4 _BaseMap_ST; // 텍스처의 UV 좌표 변환 정보 (offset, tiling)
                float _HueAdjustment; // 색조 조정 값
            CBUFFER_END

            TEXTURE2D(_BaseMap);  // 텍스처 선언
            SAMPLER(sampler_BaseMap); // 샘플러 선언

            // Vertex Shader의 입력 구조체
            struct Attributes
            {
                float4 positionOS : POSITION;  // 모델 공간에서의 정점 위치
                float2 uv : TEXCOORD0;   // UV 텍스처 좌표
                float4 color : COLOR;  // 정점 색상
            };

            // Varyings 구조체 정의
            // Fragment Shader에서 사용할 데이터(예: 변환된 위치, UV 좌표 등)를 포함
            struct Varyings
            {
                float4 positionCS : SV_POSITION; // 클립 공간에서의 정점 위치
                float2 uv : TEXCOORD0; // UV 좌표
                float4 color : COLOR; // 색상
            };

            // Vertex Shader
            Varyings vert(Attributes input)
            {
                Varyings output = (Varyings)0; // Varyings 초기화
                float4 positionOS = input.positionOS; // 모델 공간에서의 정점 위치 저장
                float3 positionWS = TransformObjectToWorld(positionOS.xyz); // 모델 공간에서 월드 공간으로 변환
                float4 positionCS = TransformWorldToHClip(positionWS); // 월드 공간에서 클립 공간으로 변환
                output.positionCS = positionCS; // 변환된 클립 공간 위치 저장
                output.uv = input.uv; // UV 좌표 저장
                output.color = input.color; // 색상 저장
                return output;
            }

            float3 ApplyHue(float3 col, float hueAdjust)
            {
                // RGB 색상을 HSV 색상 공간으로 변환
                float4 K = float4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0);
                float4 P = lerp(float4(col.bg, K.wz), float4(col.gb, K.xy), step(col.b, col.g));
                float4 Q = lerp(float4(P.xyw, col.r), float4(col.r, P.yzx), step(P.x, col.r));
                float D = Q.x - min(Q.w, Q.y);
                float E = 1e-10; // 작은 값 추가
                float3 hsv = float3(abs(Q.z + (Q.w - Q.y)/(6.0 * D + E)), D / (Q.x + E), Q.x);

                // 색조 조정
                float hue = hsv.x + hueAdjust;
                hsv.x = (hue &lt; 0)
                        ? hue + 1
                        : (hue > 1)
                            ? hue - 1
                            : hue;

                // HSV 색상을 RGB 색상으로 변환
                float4 K2 = float4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
                float3 P2 = abs(frac(hsv.xxx + K2.xyz) * 6.0 - K2.www);
                float3 result = hsv.z * lerp(K2.xxx, saturate(P2 - K2.xxx), hsv.y);
                return result;
            }

            // Fragment Shader
            float4 frag(Varyings input) : SV_Target
            {
                // UV 좌표 변환
                float2 baseMapUV = input.uv.xy * _BaseMap_ST.xy + _BaseMap_ST.zw;
                // 텍스처 샘플링
                float4 texColor = SAMPLE_TEXTURE2D(_BaseMap, sampler_BaseMap, baseMapUV);
                // 색조 조정
                float3 hueAdjustedColor = ApplyHue(texColor.rgb, _HueAdjustment);
                // 최종 색상 반환
                float4 finalColor = float4(hueAdjustedColor, texColor.a);

                // 최종 계산된 색상을 출력
                return finalColor;
            }
            ENDHLSL
        }
    }
}
</pre>



<div style="height:20px" aria-hidden="true" class="wp-block-spacer"></div>



<figure class="wp-block-video"><video height="1440" style="aspect-ratio: 2560 / 1440;" width="2560" controls muted src="https://lycos7560.com/wp-content/uploads/2024/09/녹화_2024_09_07_09_24_17_343.mp4"></video></figure>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading">1. RGB to HSV 변환 (RGB 색상을 HSV 색상 공간으로 변환)</h3>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">float4 K = float4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0);
float4 P = lerp(float4(col.bg, K.wz), float4(col.gb, K.xy), step(col.b, col.g));
float4 Q = lerp(float4(P.xyw, col.r), float4(col.r, P.yzx), step(P.x, col.r));
float D = Q.x - min(Q.w, Q.y);
float E = 1e-10; // 작은 값 추가
float3 hsv = float3(abs(Q.z + (Q.w - Q.y) / (6.0 * D + E)), D / (Q.x + E), Q.x);</pre>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<p class="wp-block-paragraph"><strong>입력 변수</strong>: <code>col</code>은 RGB 색상을 나타내는 <code>float3</code> 값입니다. 이 색상을 HSV로 변환하는 과정입니다.</p>



<p class="wp-block-paragraph"><code>K</code>: 색상 변환에 필요한 상수 값입니다. 다양한 색상 조합을 비교할 때 사용됩니다.</p>



<p class="wp-block-paragraph"><code>P</code>, <code>Q</code>: <code>lerp</code>(선형 보간) 함수와 <code>step</code> 함수를 사용하여 색상 성분을 비교하고 보간합니다. 이를 통해 RGB에서 가장 큰 값과 작은 값을 찾고, 색상 성분을 적절히 섞어 색상 차이 <code>D</code>와 관련된 값을 계산합니다.</p>



<p class="wp-block-paragraph"><code>D</code>: RGB 색상의 최댓값과 최솟값의 차이를 나타내며, 이것은 채도(Saturation)를 결정하는 값입니다.</p>



<p class="wp-block-paragraph"><code>hsv.x</code>: 색상(Hue)을 계산하기 위한 값입니다. RGB에서 Hue는 특정 범위의 계산을 통해 구해지며, 이 값은 색상 톤을 나타냅니다.</p>



<p class="wp-block-paragraph"><code>hsv.y</code>: 채도(Saturation)를 계산한 값입니다. </p>



<p class="wp-block-paragraph"><code>D</code>를 RGB에서의 최댓값과 나누어 채도를 구합니다.</p>



<p class="wp-block-paragraph"><code>hsv.z</code>: 명도(Value)로, RGB 색상에서의 최댓값이 됩니다.</p>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading">2. 색조 조정 (Hue Shift)</h3>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">float hue = hsv.x + hueAdjust;
hsv.x = (hue &lt; 0) ? hue + 1 : (hue > 1) ? hue - 1 : hue;</pre>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<p class="wp-block-paragraph"><code>hueAdjust</code>: 함수의 인자로 전달된 <strong>색조 변경 값</strong>입니다.</p>



<p class="wp-block-paragraph"><code>hsv.x + hueAdjust</code>: 기존의 색조에 새로운 색조 조정 값을 더해 색조를 변경합니다.</p>



<p class="wp-block-paragraph"><code>hsv.x</code>: Hue는 0에서 1 사이의 값으로 표현되므로, <code>hue</code> 값이 0보다 작으면 1을 더하고, 1보다 크면 1을 빼서 순환시킵니다. 이는 색조의 값을 항상 0~1 범위 내에 유지시키기 위한 작업입니다.</p>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<h3 class="wp-block-heading">3. HSV to RGB 변환 (HSV를 다시 RGB로 변환)</h3>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">float4 K2 = float4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
float3 P2 = abs(frac(hsv.xxx + K2.xyz) * 6.0 - K2.www);
float3 result = hsv.z * lerp(K2.xxx, saturate(P2 - K2.xxx), hsv.y);
</pre>



<div style="height:40px" aria-hidden="true" class="wp-block-spacer"></div>



<p class="wp-block-paragraph"><code>K2</code>: HSV에서 RGB로 변환할 때 사용되는 상수 값입니다.</p>



<p class="wp-block-paragraph"><code>frac(hsv.xxx + K2.xyz)</code>: 이 계산을 통해 <code>hsv.x</code>에 기반한 색상 조합을 생성합니다.</p>



<p class="wp-block-paragraph"><code>P2</code>: 색상을 변환할 때 필요한 중간 계산으로, 색조(Hue) 정보를 바탕으로 RGB로 변환하는데 필요한 보간을 수행합니다.</p>



<p class="wp-block-paragraph"><code>lerp</code>: 보간을 사용하여 최종 RGB 값에 대한 보정을 수행합니다. <code>hsv.y</code>는 채도, <code>hsv.z</code>는 명도에 해당하는 값을 적용하여 최종적인 색상 값을 구합니다.</p>



<p class="wp-block-paragraph"><code>result</code>: 변환된 최종 <strong>RGB 값</strong>입니다.</p>



<div style="height:100px" aria-hidden="true" class="wp-block-spacer"></div>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://lycos7560.com/unity/urp_unlit_grayscale-hue-shader-hlsl/38278/">URP_Unlit_Grayscale / Hue Shader &#8211; HLSL</a> appeared first on <a href="https://lycos7560.com">어제와 내일의 나 그 사이의 이야기</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://lycos7560.com/unity/urp_unlit_grayscale-hue-shader-hlsl/38278/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		<enclosure url="https://lycos7560.com/wp-content/uploads/2024/09/녹화_2024_09_07_09_00_02_758.mp4" length="1791108" type="video/mp4" />
<enclosure url="https://lycos7560.com/wp-content/uploads/2024/09/녹화_2024_09_07_09_24_17_343.mp4" length="2780514" type="video/mp4" />

			</item>
		<item>
		<title>Unity Urp Shader Vertex, Attributes, fragment  Unlit 예시</title>
		<link>https://lycos7560.com/unity/unity-urp-shader-vertex-attributes-struct-%ec%98%88%ec%8b%9c/38254/</link>
					<comments>https://lycos7560.com/unity/unity-urp-shader-vertex-attributes-struct-%ec%98%88%ec%8b%9c/38254/#respond</comments>
		
		<dc:creator><![CDATA[lycos7560]]></dc:creator>
		<pubDate>Fri, 06 Sep 2024 04:31:28 +0000</pubDate>
				<category><![CDATA[Unity]]></category>
		<category><![CDATA[UnityShader]]></category>
		<category><![CDATA[Attributes]]></category>
		<category><![CDATA[Core]]></category>
		<category><![CDATA[Core.hlsl]]></category>
		<category><![CDATA[Fragment]]></category>
		<category><![CDATA[positionCS]]></category>
		<category><![CDATA[positionOS]]></category>
		<category><![CDATA[Shader]]></category>
		<category><![CDATA[SpaceTransforms]]></category>
		<category><![CDATA[struct]]></category>
		<category><![CDATA[TransformObjectToWorld]]></category>
		<category><![CDATA[TransformWorldToView]]></category>
		<category><![CDATA[Unlit]]></category>
		<category><![CDATA[URP]]></category>
		<category><![CDATA[URP SHADER]]></category>
		<category><![CDATA[Varyings]]></category>
		<category><![CDATA[Vertex]]></category>
		<guid isPermaLink="false">https://lycos7560.com/?p=38254</guid>

					<description><![CDATA[<p>&#8220;Unlit/URP_UnlitBase&#8220; 참고 &#8220;Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl&#8220; &#8220;Packages/com.unity.render-pipelines.core/ShaderLibrary/SpaceTransforms.hlsl&#8221;</p>
<p>The post <a href="https://lycos7560.com/unity/unity-urp-shader-vertex-attributes-struct-%ec%98%88%ec%8b%9c/38254/">Unity Urp Shader Vertex, Attributes, fragment  Unlit 예시</a> appeared first on <a href="https://lycos7560.com">어제와 내일의 나 그 사이의 이야기</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p class="wp-block-paragraph">&#8220;<strong>Unlit/URP_UnlitBase</strong>&#8220;</p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">Shader "URP/Unlit/URP_UnlitBase"
{
    Properties
    {
        [MainTexture] _BaseMap("Texture", 2D) = "white" {}
        [MainColor] _BaseColor("Color", Color) = (1, 1, 1, 1)
    }

        SubShader
        {
            Tags { "RenderType" = "Opaque" "Queue" = "Geometry" "RenderPipeline" = "UniversalPipeline" }
            LOD 100

            Pass
            {
                Name  "URP_UnlitBase"
                Tags {"LightMode" = "SRPDefaultUnlit"} // 이 Pass는 Unlit(조명이 없는) 모드로 작동함을 선언

                HLSLPROGRAM
                #pragma target 4.5 // Shader 모델 4.5를 대상

                // vertex shader 선언 (vert 함수)
                // vert라는 이름의 함수를 vertex shader로 사용 선언
                // vert는 입력으로 Attributes 구조체를 받고, 처리된 결과를 반환
                #pragma vertex vert // vertex shader 선언 (vert 함수)
                #pragma fragment frag // fragment shader 선언 (frag 함수)

                #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"

                // Constant Buffer 
                // Unity의 각 Material 상수를 정의
                CBUFFER_START(UnityPerMaterial) 
                    float4 _BaseMap_ST; // TEXTURE UV 좌표 변환에 사용되는 정보 (offset, tiling)
                    float4 _BaseColor; // 설정 색상
                CBUFFER_END

                TEXTURE2D(_BaseMap);  // TEXTURE2D 선언
                SAMPLER(sampler_BaseMap); // SAMPLER 선언

                // vertex shader의 입력 구조체 
                struct Attributes
                {
                    float4 positionOS : POSITION;  // 모델 공간에서의 정점 위치 (float3, float4)
                    float3 normalOS : NORMAL;  // 모델 공간에서의 정점 법선 (float3)
                    float2 uv : TEXCOORD0;   // 첫 번째 UV 텍스처 좌표 (float2, float3, float4)
                    float2 uv2 : TEXCOORD1;  // 두 번째 UV 텍스처 좌표 (float2, float3, float4)
                    float2 uv3 : TEXCOORD2;  // 세 번째 UV 텍스처 좌표 (float2, float3, float4)
                    float2 uv4 : TEXCOORD3;  // 넷 번째 UV 텍스처 좌표 (float2, float3, float4)
                    float4 tangentOS : TANGENT;  // 모델 공간에서의 접선 벡터 (normal mapping에 사용)
                    float4 color : COLOR;  // 정점 별 색상  (float4)
                    int4 blendIndices : BLENDINDICES;  // 스킨 매싱에서 뼈대 인덱스
                };

                // Varyings 구조체 정의
                // 출력 구조체로, fragment Shader에서 사용할 데이터(예: 변환된 위치, UV 좌표 등)를 포함
                struct Varyings
                {
                    float4 positionCS : SV_POSITION;
                    float2 uv : TEXCOORD0;
                    float4 color : COLOR;
                };


                // vertex shader가 Attributes를 사용
                Varyings vert(Attributes input)
                {
                    // 출력 변수를 정의
                    Varyings output = (Varyings)0; // Varyings 초기화, 모든 필드에 기본값을 할당

                    // 모델 공간에서의 정점 위치를 float4 형태로 저장
                    float4 positionOS = input.positionOS;

                    // 모델 공간에서 월드 공간으로의 변환을 수행
                    float3 positionWS = TransformObjectToWorld(positionOS.xyz);

                    // 월드 공간에서 뷰 공간으로의 변환을 수행
                    float3 positionVS = TransformWorldToView(positionWS);

                    // 월드 공간에서 클립 공간으로의 변환을 수행
                    // 클립 공간 : 렌더링 파이프라인에서 최종적으로 화면에 출력될 좌표계
                    float4 positionCS = TransformWorldToHClip(positionWS);

                    // 변환된 클립 공간 위치를 출력 구조체 output에 저장
                    output.positionCS = positionCS;
                    // 입력으로 받은 UV 좌표를 출력 구조체 output에 저장
                    output.uv = input.uv;
                    output.color = input.color;

                    return output;
                }

                // 프래그먼트 셰이더(fragment shader) 
                // 픽셀 단위로 호출되며, 각 픽셀의 최종 색상을 계산해 화면에 출력
                // 기본적으로 입력된 UV 좌표를 이용해 텍스처 색상을 샘플링하고, 
                // 최종적으로 머티리얼의 색상과 결합하여 픽셀의 색상을 반환하는 역할
                float4 frag(Varyings input) : SV_Target
                {
                    // UV 좌표 변환을 위한 계산
                    // input.uv.xy는 입력된 UV 좌표이며, _BaseMap_ST.xy는 텍스처 타일링(scale)을 나타내고,
                    // _BaseMap_ST.zw는 오프셋을 나타냅니다.
                    // 따라서, 기본 UV 좌표에 타일링 및 오프셋을 적용하여 최종적으로 텍스처 좌표를 결정합니다.
                    float2 baseMapUV = input.uv.xy * _BaseMap_ST.xy + _BaseMap_ST.zw;

                    // SAMPLE_TEXTURE2D 함수를 사용하여 텍스처를 샘플링합니다.
                    // _BaseMap은 텍스처 리소스, sampler_BaseMap은 해당 텍스처를 샘플링하는 샘플러입니다.
                    // baseMapUV는 변환된 UV 좌표입니다.
                    // 이 과정에서 지정된 텍스처 좌표를 기준으로 텍스처 색상을 가져옵니다.
                    float4 texColor = SAMPLE_TEXTURE2D(_BaseMap, sampler_BaseMap, baseMapUV);

                    // 텍스처 색상과 기본 색상을 곱하여 최종 색상을 계산합니다.
                    // _BaseColor는 머티리얼에서 설정된 색상이며, 이를 텍스처 샘플링 결과와 곱하여 결과적으로
                    // 텍스처와 색상이 결합된 최종 색상을 생성합니다.
                    float4 finalColor = texColor * _BaseColor;

                    // 최종 계산된 색상을 출력합니다. SV_Target은 이 값이 픽셀 셰이더의 출력으로 화면에 렌더링된다는 것을 의미합니다.
                    return finalColor;
                }

                ENDHLSL
            }
        }
}
</pre>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>



<h2 class="wp-block-heading">참고</h2>



<p class="wp-block-paragraph">&#8220;<strong>Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl</strong>&#8220;</p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">#ifndef UNIVERSAL_PIPELINE_CORE_INCLUDED
#define UNIVERSAL_PIPELINE_CORE_INCLUDED

// 현재 URP에서는 가상 텍스처링(Virtual Texturing)을 지원하지 않으므로,
// 가상 텍스처링을 사용하는 셰이더가 일반 텍스처 샘플링으로 대체되도록 강제합니다.
#define FORCE_VIRTUAL_TEXTURING_OFF 1

// 포워드 플러스(Forward+) 렌더링이 활성화된 경우와 그렇지 않은 경우에 따라
// 추가 조명을 지원하는지 여부와 포워드 플러스 사용 여부를 설정합니다.
#if defined(_FORWARD_PLUS)
#define _ADDITIONAL_LIGHTS 1
#undef _ADDITIONAL_LIGHTS_VERTEX
#define USE_FORWARD_PLUS 1
#else
#define USE_FORWARD_PLUS 0
#endif

// URP와 관련된 공통 헤더 파일들을 포함합니다.
#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Common.hlsl"
#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Packing.hlsl"
#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Version.hlsl"
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl"

// Z-버퍼의 방향과 관련된 매크로 정의
#if UNITY_REVERSED_Z
    // Z-버퍼가 반전된 경우에 대한 처리입니다. 
    // GL과 D3D의 경우 Z-값의 클립 범위를 조정합니다.
    #if (defined(SHADER_API_GLCORE) &amp;&amp; !defined(SHADER_API_SWITCH)) || defined(SHADER_API_GLES) || defined(SHADER_API_GLES3)
        // GL에서는 Z-클립 범위가 [near, -far]이므로, 이를 [0, far]로 변환합니다.
        #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) max((coord - _ProjectionParams.y)/(-_ProjectionParams.z-_ProjectionParams.y)*_ProjectionParams.z, 0)
    #else
        // D3D에서는 Z-클립 범위가 [near, 0]이므로, 이를 [0, far]로 변환합니다.
        // max를 사용하는 것은 경사 행렬의 경우 근접 평면이 올바르지 않거나 의미가 없을 때를 대비합니다.
        #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) max(((1.0-(coord)/_ProjectionParams.y)*_ProjectionParams.z),0)
    #endif
#elif UNITY_UV_STARTS_AT_TOP
    // D3D에서는 Z-클립 범위가 [0, far]이므로, 추가적인 변환이 필요하지 않습니다.
    #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) (coord)
#else
    // OpenGL에서는 Z-클립 범위가 [-near, far]이므로, 이를 [0, far]로 변환합니다.
    #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) max(((coord + _ProjectionParams.y)/(_ProjectionParams.z+_ProjectionParams.y))*_ProjectionParams.z, 0)
#endif

// 스테레오 렌더링 관련 매크로 정의
#if defined(UNITY_STEREO_INSTANCING_ENABLED) || defined(UNITY_STEREO_MULTIVIEW_ENABLED)
    // 스테레오 렌더링이 활성화된 경우, 텍스처를 배열로 처리합니다.
    #define SLICE_ARRAY_INDEX   unity_StereoEyeIndex

    // 스테레오 렌더링 시 사용하는 텍스처 배열 매크로 정의
    #define TEXTURE2D_X(textureName)                                        TEXTURE2D_ARRAY(textureName)
    #define TEXTURE2D_X_PARAM(textureName, samplerName)                     TEXTURE2D_ARRAY_PARAM(textureName, samplerName)
    #define TEXTURE2D_X_ARGS(textureName, samplerName)                      TEXTURE2D_ARRAY_ARGS(textureName, samplerName)
    #define TEXTURE2D_X_HALF(textureName)                                   TEXTURE2D_ARRAY_HALF(textureName)
    #define TEXTURE2D_X_FLOAT(textureName)                                  TEXTURE2D_ARRAY_FLOAT(textureName)

    #define LOAD_TEXTURE2D_X(textureName, unCoord2)                         LOAD_TEXTURE2D_ARRAY(textureName, unCoord2, SLICE_ARRAY_INDEX)
    #define LOAD_TEXTURE2D_X_LOD(textureName, unCoord2, lod)                LOAD_TEXTURE2D_ARRAY_LOD(textureName, unCoord2, SLICE_ARRAY_INDEX, lod)
    #define SAMPLE_TEXTURE2D_X(textureName, samplerName, coord2)            SAMPLE_TEXTURE2D_ARRAY(textureName, samplerName, coord2, SLICE_ARRAY_INDEX)
    #define SAMPLE_TEXTURE2D_X_LOD(textureName, samplerName, coord2, lod)   SAMPLE_TEXTURE2D_ARRAY_LOD(textureName, samplerName, coord2, SLICE_ARRAY_INDEX, lod)
    #define GATHER_TEXTURE2D_X(textureName, samplerName, coord2)            GATHER_TEXTURE2D_ARRAY(textureName, samplerName, coord2, SLICE_ARRAY_INDEX)
    #define GATHER_RED_TEXTURE2D_X(textureName, samplerName, coord2)        GATHER_RED_TEXTURE2D(textureName, samplerName, float3(coord2, SLICE_ARRAY_INDEX))
    #define GATHER_GREEN_TEXTURE2D_X(textureName, samplerName, coord2)      GATHER_GREEN_TEXTURE2D(textureName, samplerName, float3(coord2, SLICE_ARRAY_INDEX))
    #define GATHER_BLUE_TEXTURE2D_X(textureName, samplerName, coord2)       GATHER_BLUE_TEXTURE2D(textureName, samplerName, float3(coord2, SLICE_ARRAY_INDEX))

#else
    // 스테레오 렌더링이 비활성화된 경우, 일반적인 2D 텍스처 샘플링 매크로 정의
    #define SLICE_ARRAY_INDEX       0

    #define TEXTURE2D_X(textureName)                                        TEXTURE2D(textureName)
    #define TEXTURE2D_X_PARAM(textureName, samplerName)                     TEXTURE2D_PARAM(textureName, samplerName)
    #define TEXTURE2D_X_ARGS(textureName, samplerName)                      TEXTURE2D_ARGS(textureName, samplerName)
    #define TEXTURE2D_X_HALF(textureName)                                   TEXTURE2D_HALF(textureName)
    #define TEXTURE2D_X_FLOAT(textureName)                                  TEXTURE2D_FLOAT(textureName)

    #define LOAD_TEXTURE2D_X(textureName, unCoord2)                         LOAD_TEXTURE2D(textureName, unCoord2)
    #define LOAD_TEXTURE2D_X_LOD(textureName, unCoord2, lod)                LOAD_TEXTURE2D_LOD(textureName, unCoord2, lod)
    #define SAMPLE_TEXTURE2D_X(textureName, samplerName, coord2)            SAMPLE_TEXTURE2D(textureName, samplerName, coord2)
    #define SAMPLE_TEXTURE2D_X_LOD(textureName, samplerName, coord2, lod)   SAMPLE_TEXTURE2D_LOD(textureName, samplerName, coord2, lod)
    #define GATHER_TEXTURE2D_X(textureName, samplerName, coord2)            GATHER_TEXTURE2D(textureName, samplerName, coord2)
    #define GATHER_RED_TEXTURE2D_X(textureName, samplerName, coord2)        GATHER_RED_TEXTURE2D(textureName, samplerName, coord2)
    #define GATHER_GREEN_TEXTURE2D_X(textureName, samplerName, coord2)      GATHER_GREEN_TEXTURE2D(textureName, samplerName, coord2)
    #define GATHER_BLUE_TEXTURE2D_X(textureName, samplerName, coord2)       GATHER_BLUE_TEXTURE2D(textureName, samplerName, coord2)
#endif

///
/// 텍스처 샘플링 매크로 오버라이드: 스케일링 지원
///
/// mip bias가 지원되는 플랫폼에서는 모든 2D 텍스처 샘플링 작업을 글로벌 mip bias 기능을 지원하도록 재정의합니다.
/// 이 기능은 이미지 스케일링이 활성화된 경우 렌더링 품질을 향상시키기 위해 사용됩니다.
/// 최종 이미지 해상도에 따라 mip 레벨을 선택할 수 있도록 mip lod 계산에 bias 값을 추가합니다.

#ifdef PLATFORM_SAMPLE_TEXTURE2D_BIAS
    #ifdef  SAMPLE_TEXTURE2D
        #undef  SAMPLE_TEXTURE2D
        #define SAMPLE_TEXTURE2D(textureName, samplerName, coord2) \
            PLATFORM_SAMPLE_TEXTURE2D_BIAS(textureName, samplerName, coord2,  _GlobalMipBias.x)
    #endif
    #ifdef  SAMPLE_TEXTURE2D_BIAS
        #undef  SAMPLE_TEXTURE2D_BIAS
        #define SAMPLE_TEXTURE2D_BIAS(textureName, samplerName, coord2, bias) \
            PLATFORM_SAMPLE_TEXTURE2D_BIAS(textureName, samplerName, coord2,  (bias + _GlobalMipBias.x))
    #endif
#endif

#ifdef PLATFORM_SAMPLE_TEXTURE2D_GRAD
    #ifdef  SAMPLE_TEXTURE2D_GRAD
        #undef  SAMPLE_TEXTURE2D_GRAD
        #define SAMPLE_TEXTURE2D_GRAD(textureName, samplerName, coord2, dpdx, dpdy) \
            PLATFORM_SAMPLE_TEXTURE2D_GRAD(textureName, samplerName, coord2, (dpdx * _GlobalMipBias.y), (dpdy * _GlobalMipBias.y))
    #endif
#endif

#ifdef PLATFORM_SAMPLE_TEXTURE2D_ARRAY_BIAS
    #ifdef  SAMPLE_TEXTURE2D_ARRAY
        #undef  SAMPLE_TEXTURE2D_ARRAY
        #define SAMPLE_TEXTURE2D_ARRAY(textureName, samplerName, coord2, index) \
            PLATFORM_SAMPLE_TEXTURE2D_ARRAY_BIAS(textureName, samplerName, coord2, index, _GlobalMipBias.x)
    #endif
    #ifdef  SAMPLE_TEXTURE2D_ARRAY_BIAS
        #undef  SAMPLE_TEXTURE2D_ARRAY_BIAS
        #define SAMPLE_TEXTURE2D_ARRAY_BIAS(textureName, samplerName, coord2, index, bias) \
            PLATFORM_SAMPLE_TEXTURE2D_ARRAY_BIAS(textureName, samplerName, coord2, index, (bias + _GlobalMipBias.x))
    #endif
#endif

#ifdef PLATFORM_SAMPLE_TEXTURECUBE_BIAS
    #ifdef  SAMPLE_TEXTURECUBE
        #undef  SAMPLE_TEXTURECUBE
        #define SAMPLE_TEXTURECUBE(textureName, samplerName, coord3) \
            PLATFORM_SAMPLE_TEXTURECUBE_BIAS(textureName, samplerName, coord3, _GlobalMipBias.x)
    #endif
    #ifdef  SAMPLE_TEXTURECUBE_BIAS
        #undef  SAMPLE_TEXTURECUBE_BIAS
        #define SAMPLE_TEXTURECUBE_BIAS(textureName, samplerName, coord3, bias) \
            PLATFORM_SAMPLE_TEXTURECUBE_BIAS(textureName, samplerName, coord3, (bias + _GlobalMipBias.x))
    #endif
#endif

#ifdef PLATFORM_SAMPLE_TEXTURECUBE_ARRAY_BIAS
    #ifdef  SAMPLE_TEXTURECUBE_ARRAY
        #undef  SAMPLE_TEXTURECUBE_ARRAY
        #define SAMPLE_TEXTURECUBE_ARRAY(textureName, samplerName, coord3, index)\
            PLATFORM_SAMPLE_TEXTURECUBE_ARRAY_BIAS(textureName, samplerName, coord3, index, _GlobalMipBias.x)
    #endif

    #ifdef  SAMPLE_TEXTURECUBE_ARRAY_BIAS
        #undef  SAMPLE_TEXTURECUBE_ARRAY_BIAS
        #define SAMPLE_TEXTURECUBE_ARRAY_BIAS(textureName, samplerName, coord3, index, bias)\
            PLATFORM_SAMPLE_TEXTURECUBE_ARRAY_BIAS(textureName, samplerName, coord3, index, (bias + _GlobalMipBias.x))
    #endif
#endif

// 글로벌 mip bias 곱셈기
#define VT_GLOBAL_MIP_BIAS_MULTIPLIER (_GlobalMipBias.y)

// 구조체 정의
// 정점의 위치 정보를 담는 구조체입니다.
struct VertexPositionInputs
{
    float3 positionWS; // 월드 공간에서의 위치
    float3 positionVS; // 뷰 공간에서의 위치
    float4 positionCS; // 동차 클립 공간에서의 위치
    float4 positionNDC;// 동차 정규화된 장치 좌표
};

// 정점의 법선 정보를 담는 구조체입니다.
struct VertexNormalInputs
{
    real3 tangentWS;   // 월드 공간에서의 탄젠트 벡터
    real3 bitangentWS; // 월드 공간에서의 비탄젠트 벡터
    float3 normalWS;   // 월드 공간에서의 법선 벡터
}

// 추가적인 셰이더 변수와 함수 정의를 포함한 헤더 파일들
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/ShaderVariablesFunctions.hlsl"
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Deprecated.hlsl"

#endif</pre>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"><strong>&#8220;Packages/com.unity.render-pipelines.core/ShaderLibrary/SpaceTransforms.hlsl&#8221;</strong></p>



<pre class="EnlighterJSRAW" data-enlighter-language="cpp" data-enlighter-theme="" data-enlighter-highlight="" data-enlighter-linenumbers="false" data-enlighter-lineoffset="" data-enlighter-title="" data-enlighter-group="">#ifndef UNITY_SHADER_VARIABLES_FUNCTIONS_INCLUDED
#define UNITY_SHADER_VARIABLES_FUNCTIONS_INCLUDED

#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/SpaceTransforms.hlsl"

// 주의: '_WorldSpaceCameraPos'는 Unity의 레거시 코드에 의해 설정됩니다.
float3 GetPrimaryCameraPosition()
{
#if (SHADEROPTIONS_CAMERA_RELATIVE_RENDERING != 0)
    // 카메라 상대 렌더링이 활성화된 경우, 카메라 위치는 (0, 0, 0)으로 간주합니다.
    return float3(0, 0, 0);
#else
    // 그렇지 않은 경우, 실제 월드 좌표계를 기준으로 카메라 위치를 반환합니다.
    return _WorldSpaceCameraPos;
#endif
}

// 예: 주 카메라 또는 그림자를 캐스팅하는 빛의 위치일 수 있습니다.
float3 GetCurrentViewPosition()
{
#if defined(SHADERPASS) &amp;&amp; (SHADERPASS != SHADERPASS_SHADOWS)
    // 그림자 패스가 아닌 경우 주 카메라 위치를 반환합니다.
    return GetPrimaryCameraPosition();
#else
    // 일반적인 해결책입니다.
    // 그러나 주 카메라의 경우 '_WorldSpaceCameraPos'를 사용하는 것이 더 좋습니다. 이는 캐시 일관성에도 유리하고, 
    // 카메라 상대 렌더링이 활성화된 경우 위치를 0으로 설정할 수 있기 때문입니다.
    return UNITY_MATRIX_I_V._14_24_34;
#endif
}

// 현재 뷰의 월드 공간에서의 전방(중앙) 방향을 반환합니다.
float3 GetViewForwardDir()
{
    float4x4 viewMat = GetWorldToViewMatrix();
    return -viewMat[2].xyz;
}

// 현재 뷰가 원근 투영을 수행하는 경우 'true'를 반환합니다.
bool IsPerspectiveProjection()
{
#if defined(SHADERPASS) &amp;&amp; (SHADERPASS != SHADERPASS_SHADOWS)
    // 그림자 패스가 아닌 경우 원근 투영 여부를 검사합니다.
    return (unity_OrthoParams.w == 0);
#else
    // TODO: 그림자 패스에서 'unity_OrthoParams'를 설정해야 합니다.
    return UNITY_MATRIX_P[3][3] == 0;
#endif
}

// 월드 공간에서의 뷰 방향을 정규화하여 계산합니다 (뷰어를 향해 있음).
float3 GetWorldSpaceNormalizeViewDir(float3 positionWS)
{
    if (IsPerspectiveProjection())
    {
        // 원근 투영인 경우
        float3 V = GetCurrentViewPosition() - positionWS;
        return normalize(V);
    }
    else
    {
        // 정사영인 경우
        return -GetViewForwardDir();
    }
}

// UNITY_MATRIX_V는 Z 축이 뷰어를 향하는 오른손 좌표계를 정의합니다.
// 이 함수는 Z 축의 방향을 반전하여(앞쪽을 향하게) 뷰 공간 좌표계를 왼손 좌표계로 만듭니다.
void GetLeftHandedViewSpaceMatrices(out float4x4 viewMatrix, out float4x4 projMatrix)
{
    viewMatrix = UNITY_MATRIX_V;
    viewMatrix._31_32_33_34 = -viewMatrix._31_32_33_34;

    projMatrix = UNITY_MATRIX_P;
    projMatrix._13_23_33_43 = -projMatrix._13_23_33_43;
}

// Z 클리핑과 관련된 부분으로, 뒤집어진 Z 버퍼를 사용하는 경우에 대한 조건부 매크로 정의
#if UNITY_REVERSED_Z
    #if (defined(SHADER_API_GLCORE) &amp;&amp; !defined(SHADER_API_SWITCH)) || defined(SHADER_API_GLES) || defined(SHADER_API_GLES3)
        // 뒤집어진 Z를 사용하는 OpenGL에서는 클리핑 범위가 [near, -far]입니다.
        // 성능을 위해 리매핑하지 않고 그대로 사용합니다 (범위가 충분히 가깝기 때문입니다).
        #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) max(-(coord), 0)
    #else
        // 뒤집어진 Z를 사용하는 Direct3D에서는 클리핑 범위가 [near, 0]입니다.
        // [0, far]로 리매핑합니다.
        #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) max(((1.0-(coord)/_ProjectionParams.y)*_ProjectionParams.z),0)
    #endif
#elif UNITY_UV_STARTS_AT_TOP
    // 뒤집어진 Z를 사용하지 않는 Direct3D에서는 클리핑 범위가 [0, far]이므로 아무것도 할 필요가 없습니다.
    #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) (coord)
#else
    // OpenGL에서는 클리핑 범위가 [-near, far]이므로 성능을 위해 리매핑하지 않고 그대로 사용합니다 (범위가 충분히 가깝기 때문입니다).
    #define UNITY_Z_0_FAR_FROM_CLIPSPACE(coord) (coord)
#endif

#endif // UNITY_SHADER_VARIABLES_FUNCTIONS_INCLUDED</pre>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>



<p class="wp-block-paragraph"></p>
<p>The post <a href="https://lycos7560.com/unity/unity-urp-shader-vertex-attributes-struct-%ec%98%88%ec%8b%9c/38254/">Unity Urp Shader Vertex, Attributes, fragment  Unlit 예시</a> appeared first on <a href="https://lycos7560.com">어제와 내일의 나 그 사이의 이야기</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://lycos7560.com/unity/unity-urp-shader-vertex-attributes-struct-%ec%98%88%ec%8b%9c/38254/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
