Dither像素抖动shader代码
·
Shader "Unlit/CodeTest1"
{
Properties
{
}
SubShader
{
Tags { "RenderPipeline" = "UniversalPipeline"
"RenderType" = "TransparentCutout"
"Queue" = "AlphaTest"
"UniversalMaterialType" = "Unlit"
}
LOD 100
HLSLINCLUDE
#pragma target 4.5
#pragma prefer_hlslcc gles
#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Common.hlsl"
#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Filtering.hlsl"
ENDHLSL
Pass
{
Name "Forward"
Tags {"LightMode" = "UniversalForwardOnly"}
Blend One Zero, One Zero
ZWrite On
ZTest LEqual
HLSLPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl"
struct Attributes
{
float4 positionsOS : POSITION;
float2 texcoord : TEXCOORD0;
};
struct PackedVaryings
{
float4 positionCS : SV_POSITION;
float4 clipPosV : TEXCOORD0;
float3 positionWS : TEXCOORD1;
float4 uv : TEXCOORD6;
};
//解决跨平台坐标系统不一致的问题
float4 ScreenPositionNormalizedToPixel( float4 screenPosNorm)
{
float4 screenPosPixel = screenPosNorm * float4(_ScreenParams.xy, 1,1);
#if UNITY_UV_STARTS_AT_TOP //如果UV从坐标顶部开始,如果内置变量X小于0,垂直反转Y坐标
screenPosPixel.xy = float2(screenPosPixel.x, (_ProjectionParams.x < 0)? _ScreenParams.y - screenPosPixel.y : screenPosPixel.y);
#else //如果UV从底部开始,和上面情况相反
screenPosPixel.xy = float2(screenPosPixel.x, (_ProjectionParams.x > 0)? _ScreenParams.y - screenPosPixel.y : screenPosPixel.y);
#endif
return screenPosPixel;
}
//像素化
inline float Dither8x8Bayer( int x, int y )
{
const float dither[ 64 ] = {
1, 49, 13, 61, 4, 52, 16, 64,
33, 17, 45, 29, 36, 20, 48, 32,
9, 57, 5, 53, 12, 60, 8, 56,
41, 25, 37, 21, 44, 28, 40, 24,
3, 51, 15, 63, 2, 50, 14, 62,
35, 19, 47, 31, 34, 18, 46, 30,
11, 59, 7, 55, 10, 58, 6, 54,
43, 27, 39, 23, 42, 26, 38, 22};
int r = y * 8 + x;
return dither[ r ] / 64; // same # of instructions as pre-dividing due to compiler magic
}
PackedVaryings vert (Attributes input)
{
PackedVaryings output = (PackedVaryings)0;
VertexPositionInputs vertexInput = GetVertexPositionInputs( input.positionsOS.xyz);
output.positionCS = vertexInput.positionCS;
output.clipPosV = vertexInput.positionCS;
output.positionWS = vertexInput.positionWS;
output.uv = half4(input.texcoord.xy,0,0);
return output;
}
half4 frag (PackedVaryings input) : SV_Target
{
float4 ScreenPos = ComputeScreenPos (input.clipPosV); //裁剪to屏幕(齐次)
half4 positionSSNorm = ScreenPos / ScreenPos.w; //统一深度
positionSSNorm.z = (UNITY_NEAR_CLIP_VALUE >= 0 ) ? positionSSNorm.z : positionSSNorm.z * 0.5 + 0.5;
half4 positionSS_Pixel = ScreenPositionNormalizedToPixel( positionSSNorm);
half dither = Dither8x8Bayer(fmod(positionSS_Pixel.x, 8 ), fmod(positionSS_Pixel.y, 8));
dither = step(dither, input.uv.x);
clip(dither - 0.5);
return half4(1,1,1,1);
}
ENDHLSL
}
}
}
更多推荐
所有评论(0)