using System; using UnityEngine; [AddComponentMenu("Enviro/Effects/Fog Image Effect")] [ExecuteInEditMode] [RequireComponent(typeof(Camera))] public class EnviroFog : EnviroEffects { public bool distanceFog = true; public bool useRadialDistance; public bool heightFog = true; public float height = 1f; [Range(0.001f, 10f)] public float heightDensity = 2f; public float startDistance; public Shader fogShader; public Material fogMaterial; private Texture3D _noiseTexture; public override bool CheckResources() { CheckSupport(true); fogMaterial = CheckShaderAndCreateMaterial(fogShader, fogMaterial); if (!isSupported) { ReportAutoDisable(); } return isSupported; } private new void Start() { LoadNoise3dTexture(); } private void OnRenderImage(RenderTexture source, RenderTexture destination) { if (!CheckResources() || (!distanceFog && !heightFog)) { Graphics.Blit(source, destination); return; } Camera component = GetComponent(); Transform transform = component.transform; float nearClipPlane = component.nearClipPlane; float farClipPlane = component.farClipPlane; float fieldOfView = component.fieldOfView; float aspect = component.aspect; Matrix4x4 identity = Matrix4x4.identity; float num = fieldOfView * 0.5f; Vector3 vector = transform.right * nearClipPlane * Mathf.Tan(num * ((float)Math.PI / 180f)) * aspect; Vector3 vector2 = transform.up * nearClipPlane * Mathf.Tan(num * ((float)Math.PI / 180f)); Vector3 vector3 = transform.forward * nearClipPlane - vector + vector2; float num2 = vector3.magnitude * farClipPlane / nearClipPlane; vector3.Normalize(); vector3 *= num2; Vector3 vector4 = transform.forward * nearClipPlane + vector + vector2; vector4.Normalize(); vector4 *= num2; Vector3 vector5 = transform.forward * nearClipPlane + vector - vector2; vector5.Normalize(); vector5 *= num2; Vector3 vector6 = transform.forward * nearClipPlane - vector - vector2; vector6.Normalize(); vector6 *= num2; identity.SetRow(0, vector3); identity.SetRow(1, vector4); identity.SetRow(2, vector5); identity.SetRow(3, vector6); Vector3 position = transform.position; float num3 = position.y - height; float z = ((!(num3 <= 0f)) ? 0f : 1f); fogMaterial.SetMatrix("_FrustumCornersWS", identity); fogMaterial.SetVector("_CameraWS", position); fogMaterial.SetVector("_HeightParams", new Vector4(height, num3, z, heightDensity * 0.5f)); fogMaterial.SetVector("_DistanceParams", new Vector4(0f - Mathf.Max(startDistance, 0f), 0f, 0f, 0f)); fogMaterial.SetTexture("_NoiseTexture", _noiseTexture); FogMode fogMode = RenderSettings.fogMode; float fogDensity = RenderSettings.fogDensity; float fogStartDistance = RenderSettings.fogStartDistance; float fogEndDistance = RenderSettings.fogEndDistance; bool flag = fogMode == FogMode.Linear; float num4 = ((!flag) ? 0f : (fogEndDistance - fogStartDistance)); float num5 = ((!(Mathf.Abs(num4) > 0.0001f)) ? 0f : (1f / num4)); Vector4 value = default(Vector4); value.x = fogDensity * 1.2011224f; value.y = fogDensity * 1.442695f; value.z = ((!flag) ? 0f : (0f - num5)); value.w = ((!flag) ? 0f : (fogEndDistance * num5)); fogMaterial.SetVector("_SceneFogParams", value); fogMaterial.SetVector("_SceneFogMode", new Vector4((float)fogMode, useRadialDistance ? 1 : 0, 0f, 0f)); int num6 = 0; CustomGraphicsBlit(passNr: (!distanceFog || !heightFog) ? (distanceFog ? 1 : 2) : 0, source: source, dest: destination, fxMaterial: fogMaterial); } private static void CustomGraphicsBlit(RenderTexture source, RenderTexture dest, Material fxMaterial, int passNr) { RenderTexture.active = dest; fxMaterial.SetTexture("_MainTex", source); GL.PushMatrix(); GL.LoadOrtho(); fxMaterial.SetPass(passNr); GL.Begin(7); GL.MultiTexCoord2(0, 0f, 0f); GL.Vertex3(0f, 0f, 3f); GL.MultiTexCoord2(0, 1f, 0f); GL.Vertex3(1f, 0f, 2f); GL.MultiTexCoord2(0, 1f, 1f); GL.Vertex3(1f, 1f, 1f); GL.MultiTexCoord2(0, 0f, 1f); GL.Vertex3(0f, 1f, 0f); GL.End(); GL.PopMatrix(); } private void LoadNoise3dTexture() { TextAsset textAsset = Resources.Load("NoiseVolume") as TextAsset; byte[] bytes = textAsset.bytes; uint num = BitConverter.ToUInt32(textAsset.bytes, 12); uint num2 = BitConverter.ToUInt32(textAsset.bytes, 16); uint num3 = BitConverter.ToUInt32(textAsset.bytes, 20); uint num4 = BitConverter.ToUInt32(textAsset.bytes, 24); uint num5 = BitConverter.ToUInt32(textAsset.bytes, 80); uint num6 = BitConverter.ToUInt32(textAsset.bytes, 88); if (num6 == 0) { num6 = num3 / num2 * 8; } _noiseTexture = new Texture3D((int)num2, (int)num, (int)num4, TextureFormat.RGBA32, false); _noiseTexture.name = "3D Noise"; Color[] array = new Color[num2 * num * num4]; uint num7 = 128u; if (textAsset.bytes[84] == 68 && textAsset.bytes[85] == 88 && textAsset.bytes[86] == 49 && textAsset.bytes[87] == 48 && (num5 & 4) != 0) { uint num8 = BitConverter.ToUInt32(textAsset.bytes, (int)num7); if (num8 >= 60 && num8 <= 65) { num6 = 8u; } else if (num8 >= 48 && num8 <= 52) { num6 = 16u; } else if (num8 >= 27 && num8 <= 32) { num6 = 32u; } num7 += 20; } uint num9 = num6 / 8; num3 = (num2 * num6 + 7) / 8; for (int i = 0; i < num4; i++) { for (int j = 0; j < num; j++) { for (int k = 0; k < num2; k++) { float num10 = (float)(int)bytes[num7 + k * num9] / 255f; array[k + j * num2 + i * num2 * num] = new Color(num10, num10, num10, num10); } num7 += num3; } } _noiseTexture.SetPixels(array); _noiseTexture.Apply(); } }