Enable HDR lighting with Reinhard tonemapping across all world shaders

Replace hardcoded specular multipliers with uLightColor * uSpecularIntensity
uniforms in all 4 world shaders (terrain, WMO, M2, character), set HDR sun
color (1.5, 1.4, 1.3) and specular intensity 0.5 so highlights can exceed
1.0, and switch the post-process pass from passthrough to exposure-compensated
Reinhard (exposure=1.8) for soft highlight roll-off without clipping.
This commit is contained in:
Kelsi 2026-02-04 15:28:47 -08:00
parent 1f672e1d73
commit 09e1ee0ae2
6 changed files with 24 additions and 6 deletions

View file

@ -32,6 +32,9 @@ uniform vec3 uAmbientColor;
// Camera
uniform vec3 uViewPos;
// HDR specular
uniform float uSpecularIntensity;
// Fog
uniform vec3 uFogColor;
uniform float uFogStart;
@ -79,7 +82,7 @@ void main() {
vec3 viewDir = normalize(uViewPos - FragPos);
vec3 halfwayDir = normalize(lightDir + viewDir);
float spec = pow(max(dot(norm, halfwayDir), 0.0), 32.0);
vec3 specular = spec * uLightColor * 0.1;
vec3 specular = spec * uLightColor * uSpecularIntensity;
// Combine lighting
vec3 result = ambient + diffuse + specular;

View file

@ -90,6 +90,8 @@ bool CharacterRenderer::initialize() {
uniform sampler2D uTexture0;
uniform vec3 uLightDir;
uniform vec3 uLightColor;
uniform float uSpecularIntensity;
uniform vec3 uViewPos;
uniform vec3 uFogColor;
@ -113,7 +115,7 @@ bool CharacterRenderer::initialize() {
vec3 viewDir = normalize(uViewPos - FragPos);
vec3 halfDir = normalize(lightDir + viewDir);
float spec = pow(max(dot(normal, halfDir), 0.0), 32.0);
vec3 specular = spec * vec3(0.2);
vec3 specular = spec * uLightColor * uSpecularIntensity;
// Shadow mapping
float shadow = 1.0;
@ -1016,6 +1018,8 @@ void CharacterRenderer::render(const Camera& camera, const glm::mat4& view, cons
characterShader->setUniform("uView", view);
characterShader->setUniform("uProjection", projection);
characterShader->setUniform("uLightDir", glm::vec3(0.0f, -1.0f, 0.3f));
characterShader->setUniform("uLightColor", glm::vec3(1.5f, 1.4f, 1.3f));
characterShader->setUniform("uSpecularIntensity", 0.5f);
characterShader->setUniform("uViewPos", camera.getPosition());
// Fog

View file

@ -253,6 +253,8 @@ bool M2Renderer::initialize(pipeline::AssetManager* assets) {
in vec2 TexCoord;
uniform vec3 uLightDir;
uniform vec3 uLightColor;
uniform float uSpecularIntensity;
uniform vec3 uAmbientColor;
uniform vec3 uViewPos;
uniform sampler2D uTexture;
@ -299,7 +301,7 @@ bool M2Renderer::initialize(pipeline::AssetManager* assets) {
vec3 viewDir = normalize(uViewPos - FragPos);
vec3 halfDir = normalize(lightDir + viewDir);
float spec = pow(max(dot(normal, halfDir), 0.0), 32.0);
vec3 specular = spec * vec3(0.1);
vec3 specular = spec * uLightColor * uSpecularIntensity;
// Shadow mapping
float shadow = 1.0;
@ -1117,6 +1119,8 @@ void M2Renderer::render(const Camera& camera, const glm::mat4& view, const glm::
shader->setUniform("uView", view);
shader->setUniform("uProjection", projection);
shader->setUniform("uLightDir", lightDir);
shader->setUniform("uLightColor", glm::vec3(1.5f, 1.4f, 1.3f));
shader->setUniform("uSpecularIntensity", 0.5f);
shader->setUniform("uAmbientColor", ambientColor);
shader->setUniform("uViewPos", camera.getPosition());
shader->setUniform("uFogColor", fogColor);

View file

@ -1176,8 +1176,10 @@ void Renderer::initPostProcess(int w, int h) {
out vec4 FragColor;
void main() {
vec3 color = texture(uScene, vUV).rgb;
// Passthrough — tonemap will kick in once HDR lighting is added
FragColor = vec4(color, 1.0);
float exposure = 1.8;
color *= exposure;
vec3 mapped = color / (color + vec3(1.0));
FragColor = vec4(mapped, 1.0);
}
)";
postProcessShader = std::make_unique<Shader>();

View file

@ -324,6 +324,7 @@ void TerrainRenderer::render(const Camera& camera) {
// Set lighting
shader->setUniform("uLightDir", glm::vec3(lightDir[0], lightDir[1], lightDir[2]));
shader->setUniform("uLightColor", glm::vec3(lightColor[0], lightColor[1], lightColor[2]));
shader->setUniform("uSpecularIntensity", 0.5f);
shader->setUniform("uAmbientColor", glm::vec3(ambientColor[0], ambientColor[1], ambientColor[2]));
// Set camera position

View file

@ -74,6 +74,8 @@ bool WMORenderer::initialize(pipeline::AssetManager* assets) {
in vec4 VertexColor;
uniform vec3 uLightDir;
uniform vec3 uLightColor;
uniform float uSpecularIntensity;
uniform vec3 uViewPos;
uniform vec3 uAmbientColor;
uniform sampler2D uTexture;
@ -105,7 +107,7 @@ bool WMORenderer::initialize(pipeline::AssetManager* assets) {
vec3 viewDir = normalize(uViewPos - FragPos);
vec3 halfDir = normalize(lightDir + viewDir);
float spec = pow(max(dot(normal, halfDir), 0.0), 32.0);
vec3 specular = spec * vec3(0.15);
vec3 specular = spec * uLightColor * uSpecularIntensity;
// Sample texture or use vertex color
vec4 texColor;
@ -490,6 +492,8 @@ void WMORenderer::render(const Camera& camera, const glm::mat4& view, const glm:
shader->setUniform("uProjection", projection);
shader->setUniform("uViewPos", camera.getPosition());
shader->setUniform("uLightDir", glm::vec3(-0.3f, -0.7f, -0.6f)); // Default sun direction
shader->setUniform("uLightColor", glm::vec3(1.5f, 1.4f, 1.3f));
shader->setUniform("uSpecularIntensity", 0.5f);
shader->setUniform("uAmbientColor", glm::vec3(0.4f, 0.4f, 0.5f));
shader->setUniform("uFogColor", fogColor);
shader->setUniform("uFogStart", fogStart);