You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
132 lines
5.0 KiB
132 lines
5.0 KiB
using UnityEngine;
|
|
using UnityEngine.Rendering;
|
|
using UnityEngine.Rendering.Universal;
|
|
using UnityEngine.Rendering.RenderGraphModule;
|
|
using UnityEngine.Rendering.RenderGraphModule.Util;
|
|
|
|
public class TiltShiftFeature : ScriptableRendererFeature
|
|
{
|
|
[System.Serializable]
|
|
public class Settings
|
|
{
|
|
[Tooltip("Vertical offset of the sharp focus band from screen centre. Positive = up.")]
|
|
[Range(-0.4f, 0.4f)]
|
|
public float centerOffset = 0f;
|
|
|
|
[Tooltip("Height of the fully-sharp band as a fraction of screen height.")]
|
|
[Range(0.01f, 0.8f)]
|
|
public float focusWidth = 0.2f;
|
|
|
|
[Tooltip("Distance over which blur fades in at each edge of the focus band.")]
|
|
[Range(0.01f, 0.4f)]
|
|
public float falloffRange = 0.15f;
|
|
|
|
[Tooltip("Maximum blur radius in pixels at the extreme top and bottom.")]
|
|
[Range(1f, 64f)]
|
|
public float maxBlurRadius = 20f;
|
|
|
|
[Tooltip("Samples per side per pass (higher = smoother blur, higher cost).")]
|
|
[Range(2, 20)]
|
|
public int sampleCount = 8;
|
|
|
|
public RenderPassEvent injectionPoint = RenderPassEvent.AfterRenderingPostProcessing;
|
|
}
|
|
|
|
public Settings settings = new Settings();
|
|
|
|
TiltShiftPass _pass;
|
|
Material _material;
|
|
|
|
public override void Create()
|
|
{
|
|
var shader = Shader.Find("Custom/TiltShift");
|
|
if (shader == null)
|
|
{
|
|
Debug.LogWarning("[TiltShift] Shader 'Custom/TiltShift' not found. " +
|
|
"Make sure TiltShift.shader is in the project.");
|
|
return;
|
|
}
|
|
|
|
_material = CoreUtils.CreateEngineMaterial(shader);
|
|
_pass = new TiltShiftPass(_material, settings);
|
|
_pass.renderPassEvent = settings.injectionPoint;
|
|
}
|
|
|
|
public override void AddRenderPasses(ScriptableRenderer renderer, ref RenderingData renderingData)
|
|
{
|
|
if (_material == null || _pass == null) return;
|
|
|
|
// Skip scene view and preview cameras to avoid visual noise.
|
|
var camType = renderingData.cameraData.cameraType;
|
|
if (camType == CameraType.Preview || camType == CameraType.Reflection) return;
|
|
|
|
_pass.UpdateSettings(settings);
|
|
renderer.EnqueuePass(_pass);
|
|
}
|
|
|
|
protected override void Dispose(bool disposing)
|
|
{
|
|
CoreUtils.Destroy(_material);
|
|
}
|
|
|
|
// -------------------------------------------------------------------------
|
|
|
|
class TiltShiftPass : ScriptableRenderPass
|
|
{
|
|
static readonly int s_CenterOffset = Shader.PropertyToID("_TiltShift_CenterOffset");
|
|
static readonly int s_FocusWidth = Shader.PropertyToID("_TiltShift_FocusWidth");
|
|
static readonly int s_FalloffRange = Shader.PropertyToID("_TiltShift_FalloffRange");
|
|
static readonly int s_MaxBlurRadius = Shader.PropertyToID("_TiltShift_MaxBlurRadius");
|
|
static readonly int s_SampleCount = Shader.PropertyToID("_TiltShift_SampleCount");
|
|
|
|
readonly Material _material;
|
|
Settings _settings;
|
|
|
|
public TiltShiftPass(Material material, Settings settings)
|
|
{
|
|
_material = material;
|
|
_settings = settings;
|
|
requiresIntermediateTexture = true;
|
|
}
|
|
|
|
public void UpdateSettings(Settings settings) => _settings = settings;
|
|
|
|
public override void RecordRenderGraph(RenderGraph renderGraph, ContextContainer frameData)
|
|
{
|
|
var resourceData = frameData.Get<UniversalResourceData>();
|
|
|
|
if (resourceData.isActiveTargetBackBuffer)
|
|
return;
|
|
|
|
// Push current settings to the material.
|
|
_material.SetFloat(s_CenterOffset, _settings.centerOffset);
|
|
_material.SetFloat(s_FocusWidth, _settings.focusWidth);
|
|
_material.SetFloat(s_FalloffRange, _settings.falloffRange);
|
|
_material.SetFloat(s_MaxBlurRadius, _settings.maxBlurRadius);
|
|
_material.SetInt(s_SampleCount, _settings.sampleCount);
|
|
|
|
var source = resourceData.activeColorTexture;
|
|
|
|
// Intermediate texture for horizontal-blur result.
|
|
var desc = renderGraph.GetTextureDesc(source);
|
|
desc.clearBuffer = false;
|
|
desc.name = "TiltShift_Temp";
|
|
TextureHandle temp = renderGraph.CreateTexture(desc);
|
|
|
|
// Final texture for vertical-blur result.
|
|
desc.name = "TiltShift_Final";
|
|
TextureHandle final = renderGraph.CreateTexture(desc);
|
|
|
|
// Pass 0 — horizontal blur: source → temp
|
|
var paraH = new RenderGraphUtils.BlitMaterialParameters(source, temp, _material, 0);
|
|
renderGraph.AddBlitPass(paraH, passName: "TiltShift_H");
|
|
|
|
// Pass 1 — vertical blur: temp → final
|
|
var paraV = new RenderGraphUtils.BlitMaterialParameters(temp, final, _material, 1);
|
|
renderGraph.AddBlitPass(paraV, passName: "TiltShift_V");
|
|
|
|
// Redirect the camera colour so subsequent passes see our result.
|
|
resourceData.cameraColor = final;
|
|
}
|
|
}
|
|
}
|
|
|