Lack of ozone contribution in EA sky

Any issues, problems or troubleshooting topics related to the Prepar3D client application.
Post Reply
BiologicalNanobot
Posts: 42
Joined: Wed Feb 10, 2021 4:15 pm

Lack of ozone contribution in EA sky

Post by BiologicalNanobot »

Hi,

Since Prepar3D v5.1, Enhanced Atmospherics mode stopped taking ozone contribution into account, which leads to rather inaccurate sunset/sunrise views. This was not the case with the Enhanced Atmospherics of Prepar3D v5.0, which had simply astonishing sunset/sunrise sky colors. Here is a YouTube video I have found which shows the beauty of v5.0 sky colors: https://youtu.be/K7zOPVeowo4

These sky colors are simply no more in v5.1 and above - assuming it is an intentional design change by Lockheed Martin, what is the reason behind this change? Do you have plans to improve the sky color appearance during sunset/sunrise especially at higher altitudes?

Thanks in advance.
BiologicalNanobot
Posts: 42
Joined: Wed Feb 10, 2021 4:15 pm

Re: Lack of ozone contribution in EA sky

Post by BiologicalNanobot »

As an additional note, me and Henrik2k17 have been working on a shader tweak to add ozone contribution manually to Enhanced Atmospherics. I can safely say the results are very promising:

Before:

Image

After:

Image

Before:

Image

After:

Image

Before:

Image

After:

Image

This alone shows the immense difference taking ozone contribution into account would make. I really hope next versions of Prepar3D end up addressing EA sky colors.
gsnde
Posts: 84
Joined: Mon Nov 25, 2013 5:06 am

Re: Lack of ozone contribution in EA sky

Post by gsnde »

That looks very good!
hotbso
Posts: 28
Joined: Tue May 14, 2019 9:01 am

Re: Lack of ozone contribution in EA sky

Post by hotbso »

Wonderful looks. After each try I went back to legacy atmospherics so the "golden hour" is golden and not a yellow or even brownish hour.
gsnde
Posts: 84
Joined: Mon Nov 25, 2013 5:06 am

Re: Lack of ozone contribution in EA sky

Post by gsnde »

Would you share your magic with the community? Or is it still work in progress?
BiologicalNanobot
Posts: 42
Joined: Wed Feb 10, 2021 4:15 pm

Re: Lack of ozone contribution in EA sky

Post by BiologicalNanobot »

It is still a work-in-progress, but it shouldn't take too long. It only involves changing a file called DeferredComposite.fx, which blends trueSKY atmosphere with P3D world.

I really wish we got a statement about the decision to remove ozone contribution from the atmosphere by Lockheed Martin as I really cannot understand the reason behind this decision. While Enhanced Atmospherics clouds are pretty good considering the limitations of trueSKY, I believe much better sky colors could easily be achieved using trueSKY, at least based on my experience. An accurate atmosphere is not only necessary for viewing pleasure, but also simulating different conditions accurately.

Bringing P3D v5.0 EA sky colors back while keeping the clouds the same would be a great improvement. I really hope Lockheed Martin at least considers it for the upcoming hotfix / point release.
B777ER
Posts: 106
Joined: Sat May 14, 2016 2:45 pm

Re: Lack of ozone contribution in EA sky

Post by B777ER »

BiologicalNanobot wrote: Sun Dec 26, 2021 10:37 am It is still a work-in-progress, but it shouldn't take too long. It only involves changing a file called DeferredComposite.fx, which blends trueSKY atmosphere with P3D world.

I really wish we got a statement about the decision to remove ozone contribution from the atmosphere by Lockheed Martin as I really cannot understand the reason behind this decision. While Enhanced Atmospherics clouds are pretty good considering the limitations of trueSKY, I believe much better sky colors could easily be achieved using trueSKY, at least based on my experience. An accurate atmosphere is not only necessary for viewing pleasure, but also simulating different conditions accurately.

Bringing P3D v5.0 EA sky colors back while keeping the clouds the same would be a great improvement. I really hope Lockheed Martin at least considers it for the upcoming hotfix / point release.
Thanks, I am still using your HSL mod to brighten the cockpit with EA on. Looking fwd to this one.
MPO910
Posts: 855
Joined: Wed Apr 15, 2020 5:00 am

Re: Lack of ozone contribution in EA sky

Post by MPO910 »

BiologicalNanobot wrote: Wed Dec 22, 2021 10:23 pm As an additional note, me and Henrik2k17 have been working on a shader tweak to add ozone contribution manually to Enhanced Atmospherics. I can safely say the results are very promising:

Before:

Image

After:

Image

Before:

Image

After:

Image

Before:

Image

After:

Image

This alone shows the immense difference taking ozone contribution into account would make. I really hope next versions of Prepar3D end up addressing EA sky colors.
This looks indeed very good! I would love to see LM take this and make it their default!
Marcus P
Windows 10 Home 21H1
Build 19043.1586
Feature Exp. Pack 120.2212.4170.0
i9 10900K @ 5.0 Ghz | HT OFF | 1.32V
Mainboard ASUS ROG Maximus XII Formula Z490
32 GB RAM 3600 Mhz
RTX 3090 24GB
32" Samsung UHD Monitor
HP Reverb G2 VR HMD | Steam VR
BiologicalNanobot
Posts: 42
Joined: Wed Feb 10, 2021 4:15 pm

Re: Lack of ozone contribution in EA sky

Post by BiologicalNanobot »

Hi,

The first version of my and Henrik2k17's EA tweak is finally ready:

Code: Select all

//---------------------------------------------------------------------------
// Prepar3d - Shader Effect Files
// Copyright (c) 2021, Lockheed Martin Corporation
//---------------------------------------------------------------------------

#include "ShaderMacros.h"
#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_3)
#define SHD_VIEW_INSTANCING
#endif

#define SHD_ENHANCED_ATMOSPHERICS_BLEND

#include "ConstantBuffers.fxh"
#include "FuncLibrary.fxh"
#include "IRSim.fxh"
#include "Quad.sh"

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_1)
#define SHD_CLOUDS
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_2)
#define SHD_GODRAYS
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_4)
#define SHD_IR_ACTIVE
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_5)
#define SHD_IR_BLACK_HOT
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_6)
#define SHD_NO_SCATTER
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_7)
#define SHD_CUBEMAP
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_8)
#define SHD_GDATA
#endif

#if(QUAD_RENDER_SHADER_FLAGS & SHD_FLAGS_MISC_9)
#define SHD_ORTHO_PROJ
#endif

#if defined(QUAD_RENDER_MULTISAMPLED)
shared Texture2DMSArray<float> inputDepth : register(t0);
#else
shared Texture2DArray<float> inputDepth : register(t0);
#endif
shared Texture2DArray<float4> lowResMinMaxDepth : register(t1);

shared cbuffer cbData : REGISTER(b, POST_PROCESS_CB_REGISTER)
{
    uint2 TextureSize;
    uint InstanceID;
    uint MSAASampleCount;
    uint CloudArraySize;
    uint CloudTextureSize;
    float Precipitation;
    float unused;
};

struct CompositeOutput
{
    float4 src : SV_Target0;
    float4 src1 : SV_Target1;
};

static const float3 normalized_ozone_coefficient = float3(0.61344749, 0.0, 1.0); //Ozone extinction (absorption) coefficients based on observations, normalized and inverted

//Effect of the ozone on sky, between 0 and 1
static const float sky_ozone_effect_day = 0.125;
static const float sky_ozone_effect_twilight = 0.325;
static const float sky_ozone_effect_night = 0.125;

//Effect of the ozone on clouds, between 0 and 1
static const float cloud_ozone_effect_day = 0.0;
static const float cloud_ozone_effect_twilight = 0.325;
static const float cloud_ozone_effect_night = 0.125;

//Brightness of sky, expressed as a ratio versus default
static const float sky_brightness_day = 1.0;
static const float sky_brightness_twilight = 3.25;
static const float sky_brightness_night = 0.5;

//Brightness of clouds, expressed as a ratio versus default
static const float cloud_brightness_day = 1.0;
static const float cloud_brightness_twilight = 1.5;
static const float cloud_brightness_night = 0.25;

float map(float input_value, float input_start, float input_end, float output_start, float output_end)
{
	float slope = (output_end - output_start) / (input_end - input_start);

	return clamp(output_start + (slope * (input_value - input_start)), min(output_start, output_end), max(output_start, output_end));
}

float interpolate_sun_angle(float sun_angle, float day_value, float twilight_value, float night_value)
{
    float output_value;

    if (sun_angle < 0.0) output_value = map(sun_angle, -0.25, -0.125, night_value, twilight_value);
    else if (sun_angle < 0.175) output_value = map(sqrt(sun_angle), 0.0, sqrt(0.175), twilight_value, day_value);
    else output_value = day_value;

    return output_value;
}

float LoadDepth(int3 loadCoords, uint sampleIndex)
{
#if defined(QUAD_RENDER_MULTISAMPLED)
    return inputDepth.Load(loadCoords, sampleIndex);
#else
    return inputDepth.Load(int4(loadCoords, 0));
#endif
}

CompositeOutput DeferredComposite(PsQuad vert, uint sampleIndex : SV_SAMPLEINDEX)
{
    CompositeOutput output = (CompositeOutput)0;
    float4 clouds = float4(0, 0, 0, 1);
    float cloudFade = 1;
    float4 insc = float4(0, 0, 0, 0);
    float4 loss = float4(1, 1, 1, 1);

    float2 screen = UVToScreen(vert.texcoord.xy);
    float depth = LoadDepth(int3(TextureSize.x * vert.texcoord.x, TextureSize.y * vert.texcoord.y, vert.RTIndex), sampleIndex);
    float distToFadeDist = rcp(cb_mFadeDistance * 1000);
#if defined(SHD_CUBEMAP)
    float4 positionVS = mul(float4(screen, depth, 1.0f), cb_View.mInverseProj);
    positionVS /= positionVS.w;
    float4 positionWS = mul(positionVS, cb_mInvViewCubemap[InstanceID]);
#else
    float4 positionWS = ScreenToWorldSpace(float4(screen, depth, 1.0f), InstanceID);
#endif

#if defined(SHD_ORTHO_PROJ)
    float3 view = cb_View.mView[2].xzy;
    //TODO revisit.  Should be able to convert from depth directly to dist for ortho view using near/far
    float dist = mul(positionWS, cb_View.mView).z * distToFadeDist;
#else
    float3 view = normalize(positionWS.xzy);
    float3 cubeRay = view;
    float dist = length(positionWS.xzy) * distToFadeDist;
#endif

#if defined(SHD_GDATA) && defined(SHD_CLOUDS)
    float2 minMaxDepth = lowResMinMaxDepth.Sample(samWrap, float3(vert.texcoord.xy, 0)).xy;
    float nearInterp = saturate((dist - minMaxDepth.x) / max(0.00000001, minMaxDepth.y - minMaxDepth.x));
    float nearIndex = float(CloudArraySize - 1) * nearInterp;
    clouds = txBindlessArray(cb_mCloudCubeArrayTextureIndex).Sample(samWrap, float3(vert.texcoord.xy, nearIndex));
    if (clouds.a < 0.95)
    {
        float precip = 1 - clouds.a;
        precip *= 0.1 + Precipitation * 0.9;
        insc = float4(0, 1, precip, 1);
    }
#else

    const float distRT = sqrt(dist);
    const float2 lossUV = float2(distRT, 0.5 * (1.0f - view.z));
    float3 inscatterUVs = float3(atan2(view.x, view.y) / (2.0 * PI), 0.5 * (1.0 + 2.0 * asin(view.z) / PI), distRT);

    #if !defined(SHD_NO_SCATTER)
        insc = txBindless3D(cb_mInscatterVolumeTextureIndex).SampleLevel(samWMC, inscatterUVs, 0);
        loss = txBindless(cb_mLoss2DTextureIndex).SampleLevel(samClamp, lossUV, 0);

        insc.rgb = interpolate_sun_angle(cb_mSun.mDirection.y, sky_brightness_day, sky_brightness_twilight, sky_brightness_night) * lerp(insc.rgb, insc.rgb * normalized_ozone_coefficient, interpolate_sun_angle(cb_mSun.mDirection.y, sky_ozone_effect_day, sky_ozone_effect_twilight, sky_ozone_effect_night));
    #endif

    #if defined(SHD_GODRAYS)
        float3 viewOffset = view.xyz * dist * cb_mFadeDistance;
        float3 viewOffsetGodRaysSpace = mul(cb_mWorldToGodRaySpace, float4(viewOffset, 1.0f)).xyz;
        float rayLength = length(viewOffsetGodRaysSpace);
        float3 godRaysUVs = float3(frac(atan2(viewOffsetGodRaysSpace.x, viewOffsetGodRaysSpace.y) / (2.0f * PI)),
            0.5f + 0.5f * asin(viewOffsetGodRaysSpace.z / rayLength) * 2.0f / PI, rayLength);
        float4 godRays = txBindless3D(cb_mGodRayVolumeTextureIndex).SampleLevel(samWCC, godRaysUVs, 0);
        insc.rgb *= godRays.x;
    #endif

    //TODO correct fog distance for ortho.  Disable for now
    #if defined(SHD_ORTHO_PROJ)
        // Ortho gets some od values since insc is based on vir direction.  It can cause terrain to fade out entirely
        // at some angles, so scale the haze value down
        insc *= 0.2;
        loss += 0.8 * (1 - loss);
    #else
        float4 fogInscatter = CalculateFogAndTransmittance(positionWS.xyz, InstanceID);
        insc.rgb = insc.rgb * fogInscatter.a + fogInscatter.rgb;
        loss *= fogInscatter.a;
    #endif

    #if defined(SHD_CLOUDS)
        #if !defined(SHD_CUBEMAP)
            //float4 nearFarCloud = txBindlessArray(cb_mNearFarTextureIndex).Sample(samWrap, float3(vert.texcoord.xy, 0));
            float2 minMaxDepth = lowResMinMaxDepth.Sample(samWrap, float3(vert.texcoord.xy, 0)).xy;
        #endif

        cloudFade = saturate((dist - cb_mNearFadeDistance) / max(0.0001f, 2.0f * cb_mNearFadeDistance));            
        // Sampling artifacts arise when interpolating to values near 1 caused by pixels that hit no
        // clouds in the ray cast. If depth is at far plane, there's no point in fading anyway so just assume clouds are
        // in front and set cloudFade to 1
        cloudFade = depth > 0.9999f ? 1.0f : cloudFade;

        if (cloudFade > 0)
        {
            #if defined(SHD_CUBEMAP)
                float4 nearClouds = txBindlessCubeArray(cb_mCloudCubeArrayTextureIndex).Sample(samWrap, float4(cubeRay, 0));
            #else
                float nearInterp = saturate((dist - minMaxDepth.x) / max(0.00000001, minMaxDepth.y - minMaxDepth.x));
                float nearIndex = float(CloudArraySize - 1) * nearInterp;
                float4 nearClouds = txBindlessArray(cb_mCloudCubeArrayTextureIndex).Sample(samWrap, float3(vert.texcoord.xy, nearIndex));
                //nearClouds = float4(minMaxDepth.y - minMaxDepth.x, 0, 0, 0);
            #endif          

            clouds = lerp(clouds, nearClouds, cloudFade);
            clouds.rgb = interpolate_sun_angle(cb_mSun.mDirection.y, cloud_brightness_day, cloud_brightness_twilight, cloud_brightness_night) * lerp(clouds.rgb, clouds.rgb * normalized_ozone_coefficient, interpolate_sun_angle(cb_mSun.mDirection.y, cloud_ozone_effect_day, cloud_ozone_effect_twilight, cloud_ozone_effect_night));

            insc.rgb = insc.rgb * clouds.a + clouds.rgb;
            loss *= clouds.a;
        }
    #endif

    #if defined(SHD_IR_ACTIVE)
        insc = ApplyIr(saturate(insc), 1);
        loss = float4(1, 1, 1, 1);
        #if defined(SHD_IR_BLACK_HOT)
            insc.rgb = 1.0f - insc.rgb;
        #endif
    #endif
#endif

    output.src = insc;
    output.src1 = loss;

    return output;
}
Installation Instructions:

1. Go to your Prepar3D v5 main folder/ShadersHLSL, find DeferredComposite.fx and create a backup for it.
2. Open the DeferredComposite.fx file with a text editor like Notepad and replace all of the contents of the file with the code above.
3. Clear your shader cache by deleting %localappdata%/Lockheed Martin/Prepar3D v5/Shaders folder.

Be noted that this mod will only work with Prepar3D v5.3 HF1 + Update 1, do not install it in other versions.

Happy new years!
BAWV12
Posts: 142
Joined: Mon Jan 13, 2020 4:49 pm

Re: Lack of ozone contribution in EA sky

Post by BAWV12 »

First look - very good.
hotbso
Posts: 28
Joined: Tue May 14, 2019 9:01 am

Re: Lack of ozone contribution in EA sky

Post by hotbso »

That looks already pretty sweet! Thanks for sharing and a happy new year!
hotbso
Posts: 28
Joined: Tue May 14, 2019 9:01 am

Re: Lack of ozone contribution in EA sky

Post by hotbso »

Wonderful, the horrible yellow/brownish twilight is gone!
BAWV12
Posts: 142
Joined: Mon Jan 13, 2020 4:49 pm

Re: Lack of ozone contribution in EA sky

Post by BAWV12 »

Fix applied, somewhere between Lhasa and Paro :

Image

Image

Image

The atmosphere looks deeper than without fix.
disco79stu
Posts: 57
Joined: Thu Jul 16, 2020 9:05 pm

Re: Lack of ozone contribution in EA sky

Post by disco79stu »

Is this for EA with volumetric clouds only?
Because EA with legacy clouds, they seem still pretty green-yellowish to me...

Image
adam2019
Posts: 15
Joined: Sat Jan 05, 2019 9:38 am

Re: Lack of ozone contribution in EA sky

Post by adam2019 »

STUNNING! thank you!
Post Reply