add simple fog
This commit is contained in:
@ -664,7 +664,7 @@ namespace Prism
|
||||
{
|
||||
SceneRenderer::SetViewportSize((uint32_t)viewportSize.x, (uint32_t)viewportSize.y);
|
||||
m_EditorScene->SetViewportSize((uint32_t)viewportSize.x, (uint32_t)viewportSize.y);
|
||||
m_EditorCamera.SetProjectionMatrix(glm::perspectiveFov(glm::radians(45.0f), viewportSize.x, viewportSize.y, 0.1f, 10000.0f));
|
||||
m_EditorCamera.SetProjectionMatrix(glm::perspectiveFov(glm::radians(45.0f), viewportSize.x, viewportSize.y, 0.1f, 1000.0f));
|
||||
m_EditorCamera.SetViewportSize((uint32_t)viewportSize.x, (uint32_t)viewportSize.y);
|
||||
ImGui::Image((ImTextureRef)SceneRenderer::GetFinalColorBufferRendererID(), viewportSize, { 0, 1 }, { 1, 0 });
|
||||
|
||||
|
||||
@ -75,6 +75,9 @@ const float Epsilon = 0.00001;
|
||||
const int LightCount = 1;
|
||||
const vec3 Fdielectric = vec3(0.04);
|
||||
|
||||
layout(location = 0) out vec4 color;
|
||||
layout(location = 1) out vec4 o_BloomColor;
|
||||
|
||||
struct DirectionalLight {
|
||||
vec3 Direction;
|
||||
vec3 Radiance;
|
||||
@ -113,8 +116,6 @@ in VertexOutput
|
||||
vec4 FragPosLightSpace;
|
||||
} vs_Input;
|
||||
|
||||
layout(location = 0) out vec4 color;
|
||||
layout(location = 1) out vec4 o_BloomColor;
|
||||
|
||||
uniform DirectionalLight u_DirectionalLights;
|
||||
uniform vec3 u_CameraPosition;
|
||||
|
||||
@ -61,6 +61,9 @@ const float Epsilon = 0.00001;
|
||||
const int LightCount = 1;
|
||||
const vec3 Fdielectric = vec3(0.04);
|
||||
|
||||
layout(location = 0) out vec4 color;
|
||||
layout(location = 1) out vec4 o_BloomColor;
|
||||
|
||||
struct DirectionalLight {
|
||||
vec3 Direction;
|
||||
vec3 Radiance;
|
||||
@ -100,9 +103,6 @@ in VertexOutput
|
||||
vec4 FragPosLightSpace;
|
||||
} vs_Input;
|
||||
|
||||
layout(location = 0) out vec4 color;
|
||||
layout(location = 1) out vec4 o_BloomColor;
|
||||
|
||||
uniform DirectionalLight u_DirectionalLights;
|
||||
|
||||
uniform int u_PointLightCount;
|
||||
|
||||
@ -22,8 +22,20 @@ layout(location = 1) out vec4 o_BloomTexture;
|
||||
in vec2 v_TexCoord;
|
||||
|
||||
uniform sampler2DMS u_Texture;
|
||||
uniform sampler2DMS u_DepthTexture;
|
||||
uniform sampler2D u_BloomTexture;
|
||||
|
||||
uniform mat4 u_InvProjection;
|
||||
uniform mat4 u_InvView;
|
||||
|
||||
// Fog
|
||||
uniform float u_FogEnabled;
|
||||
uniform vec3 u_FogColor;
|
||||
uniform float u_FogDensity; // 雾密度,典型值 0.01~0.05
|
||||
uniform float u_FogHeight; // 雾的起始高度(世界 Y 坐标),低于此高度雾最浓
|
||||
uniform float u_FogHeightFalloff; // 高度衰减系数,值越大高度影响越剧烈(典型 0.5~2.0)
|
||||
|
||||
|
||||
|
||||
uniform bool u_EnableAutoExposure;
|
||||
uniform float u_ManualExposure;
|
||||
@ -62,7 +74,7 @@ float MultiSampleDepth(sampler2DMS tex, vec2 tc)
|
||||
ivec2 texCoord = ivec2(tc * texSize);
|
||||
float result = 0.0;
|
||||
for (int i = 0; i < u_TextureSamples; i++)
|
||||
result += texelFetch(tex, texCoord, i).r;
|
||||
result += texelFetch(tex, texCoord, i).r;
|
||||
result /= float(u_TextureSamples);
|
||||
return result;
|
||||
}
|
||||
@ -82,10 +94,14 @@ void main()
|
||||
color += bloomColor;
|
||||
}
|
||||
|
||||
|
||||
float exposure = 1.0f;
|
||||
if(u_EnableAutoExposure)
|
||||
color *= u_Exposure;
|
||||
exposure = u_Exposure;
|
||||
else
|
||||
color *= u_ManualExposure;
|
||||
exposure = u_ManualExposure;
|
||||
color *= exposure;
|
||||
|
||||
|
||||
// Reinhard tonemapping operator.
|
||||
// see: "Photographic Tone Reproduction for Digital Images", eq. 4
|
||||
@ -95,6 +111,49 @@ void main()
|
||||
// Scale color by ratio of average luminances.
|
||||
vec3 mappedColor = (mappedLuminance / luminance) * color;
|
||||
|
||||
if (u_FogEnabled > 0.5)
|
||||
{
|
||||
// 1. 获取深度并重建视空间坐标
|
||||
float depth = MultiSampleDepth(u_DepthTexture, v_TexCoord);
|
||||
vec4 clipPos = vec4(v_TexCoord * 2.0 - 1.0, depth * 2.0 - 1.0, 1.0);
|
||||
vec4 viewPos4 = u_InvProjection * clipPos;
|
||||
viewPos4 /= viewPos4.w;
|
||||
vec3 viewPos = viewPos4.xyz; // 视空间坐标(相机为原点,Z 轴向内)
|
||||
|
||||
// 2. 距离雾因子(指数雾)
|
||||
float distance = length(viewPos);
|
||||
float distanceFactor = 1.0 - exp(-distance * u_FogDensity);
|
||||
// 可选:指数平方雾(更平滑)
|
||||
// float distanceFactor = 1.0 - exp(-pow(distance * u_FogDensity, 2.0));
|
||||
|
||||
// 3. 高度雾因子(基于世界 Y)
|
||||
// 将视空间坐标转换到世界空间
|
||||
vec4 worldPos4 = u_InvView* vec4(viewPos, 1.0);
|
||||
vec3 worldPos = worldPos4.xyz / worldPos4.w;
|
||||
float worldY = worldPos.y;
|
||||
|
||||
float heightFactor = 0.0;
|
||||
if (worldY < u_FogHeight)
|
||||
{
|
||||
// 低于起始高度:雾最浓,因子为 1
|
||||
heightFactor = 1.0;
|
||||
}
|
||||
else
|
||||
{
|
||||
// 高于起始高度:指数衰减,高度越高雾越淡
|
||||
float deltaY = worldY - u_FogHeight;
|
||||
heightFactor = exp(-deltaY * u_FogHeightFalloff);
|
||||
}
|
||||
// 可选:使用 clamp 限制范围
|
||||
heightFactor = clamp(heightFactor, 0.0, 1.0);
|
||||
|
||||
// 4. 综合雾因子(可相乘,也可取最大值,通常相乘)
|
||||
float fogFactor = distanceFactor * heightFactor;
|
||||
|
||||
// 5. 混合雾颜色(雾颜色直接使用 u_FogColor,已在 LDR 空间)
|
||||
mappedColor = mix(mappedColor, u_FogColor, fogFactor);
|
||||
}
|
||||
|
||||
// Gamma correction.
|
||||
o_Color = vec4(pow(mappedColor, vec3(1.0 / gamma)), 1.0);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user