63 lines
3.6 KiB
HLSL
63 lines
3.6 KiB
HLSL
// SPDX-License-Identifier: (Not available for this version, you are only allowed to use this software if you have express permission from the copyright holder and agreed to the latest NiloToonURP EULA)
|
|
// Copyright (c) 2021 Kuroneko ShaderLab Limited
|
|
|
|
// For more information, visit -> https://github.com/ColinLeung-NiloCat/UnityURPToonLitShaderExample
|
|
|
|
// #pragma once is a safe guard best practice in almost every .hlsl,
|
|
// doing this can make sure your .hlsl's user can include this .hlsl anywhere anytime without producing any multi include conflict
|
|
#pragma once
|
|
|
|
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
// core functions
|
|
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
float Convert_SV_PositionZ_ToLinearViewSpaceDepthPerspectiveCamera(float rawDepthValueFromDepthTextureSample)
|
|
{
|
|
// if perspective camera, URP's LinearEyeDepth will handle everything for you
|
|
// https://docs.unity3d.com/Manual/SL-PlatformDifferences.html
|
|
// remember we can't use LinearEyeDepth() for orthographic camera!
|
|
return LinearEyeDepth(rawDepthValueFromDepthTextureSample,_ZBufferParams);
|
|
}
|
|
float Convert_SV_PositionZ_ToLinearViewSpaceDepthOrthographicCamera(float rawDepthValueFromDepthTextureSample)
|
|
{
|
|
// if orthographic camera, _CameraDepthTexture store scene depth linearly within 0~1 range, no matter which platform, even OpenGL
|
|
// if platform use reverse depth, make sure to 1-depth also
|
|
// https://docs.unity3d.com/Manual/SL-PlatformDifferences.html
|
|
#if defined(UNITY_REVERSED_Z)
|
|
// + UNITY_NEAR_CLIP_VALUE check here to support some android emulator also
|
|
// TODO: check if this check is still useful or not
|
|
rawDepthValueFromDepthTextureSample = UNITY_NEAR_CLIP_VALUE == 1 ? 1-rawDepthValueFromDepthTextureSample : rawDepthValueFromDepthTextureSample;
|
|
#endif
|
|
|
|
// simply lerp(near,far, [0,1]depth) to get view space depth
|
|
return lerp(_ProjectionParams.y, _ProjectionParams.z, rawDepthValueFromDepthTextureSample);
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
// high level helper functions
|
|
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
// expected input:
|
|
// - SV_POSITION.z in fragment shader
|
|
// - tex2D(_CameraDepthTexture).r, which is SV_POSITION.z of ShadowCaster pass
|
|
// *this function runs slower but support both orthographic and perspective camera projection
|
|
float Convert_SV_PositionZ_ToLinearViewSpaceDepth(float SV_POSITIONz)
|
|
{
|
|
// use a ? b : c (conditional move / movc) instead of if() here because if() itself may introduce more cost then a few extra math
|
|
return IsPerspectiveProjection() ?
|
|
Convert_SV_PositionZ_ToLinearViewSpaceDepthPerspectiveCamera(SV_POSITIONz):
|
|
Convert_SV_PositionZ_ToLinearViewSpaceDepthOrthographicCamera(SV_POSITIONz)
|
|
;
|
|
}
|
|
|
|
float LoadDepthTextureLinearDepthVS(int2 loadTexPos)
|
|
{
|
|
// clamp loadTexPos to prevent loading outside of _CameraDepthTexture's valid area
|
|
loadTexPos.x = max(loadTexPos.x,0);
|
|
loadTexPos.y = max(loadTexPos.y,0);
|
|
loadTexPos = min(loadTexPos,GetScaledScreenWidthHeight()-1);
|
|
|
|
float depthTextureRawSampleValue = LoadSceneDepth(loadTexPos); // using URP provided LoadSceneDepth(pos), this will make rendering correct in VR also
|
|
float depthTextureLinearDepthVS = Convert_SV_PositionZ_ToLinearViewSpaceDepth(depthTextureRawSampleValue);
|
|
return depthTextureLinearDepthVS;
|
|
}
|
|
|