Files
2025-01-25 04:38:09 +08:00

225 lines
7.5 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using UnityEngine;
namespace UnityStandardAssets.ImageEffects
{
[ExecuteInEditMode]
[RequireComponent (typeof(Camera))]
[AddComponentMenu ("Image Effects/Bloom and Glow/Bloom (Optimized)")]
public class BloomOptimized : PostEffectsBase
{
public enum Resolution
{
Low = 0,
High = 1,
}
public enum BlurType
{
Standard = 0,
Sgx = 1,
}
[Range(0.0f, 1.5f)]
public float threshold = 0.25f;
[Range(0.0f, 2.5f)]
public float intensity = 0.75f;
[Range(0.25f, 5.5f)]
public float blurSize = 1.0f;
Resolution resolution = Resolution.Low;
[Range(1, 4)]
public int blurIterations = 1;
public BlurType blurType= BlurType.Standard;
public Shader bloomMaskShader;
public Shader fastBloomShader = null;
private Material fastBloomMaterial = null;
//是否Mask来处理Bloom
public bool _useMask;
private Camera _maskCamera;
private RenderTexture _maskCameraRenderTex;
private Camera _selfCamera;
public override bool CheckResources ()
{
CheckSupport (false);
fastBloomMaterial = CheckShaderAndCreateMaterial (fastBloomShader, fastBloomMaterial);
if (!isSupported)
ReportAutoDisable ();
return isSupported;
}
private void MaskCameraRender(ref Camera camera,ref RenderTexture rt, int rtW, int rtH,RenderTextureFormat format)
{
if (bloomMaskShader == null)
{
bloomMaskShader = Shader.Find("Ares/Bloom/BloomMaskPass");
if (bloomMaskShader == null)
{
Debug.LogError("找到着色器Ares/Bloom/BloomMaskPass");
return;
}
}
if (_selfCamera == null)
{
_selfCamera = GetComponent<Camera>();
}
if (rt == null)
{
rt = RenderTexture.GetTemporary(rtW, rtH, 16, format);
rt.antiAliasing = 1;
rt.name = "__WaterRefraction" + GetInstanceID();
rt.isPowerOfTwo = true;
rt.hideFlags = HideFlags.DontSave;
}
if (camera == null)
{
var trans = transform.Find("[BloomMaskCamera]");
GameObject go;
if (trans == null)
{
go = new GameObject("[BloomMaskCamera]");
trans = go.transform;
}
else
{
go = trans.gameObject;
}
trans.parent = transform;
trans.localPosition = Vector3.zero;
trans.localRotation = Quaternion.identity;
//获取Camera组件
camera = go.GetComponent<Camera>();
if (camera == null)
{
camera = go.AddComponent<Camera>();
}
camera.enabled = false;
camera.clearFlags = CameraClearFlags.SolidColor;
camera.backgroundColor = Color.black;
camera.farClipPlane = _selfCamera.farClipPlane;
camera.nearClipPlane = _selfCamera.nearClipPlane;
camera.orthographic = _selfCamera.orthographic;
camera.fieldOfView = _selfCamera.fieldOfView;
camera.aspect = _selfCamera.aspect;
camera.orthographicSize = _selfCamera.orthographicSize;
camera.SetReplacementShader(bloomMaskShader, "RenderType");
camera.targetTexture = rt;
}
if(camera != null) camera.Render();
}
void OnDisable ()
{
if (fastBloomMaterial)
DestroyImmediate (fastBloomMaterial);
if (_maskCamera != null)
{
DestroyImmediate(_maskCamera.gameObject);
_maskCamera = null;
}
if (_maskCameraRenderTex != null)
{
RenderTexture.ReleaseTemporary(_maskCameraRenderTex);
_maskCameraRenderTex = null;
}
}
void OnRenderImage(RenderTexture source, RenderTexture destination)
{
if (CheckResources() == false)
{
Graphics.Blit(source, destination);
return;
}
int divider = resolution == Resolution.Low ? 4 : 2;
float widthMod = resolution == Resolution.Low ? 0.5f : 1.0f;
var rtW = source.width / divider;
var rtH = source.height / divider;
// mask
RenderTexture sourceWithMask = null;
if (_useMask)
{
MaskCameraRender(ref _maskCamera, ref _maskCameraRenderTex, rtW, rtH, source.format);
sourceWithMask = RenderTexture.GetTemporary(rtW, rtH, 0, source.format);
sourceWithMask.name = "RenderTexture100";
sourceWithMask.antiAliasing = 1;
sourceWithMask.filterMode = FilterMode.Bilinear;
fastBloomMaterial.SetTexture("_BloomMaskTex", _maskCameraRenderTex);
Graphics.Blit(source, sourceWithMask, fastBloomMaterial, 6);
}
else
{
sourceWithMask = source;
}
// downsample
RenderTexture rt = RenderTexture.GetTemporary(rtW, rtH, 0, source.format);
rt.name = "RenderTexture15";
rt.antiAliasing = 1;
rt.filterMode = FilterMode.Bilinear;
fastBloomMaterial.SetVector("_Parameter", new Vector4(blurSize * widthMod, 0.0f, threshold, intensity));
source.filterMode = FilterMode.Bilinear;
Graphics.Blit(sourceWithMask, rt, fastBloomMaterial, 1);
if (_useMask)
{
RenderTexture.ReleaseTemporary(sourceWithMask);
}
var passOffs= blurType == BlurType.Standard ? 0 : 2;
for(int i = 0; i < blurIterations; i++)
{
fastBloomMaterial.SetVector ("_Parameter", new Vector4 (blurSize * widthMod + (i*1.0f), 0.0f, threshold, intensity));
// vertical blur
RenderTexture rt2 = RenderTexture.GetTemporary (rtW, rtH, 0, source.format);
rt2.name = "RenderTexture16";
rt2.antiAliasing = 1;
rt2.filterMode = FilterMode.Bilinear;
Graphics.Blit (rt, rt2, fastBloomMaterial, 2 + passOffs);
RenderTexture.ReleaseTemporary (rt);
rt = rt2;
// horizontal blur
rt2 = RenderTexture.GetTemporary (rtW, rtH, 0, source.format);
rt2.name = "RenderTexture17";
rt2.antiAliasing = 1;
rt2.filterMode = FilterMode.Bilinear;
Graphics.Blit (rt, rt2, fastBloomMaterial, 3 + passOffs);
RenderTexture.ReleaseTemporary (rt);
rt = rt2;
}
fastBloomMaterial.SetTexture ("_Bloom", rt);
Graphics.Blit (source, destination, fastBloomMaterial, 0);
//Graphics.Blit(_maskCameraRenderTex, destination);
RenderTexture.ReleaseTemporary (rt);
}
}
}