feat : add a cathodic efect on the player cam

This commit is contained in:
Thibault Pouch
2026-03-13 18:38:48 +01:00
parent 935b4c089a
commit ab434be65f
6 changed files with 342 additions and 29 deletions

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 97a4ae8015df4732ac9524441048a765
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,173 @@
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.Rendering.RenderGraphModule;
using UnityEngine.Rendering.RenderGraphModule.Util;
using UnityEngine.Rendering.Universal;
public class CRTRendererFeature : ScriptableRendererFeature
{
[System.Serializable]
public class CRTSettings
{
public bool EffectEnabled = true;
public RenderPassEvent PassEvent = RenderPassEvent.AfterRenderingPostProcessing;
public Shader CRTShader;
[Range(0f, 1f)] public float Intensity = 0.65f;
[Range(0f, 2f)] public float ScanlineDensity = 1.2f;
[Range(0f, 1f)] public float ScanlineStrength = 0.18f;
[Range(0f, 0.2f)] public float Curvature = 0.04f;
[Range(0f, 1f)] public float VignetteStrength = 0.28f;
[Range(0f, 0.05f)] public float ChromaticAberration = 0.004f;
[Range(0f, 0.2f)] public float NoiseStrength = 0.03f;
[Range(0f, 0.1f)] public float FlickerStrength = 0.015f;
}
class CRTPass : ScriptableRenderPass
{
private readonly ProfilingSampler m_ProfilingSampler = new("CRT Effect");
private Material m_Material;
private CRTSettings m_Settings;
private RTHandle m_TempColorTexture;
public void Setup(Material material, CRTSettings settings)
{
m_Material = material;
m_Settings = settings;
renderPassEvent = settings.PassEvent;
requiresIntermediateTexture = true;
}
public override void RecordRenderGraph(RenderGraph renderGraph, ContextContainer frameData)
{
if (m_Material == null || m_Settings == null || !m_Settings.EffectEnabled)
{
return;
}
UniversalResourceData resourceData = frameData.Get<UniversalResourceData>();
if (resourceData.isActiveTargetBackBuffer)
{
return;
}
m_Material.SetFloat("_Intensity", m_Settings.Intensity);
m_Material.SetFloat("_ScanlineDensity", m_Settings.ScanlineDensity);
m_Material.SetFloat("_ScanlineStrength", m_Settings.ScanlineStrength);
m_Material.SetFloat("_Curvature", m_Settings.Curvature);
m_Material.SetFloat("_VignetteStrength", m_Settings.VignetteStrength);
m_Material.SetFloat("_ChromaticAberration", m_Settings.ChromaticAberration);
m_Material.SetFloat("_NoiseStrength", m_Settings.NoiseStrength);
m_Material.SetFloat("_FlickerStrength", m_Settings.FlickerStrength);
TextureHandle source = resourceData.activeColorTexture;
TextureDesc destinationDesc = renderGraph.GetTextureDesc(source);
destinationDesc.name = "CameraColor-CRT";
destinationDesc.clearBuffer = false;
TextureHandle destination = renderGraph.CreateTexture(destinationDesc);
RenderGraphUtils.BlitMaterialParameters blitParams = new(source, destination, m_Material, 0);
renderGraph.AddBlitPass(blitParams, "CRT Effect");
resourceData.cameraColor = destination;
}
public override void Configure(CommandBuffer cmd, RenderTextureDescriptor cameraTextureDescriptor)
{
cameraTextureDescriptor.depthBufferBits = 0;
RenderingUtils.ReAllocateHandleIfNeeded(
ref m_TempColorTexture,
cameraTextureDescriptor,
FilterMode.Bilinear,
TextureWrapMode.Clamp,
name: "_CRTTempColorTexture"
);
}
public override void Execute(ScriptableRenderContext context, ref RenderingData renderingData)
{
if (m_Material == null || m_Settings == null || !m_Settings.EffectEnabled)
{
return;
}
if (renderingData.cameraData.isSceneViewCamera)
{
return;
}
CommandBuffer cmd = CommandBufferPool.Get();
using (new ProfilingScope(cmd, m_ProfilingSampler))
{
m_Material.SetFloat("_Intensity", m_Settings.Intensity);
m_Material.SetFloat("_ScanlineDensity", m_Settings.ScanlineDensity);
m_Material.SetFloat("_ScanlineStrength", m_Settings.ScanlineStrength);
m_Material.SetFloat("_Curvature", m_Settings.Curvature);
m_Material.SetFloat("_VignetteStrength", m_Settings.VignetteStrength);
m_Material.SetFloat("_ChromaticAberration", m_Settings.ChromaticAberration);
m_Material.SetFloat("_NoiseStrength", m_Settings.NoiseStrength);
m_Material.SetFloat("_FlickerStrength", m_Settings.FlickerStrength);
RTHandle source = renderingData.cameraData.renderer.cameraColorTargetHandle;
Blitter.BlitCameraTexture(cmd, source, m_TempColorTexture, m_Material, 0);
Blitter.BlitCameraTexture(cmd, m_TempColorTexture, source);
}
context.ExecuteCommandBuffer(cmd);
CommandBufferPool.Release(cmd);
}
public void Dispose()
{
m_TempColorTexture?.Release();
m_TempColorTexture = null;
}
}
public CRTSettings Settings = new();
private CRTPass m_Pass;
private Material m_Material;
public override void Create()
{
if (Settings.CRTShader == null)
{
Settings.CRTShader = Shader.Find("Hidden/HeadlessHazard/CRT");
}
if (Settings.CRTShader != null)
{
m_Material = CoreUtils.CreateEngineMaterial(Settings.CRTShader);
}
m_Pass ??= new CRTPass();
}
public override void AddRenderPasses(ScriptableRenderer renderer, ref RenderingData renderingData)
{
if (m_Material == null || !Settings.EffectEnabled)
{
return;
}
if (renderingData.cameraData.cameraType != CameraType.Game)
{
return;
}
m_Pass.Setup(m_Material, Settings);
renderer.EnqueuePass(m_Pass);
}
protected override void Dispose(bool disposing)
{
m_Pass?.Dispose();
m_Pass = null;
CoreUtils.Destroy(m_Material);
m_Material = null;
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 4f2de7a6cfbd47c8bc740d43bb991205
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,97 @@
Shader "Hidden/HeadlessHazard/CRT"
{
Properties
{
_Intensity ("Intensity", Range(0,1)) = 0.65
_ScanlineDensity ("Scanline Density", Range(0,2)) = 1.2
_ScanlineStrength ("Scanline Strength", Range(0,1)) = 0.18
_Curvature ("Curvature", Range(0,0.2)) = 0.04
_VignetteStrength ("Vignette Strength", Range(0,1)) = 0.28
_ChromaticAberration ("Chromatic Aberration", Range(0,0.05)) = 0.004
_NoiseStrength ("Noise Strength", Range(0,0.2)) = 0.03
_FlickerStrength ("Flicker Strength", Range(0,0.1)) = 0.015
}
SubShader
{
Tags { "RenderPipeline" = "UniversalPipeline" }
Pass
{
Name "CRT"
ZWrite Off
ZTest Always
Cull Off
Blend One Zero
HLSLPROGRAM
#pragma vertex Vert
#pragma fragment Frag
#pragma target 3.5
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
#include "Packages/com.unity.render-pipelines.core/Runtime/Utilities/Blit.hlsl"
float _Intensity;
float _ScanlineDensity;
float _ScanlineStrength;
float _Curvature;
float _VignetteStrength;
float _ChromaticAberration;
float _NoiseStrength;
float _FlickerStrength;
float Random01(float2 seed)
{
return frac(sin(dot(seed, float2(12.9898, 78.233))) * 43758.5453);
}
float2 DistortUV(float2 uv, float curvature)
{
float2 center = uv * 2.0 - 1.0;
float radius2 = dot(center, center);
center *= 1.0 + (radius2 * curvature);
return center * 0.5 + 0.5;
}
half4 Frag(Varyings input) : SV_Target
{
float2 uv = input.texcoord;
float2 curvedUV = DistortUV(uv, _Curvature);
if (curvedUV.x < 0.0 || curvedUV.x > 1.0 || curvedUV.y < 0.0 || curvedUV.y > 1.0)
{
return half4(0.0, 0.0, 0.0, 1.0);
}
float2 fromCenter = curvedUV - 0.5;
float2 aberrationOffset = fromCenter * _ChromaticAberration;
half red = SAMPLE_TEXTURE2D_X(_BlitTexture, sampler_LinearClamp, curvedUV + aberrationOffset).r;
half green = SAMPLE_TEXTURE2D_X(_BlitTexture, sampler_LinearClamp, curvedUV).g;
half blue = SAMPLE_TEXTURE2D_X(_BlitTexture, sampler_LinearClamp, curvedUV - aberrationOffset).b;
half3 color = half3(red, green, blue);
float scanlineWave = sin((curvedUV.y * _ScreenParams.y * 0.5 * _ScanlineDensity) + (_Time.y * 18.0));
float scanlineMask = lerp(1.0, saturate(0.7 + 0.3 * scanlineWave), _ScanlineStrength);
color *= scanlineMask;
float noise = Random01(curvedUV * _ScreenParams.xy + _Time.yy * 37.0) - 0.5;
color += noise * _NoiseStrength;
float flicker = 1.0 - (_FlickerStrength * (0.5 + 0.5 * sin(_Time.y * 32.0)));
color *= flicker;
float2 vignetteUV = curvedUV * (1.0 - curvedUV.yx);
float vignette = saturate(pow(vignetteUV.x * vignetteUV.y * 18.0, 0.2));
color *= lerp(1.0 - _VignetteStrength, 1.0, vignette);
half3 baseColor = SAMPLE_TEXTURE2D_X(_BlitTexture, sampler_LinearClamp, uv).rgb;
half3 finalColor = lerp(baseColor, color, _Intensity);
return half4(finalColor, 1.0);
}
ENDHLSL
}
}
}

View File

@@ -0,0 +1,10 @@
fileFormatVersion: 2
guid: 0a9f7eb85c2f4f9f8ec82c8565f4e8b1
ShaderImporter:
externalObjects: {}
defaultTextures: []
nonModifiableTextures: []
preprocessorOverride: 0
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -1,5 +1,30 @@
%YAML 1.1 %YAML 1.1
%TAG !u! tag:unity3d.com,2011: %TAG !u! tag:unity3d.com,2011:
--- !u!114 &-4377071725885749089
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 0}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 4f2de7a6cfbd47c8bc740d43bb991205, type: 3}
m_Name: CRTRendererFeature
m_EditorClassIdentifier: Assembly-CSharp::CRTRendererFeature
m_Active: 1
Settings:
EffectEnabled: 1
PassEvent: 600
CRTShader: {fileID: 4800000, guid: 0a9f7eb85c2f4f9f8ec82c8565f4e8b1, type: 3}
Intensity: 0.65
ScanlineDensity: 1.2
ScanlineStrength: 0.18
Curvature: 0.04
VignetteStrength: 0.28
ChromaticAberration: 0.004
NoiseStrength: 0.03
FlickerStrength: 0.015
--- !u!114 &11400000 --- !u!114 &11400000
MonoBehaviour: MonoBehaviour:
m_ObjectHideFlags: 0 m_ObjectHideFlags: 0
@@ -13,32 +38,28 @@ MonoBehaviour:
m_Name: PC_Renderer m_Name: PC_Renderer
m_EditorClassIdentifier: m_EditorClassIdentifier:
debugShaders: debugShaders:
debugReplacementPS: {fileID: 4800000, guid: cf852408f2e174538bcd9b7fda1c5ae7, debugReplacementPS: {fileID: 4800000, guid: cf852408f2e174538bcd9b7fda1c5ae7, type: 3}
type: 3}
hdrDebugViewPS: {fileID: 4800000, guid: 573620ae32aec764abd4d728906d2587, type: 3} hdrDebugViewPS: {fileID: 4800000, guid: 573620ae32aec764abd4d728906d2587, type: 3}
probeVolumeSamplingDebugComputeShader: {fileID: 7200000, guid: 53626a513ea68ce47b59dc1299fe3959, probeVolumeSamplingDebugComputeShader: {fileID: 7200000, guid: 53626a513ea68ce47b59dc1299fe3959, type: 3}
type: 3}
probeVolumeResources: probeVolumeResources:
probeVolumeDebugShader: {fileID: 4800000, guid: e5c6678ed2aaa91408dd3df699057aae, probeVolumeDebugShader: {fileID: 4800000, guid: e5c6678ed2aaa91408dd3df699057aae, type: 3}
type: 3} probeVolumeFragmentationDebugShader: {fileID: 4800000, guid: 03cfc4915c15d504a9ed85ecc404e607, type: 3}
probeVolumeFragmentationDebugShader: {fileID: 4800000, guid: 03cfc4915c15d504a9ed85ecc404e607, probeVolumeOffsetDebugShader: {fileID: 4800000, guid: 53a11f4ebaebf4049b3638ef78dc9664, type: 3}
type: 3} probeVolumeSamplingDebugShader: {fileID: 4800000, guid: 8f96cd657dc40064aa21efcc7e50a2e7, type: 3}
probeVolumeOffsetDebugShader: {fileID: 4800000, guid: 53a11f4ebaebf4049b3638ef78dc9664, probeSamplingDebugMesh: {fileID: -3555484719484374845, guid: 57d7c4c16e2765b47a4d2069b311bffe, type: 3}
type: 3} probeSamplingDebugTexture: {fileID: 2800000, guid: 24ec0e140fb444a44ab96ee80844e18e, type: 3}
probeVolumeSamplingDebugShader: {fileID: 4800000, guid: 8f96cd657dc40064aa21efcc7e50a2e7, probeVolumeBlendStatesCS: {fileID: 7200000, guid: b9a23f869c4fd45f19c5ada54dd82176, type: 3}
type: 3}
probeSamplingDebugMesh: {fileID: -3555484719484374845, guid: 57d7c4c16e2765b47a4d2069b311bffe,
type: 3}
probeSamplingDebugTexture: {fileID: 2800000, guid: 24ec0e140fb444a44ab96ee80844e18e,
type: 3}
probeVolumeBlendStatesCS: {fileID: 7200000, guid: b9a23f869c4fd45f19c5ada54dd82176,
type: 3}
m_RendererFeatures: m_RendererFeatures:
- {fileID: 7833122117494664109} - {fileID: 7833122117494664109}
m_RendererFeatureMap: ad6b866f10d7b46c - {fileID: -4377071725885749089}
m_RendererFeatureMap: ad6b866f10d7b46c9f882cbe748441c3
m_UseNativeRenderPass: 1 m_UseNativeRenderPass: 1
xrSystemData: {fileID: 0}
postProcessData: {fileID: 11400000, guid: 41439944d30ece34e96484bdb6645b55, type: 2} postProcessData: {fileID: 11400000, guid: 41439944d30ece34e96484bdb6645b55, type: 2}
m_AssetVersion: 2 m_AssetVersion: 3
m_PrepassLayerMask:
serializedVersion: 2
m_Bits: 4294967295
m_OpaqueLayerMask: m_OpaqueLayerMask:
serializedVersion: 2 serializedVersion: 2
m_Bits: 4294967295 m_Bits: 4294967295
@@ -56,6 +77,8 @@ MonoBehaviour:
m_RenderingMode: 2 m_RenderingMode: 2
m_DepthPrimingMode: 0 m_DepthPrimingMode: 0
m_CopyDepthMode: 0 m_CopyDepthMode: 0
m_DepthAttachmentFormat: 0
m_DepthTextureFormat: 0
m_AccurateGbufferNormals: 0 m_AccurateGbufferNormals: 0
m_IntermediateTextureMode: 0 m_IntermediateTextureMode: 0
--- !u!114 &7833122117494664109 --- !u!114 &7833122117494664109
@@ -84,12 +107,3 @@ MonoBehaviour:
BlurQuality: 0 BlurQuality: 0
Falloff: 100 Falloff: 100
SampleCount: -1 SampleCount: -1
m_BlueNoise256Textures:
- {fileID: 2800000, guid: 36f118343fc974119bee3d09e2111500, type: 3}
- {fileID: 2800000, guid: 4b7b083e6b6734e8bb2838b0b50a0bc8, type: 3}
- {fileID: 2800000, guid: c06cc21c692f94f5fb5206247191eeee, type: 3}
- {fileID: 2800000, guid: cb76dd40fa7654f9587f6a344f125c9a, type: 3}
- {fileID: 2800000, guid: e32226222ff144b24bf3a5a451de54bc, type: 3}
- {fileID: 2800000, guid: 3302065f671a8450b82c9ddf07426f3a, type: 3}
- {fileID: 2800000, guid: 56a77a3e8d64f47b6afe9e3c95cb57d5, type: 3}
m_Shader: {fileID: 4800000, guid: 0849e84e3d62649e8882e9d6f056a017, type: 3}