Hyluss

post outline shader

Jul 24th, 2019
263
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. // Upgrade NOTE: replaced 'mul(UNITY_MATRIX_MVP,*)' with 'UnityObjectToClipPos(*)'
  2.  
  3. Shader "Custom/Post Outline"
  4. {
  5.     Properties
  6.     {
  7.          _Color("Main Color", Color) = (0.5,0.5,0.5,1)
  8.         _MainTex("Main Texture",2D) = "black"{}
  9.         _SceneTex("Scene Texture",2D) = "black"{}
  10.     }
  11.    
  12.     SubShader
  13.     {
  14.         // Fog { Mode Off }
  15.          ZWrite off
  16.              Cull Off
  17.             Lighting Off
  18.  
  19.         Pass
  20.         {
  21.             CGPROGRAM
  22.  
  23.             sampler2D _MainTex;
  24.     float4 _Color;
  25.  
  26.             //<SamplerName>_TexelSize is a float2 that says how much screen space a texel occupies.
  27.             float2 _MainTex_TexelSize;
  28.  
  29.             #pragma vertex vert
  30.             #pragma fragment frag
  31.             #include "UnityCG.cginc"
  32.  
  33.             struct v2f
  34.             {
  35.                 float4 pos : SV_POSITION;
  36.                 float2 uvs : TEXCOORD0;
  37.             };
  38.  
  39.             v2f vert(appdata_base v)
  40.             {
  41.                 v2f o;
  42.  
  43.                 //Despite the fact that we are only drawing a quad to the screen, Unity requires us to multiply vertices by our MVP matrix, presumably to keep things working when inexperienced people try copying code from other shaders.
  44.                 o.pos = UnityObjectToClipPos(v.vertex);
  45.  
  46.                 //Also, we need to fix the UVs to match our screen space coordinates. There is a Unity define for this that should normally be used.
  47.                 o.uvs = o.pos.xy / 2 + 0.5;
  48.  
  49.                 return o;
  50.             }
  51.  
  52.  
  53.             half frag(v2f i) : COLOR
  54.             {
  55.                 //arbitrary number of iterations for now
  56.                 int NumberOfIterations = 4;
  57.  
  58.                 //split texel size into smaller words
  59.                 float TX_x = _MainTex_TexelSize.x;
  60.  
  61.                 //and a final intensity that increments based on surrounding intensities.
  62.                 float ColorIntensityInRadius;
  63.  
  64.                 //for every iteration we need to do horizontally
  65.                 for (int k = 0; k < NumberOfIterations; k += 1)
  66.                 {
  67.                     //increase our output color by the pixels in the area
  68.                     ColorIntensityInRadius += tex2D(
  69.                         _MainTex,
  70.                         i.uvs.xy + float2((k - NumberOfIterations / 2)*TX_x, 0)).r / NumberOfIterations;
  71.                 }
  72.                 //output some intensity of teal
  73.             //  ColorIntensityInRadius = 0;
  74.  
  75.                 return ColorIntensityInRadius;
  76.             }
  77.         ENDCG
  78.  
  79.         }
  80.         //end pass    
  81.  
  82.         GrabPass{}
  83.  
  84.         Pass
  85.         {
  86.                 ZWrite off
  87.  
  88.             CGPROGRAM
  89.  
  90.             sampler2D _MainTex;
  91.             sampler2D _SceneTex;
  92.  
  93.             //we need to declare a sampler2D by the name of "_GrabTexture" that Unity can write to during GrabPass{}
  94.             sampler2D _GrabTexture;
  95.  
  96.             //<SamplerName>_TexelSize is a float2 that says how much screen space a texel occupies.
  97.             float2 _GrabTexture_TexelSize;
  98.  
  99.             #pragma vertex vert
  100.             #pragma fragment frag
  101.             #include "UnityCG.cginc"
  102.  
  103.             struct v2f
  104.             {
  105.                 float4 pos : SV_POSITION;
  106.                 float2 uvs : TEXCOORD0;
  107.             };
  108.  
  109.             v2f vert(appdata_base v)
  110.             {
  111.                 v2f o;
  112.  
  113.                 //Despite the fact that we are only drawing a quad to the screen, Unity requires us to multiply vertices by our MVP matrix, presumably to keep things working when inexperienced people try copying code from other shaders.
  114.                 o.pos = UnityObjectToClipPos(v.vertex);
  115.  
  116.                 //Also, we need to fix the UVs to match our screen space coordinates. There is a Unity define for this that should normally be used.
  117.                 o.uvs = o.pos.xy / 2 + 0.5; // smooth rough line
  118.  
  119.                 return o;
  120.             }
  121.  
  122.  
  123.             half4 frag(v2f i) : COLOR
  124.             {
  125.                 //arbitrary number of iterations for now
  126.                 int NumberOfIterations = 20;
  127.  
  128.                 //split texel size into smaller words
  129.                 float TX_y = _GrabTexture_TexelSize.y; //here we can change outline width
  130.  
  131.                 //and a final intensity that increments based on surrounding intensities.
  132.                 half ColorIntensityInRadius = 0;
  133.  
  134.                 //if something already exists underneath the fragment (in the original texture), discard the fragment.
  135.                 if (tex2D(_MainTex,i.uvs.xy).r > 0)
  136.                 {
  137.                     return tex2D(_SceneTex,float2(i.uvs.x,1 - i.uvs.y));
  138.                 }
  139.  
  140.                 //for every iteration we need to do vertically
  141.                 for (int j = 0; j < NumberOfIterations; j += 1)
  142.                 {
  143.                     //increase our output color by the pixels in the area
  144.                     ColorIntensityInRadius += tex2D(
  145.                                                     _GrabTexture,
  146.                                                     float2(i.uvs.x,1 - i.uvs.y) + float2
  147.                                                                                     (
  148.                                                                                         0,
  149.                                                                                         (j - NumberOfIterations / 2)*TX_y
  150.                                                                                     )
  151.                                                 //  ).r / (NumberOfIterations);
  152.                                                     ).r / (1);
  153.                 }
  154.  
  155.                 //this is alpha blending, but we can't use HW blending unless we make a third pass, so this is probably cheaper.
  156.             //  half4 outcolor = ColorIntensityInRadius * half4(0,1,1,1) * 2 + (1 - ColorIntensityInRadius)*tex2D(_SceneTex,float2(i.uvs.x,1 - i.uvs.y));
  157.                 half4 outcolor = half4(0, 0, 0, 0)  + (1 - ColorIntensityInRadius)  *tex2D(_SceneTex, float2(i.uvs.x, 1 - i.uvs.y));
  158.  
  159.             //  outcolor = (outcolor[0], outcolor[1], outcolor[2], 0.5f);
  160.                 return outcolor;
  161.             }
  162.         ENDCG
  163.         }
  164.         //end pass    
  165.     }
  166.     //end subshader
  167. }
  168. //end shader
RAW Paste Data