142 lines
3.6 KiB
C#
142 lines
3.6 KiB
C#
using UnityEngine;
|
|
using UnityEngine.Rendering;
|
|
using UnityEngine.XR;
|
|
|
|
namespace LuxWater
|
|
{
|
|
[RequireComponent(typeof(Camera))]
|
|
public class LuxWater_UnderWaterBlur : MonoBehaviour
|
|
{
|
|
[Space(6f)]
|
|
[LuxWater_HelpBtn("h.3a2840a53u5j")]
|
|
public float blurSpread = 0.6f;
|
|
|
|
public int blurDownSample = 4;
|
|
|
|
public int blurIterations = 4;
|
|
|
|
private Vector2[] m_offsets = new Vector2[4];
|
|
|
|
private Material blurMaterial;
|
|
|
|
private Material blitMaterial;
|
|
|
|
private LuxWater_UnderWaterRendering waterrendermanager;
|
|
|
|
private bool doBlur;
|
|
|
|
private bool initBlur = true;
|
|
|
|
private Camera cam;
|
|
|
|
private void OnEnable()
|
|
{
|
|
blurMaterial = new Material(Shader.Find("Hidden/Lux Water/BlurEffectConeTap"));
|
|
blitMaterial = new Material(Shader.Find("Hidden/Lux Water/UnderWaterPost"));
|
|
cam = GetComponent<Camera>();
|
|
Invoke("GetWaterrendermanagerInstance", 0f);
|
|
}
|
|
|
|
private void OnDisable()
|
|
{
|
|
if ((bool)blurMaterial)
|
|
{
|
|
Object.DestroyImmediate(blurMaterial);
|
|
}
|
|
if ((bool)blitMaterial)
|
|
{
|
|
Object.DestroyImmediate(blitMaterial);
|
|
}
|
|
}
|
|
|
|
private void GetWaterrendermanagerInstance()
|
|
{
|
|
waterrendermanager = LuxWater_UnderWaterRendering.instance;
|
|
}
|
|
|
|
private void OnRenderImage(RenderTexture src, RenderTexture dest)
|
|
{
|
|
if (waterrendermanager == null)
|
|
{
|
|
Graphics.Blit(src, dest);
|
|
return;
|
|
}
|
|
TextureDimension dimension = TextureDimension.Tex2D;
|
|
int volumeDepth = 1;
|
|
VRTextureUsage vrUsage = VRTextureUsage.None;
|
|
if (cam.stereoEnabled)
|
|
{
|
|
vrUsage = VRTextureUsage.OneEye;
|
|
if (XRSettings.stereoRenderingMode == XRSettings.StereoRenderingMode.SinglePassInstanced)
|
|
{
|
|
dimension = TextureDimension.Tex2DArray;
|
|
volumeDepth = 2;
|
|
vrUsage = VRTextureUsage.TwoEyes;
|
|
}
|
|
}
|
|
doBlur = waterrendermanager.activeWaterVolume > -1;
|
|
if (doBlur || initBlur)
|
|
{
|
|
initBlur = false;
|
|
int width = src.width / blurDownSample;
|
|
int height = src.height / blurDownSample;
|
|
RenderTextureDescriptor desc = new RenderTextureDescriptor(width, height, RenderTextureFormat.DefaultHDR, 0);
|
|
desc.dimension = dimension;
|
|
desc.volumeDepth = volumeDepth;
|
|
desc.vrUsage = vrUsage;
|
|
RenderTexture renderTexture = RenderTexture.GetTemporary(desc);
|
|
DownSample(src, renderTexture);
|
|
for (int i = 0; i < blurIterations; i++)
|
|
{
|
|
RenderTexture temporary = RenderTexture.GetTemporary(desc);
|
|
FourTapCone(renderTexture, temporary, i);
|
|
RenderTexture.ReleaseTemporary(renderTexture);
|
|
renderTexture = temporary;
|
|
}
|
|
Shader.SetGlobalTexture("_UnderWaterTex", renderTexture);
|
|
Graphics.Blit(src, dest, blitMaterial, 1);
|
|
RenderTexture.ReleaseTemporary(renderTexture);
|
|
}
|
|
else
|
|
{
|
|
Graphics.Blit(src, dest);
|
|
}
|
|
}
|
|
|
|
private void FourTapCone(RenderTexture source, RenderTexture dest, int iteration)
|
|
{
|
|
float num = 0.5f + (float)iteration * blurSpread;
|
|
m_offsets[0].x = 0f - num;
|
|
m_offsets[0].y = 0f - num;
|
|
m_offsets[1].x = 0f - num;
|
|
m_offsets[1].y = num;
|
|
m_offsets[2].x = num;
|
|
m_offsets[2].y = num;
|
|
m_offsets[3].x = num;
|
|
m_offsets[3].y = 0f - num;
|
|
if (iteration == 0)
|
|
{
|
|
Graphics.BlitMultiTap(source, dest, blurMaterial, m_offsets);
|
|
}
|
|
else
|
|
{
|
|
Graphics.BlitMultiTap(source, dest, blurMaterial, m_offsets);
|
|
}
|
|
}
|
|
|
|
private void DownSample(RenderTexture source, RenderTexture dest)
|
|
{
|
|
float num = 1f;
|
|
m_offsets[0].x = 0f - num;
|
|
m_offsets[0].y = 0f - num;
|
|
m_offsets[1].x = 0f - num;
|
|
m_offsets[1].y = num;
|
|
m_offsets[2].x = num;
|
|
m_offsets[2].y = num;
|
|
m_offsets[3].x = num;
|
|
m_offsets[3].y = 0f - num;
|
|
Graphics.BlitMultiTap(source, dest, blurMaterial, m_offsets);
|
|
}
|
|
}
|
|
}
|