From df50fdf98621d2e3e0e28e097b1be89c0b53c332 Mon Sep 17 00:00:00 2001 From: Jonathan Young Date: Wed, 21 Sep 2016 14:43:21 +1000 Subject: [PATCH] More closely match GL1 renderer entity lighting. --- code/renderer_bgfx/Main_frame.cpp | 24 ++++++++++++++++++------ code/renderer_bgfx/Precompiled.h | 1 + code/renderer_bgfx/Util.cpp | 22 ++++++++++++++++++++++ code/renderer_bgfx/World.cpp | 21 +++++++++++++-------- 4 files changed, 54 insertions(+), 14 deletions(-) diff --git a/code/renderer_bgfx/Main_frame.cpp b/code/renderer_bgfx/Main_frame.cpp index 0f1bd6f..b5dd7a5 100644 --- a/code/renderer_bgfx/Main_frame.cpp +++ b/code/renderer_bgfx/Main_frame.cpp @@ -293,6 +293,20 @@ static void RenderDebugDraw(bgfx::TextureHandle texture, int x = 0, int y = 0, S RenderScreenSpaceQuad(s_main->defaultFb, program, BGFX_STATE_RGB_WRITE, BGFX_CLEAR_NONE, s_main->isTextureOriginBottomLeft, Rect(g_cvars.debugDrawSize.getInt() * x, g_cvars.debugDrawSize.getInt() * y, g_cvars.debugDrawSize.getInt(), g_cvars.debugDrawSize.getInt())); } +static void ClampEntityLight(vec3 *light) +{ + assert(light); + float max = std::max(light->r, std::max(light->g, light->b)); + + if (max > 255.0f) + { + max = 255.0f / max; + light->r *= max; + light->g *= max; + light->b *= max; + } +} + static void SetupEntityLighting(Entity *entity) { assert(entity); @@ -335,10 +349,8 @@ static void SetupEntityLighting(Entity *entity) s_main->dlightManager->contribute(s_main->frameNo, lightPosition, &entity->directedLight, &entity->lightDir); } - // Clamp ambient. - for (int i = 0; i < 3; i++) - entity->ambientLight[i] = std::min(entity->ambientLight[i], g_identityLight * 255); - + ClampEntityLight(&entity->ambientLight); + ClampEntityLight(&entity->directedLight); entity->lightDir.normalize(); } @@ -1134,8 +1146,8 @@ static void RenderCamera(const RenderCameraArgs &args) if (s_main->currentEntity) { - s_main->entityUniforms->ambientLight.set(vec4(s_main->currentEntity->ambientLight / 255.0f, 0)); - s_main->entityUniforms->directedLight.set(vec4(s_main->currentEntity->directedLight / 255.0f, 0)); + s_main->entityUniforms->ambientLight.set(vec4(util::ToLinear(s_main->currentEntity->ambientLight / 255.0f), 0)); + s_main->entityUniforms->directedLight.set(vec4(util::ToLinear(s_main->currentEntity->directedLight / 255.0f), 0)); s_main->entityUniforms->lightDirection.set(vec4(s_main->currentEntity->lightDir, 0)); } diff --git a/code/renderer_bgfx/Precompiled.h b/code/renderer_bgfx/Precompiled.h index ecb6c25..87f3a02 100644 --- a/code/renderer_bgfx/Precompiled.h +++ b/code/renderer_bgfx/Precompiled.h @@ -1608,6 +1608,7 @@ namespace util vec3 MirroredPoint(const vec3 in, const Transform &surface, const Transform &camera); vec3 MirroredVector(const vec3 in, const Transform &surface, const Transform &camera); vec3 OverbrightenColor(vec3 color); + void OverbrightenColor(const uint8_t *src, uint8_t *dest); char *SkipPath(char *pathname); const char *GetFilename(const char *name); diff --git a/code/renderer_bgfx/Util.cpp b/code/renderer_bgfx/Util.cpp index 753fd91..63d8253 100644 --- a/code/renderer_bgfx/Util.cpp +++ b/code/renderer_bgfx/Util.cpp @@ -407,6 +407,28 @@ vec3 OverbrightenColor(vec3 color) return color; } +void OverbrightenColor(const uint8_t *src, uint8_t *dest) +{ + int r = int(src[0] * g_overbrightFactor); + int g = int(src[1] * g_overbrightFactor); + int b = int(src[2] * g_overbrightFactor); + + // Normalize by color instead of saturating to white. + if ((r | g | b) > 255) + { + int max = r > g ? r : g; + max = max > b ? max : b; + r = r * 255 / max; + g = g * 255 / max; + b = b * 255 / max; + } + + dest[0] = r; + dest[1] = g; + dest[2] = b; + dest[3] = src[3]; +} + char *SkipPath(char *pathname) { char *last = pathname; diff --git a/code/renderer_bgfx/World.cpp b/code/renderer_bgfx/World.cpp index 5dceecb..50b503a 100644 --- a/code/renderer_bgfx/World.cpp +++ b/code/renderer_bgfx/World.cpp @@ -780,6 +780,13 @@ void Load(const char *name) s_world->lightGridData.resize(lump.filelen); memcpy(s_world->lightGridData.data(), &fileData[lump.fileofs], lump.filelen); } + + // deal with overbright bits + for (int i = 0; i < numGridPoints; i++) + { + util::OverbrightenColor(&s_world->lightGridData[i*8], &s_world->lightGridData[i*8]); + util::OverbrightenColor(&s_world->lightGridData[i*8+3], &s_world->lightGridData[i*8+3]); + } } // Materials @@ -1266,12 +1273,12 @@ void SampleLightGrid(vec3 position, vec3 *ambientLight, vec3 *directedLight, vec totalFactor += factor; - (*ambientLight)[0] += factor * data[0] * g_overbrightFactor; - (*ambientLight)[1] += factor * data[1] * g_overbrightFactor; - (*ambientLight)[2] += factor * data[2] * g_overbrightFactor; - (*directedLight)[0] += factor * data[3] * g_overbrightFactor; - (*directedLight)[1] += factor * data[4] * g_overbrightFactor; - (*directedLight)[2] += factor * data[5] * g_overbrightFactor; + (*ambientLight)[0] += factor * data[0]; + (*ambientLight)[1] += factor * data[1]; + (*ambientLight)[2] += factor * data[2]; + (*directedLight)[0] += factor * data[3]; + (*directedLight)[1] += factor * data[4]; + (*directedLight)[2] += factor * data[5]; int lat = data[7]; int lng = data[6]; @@ -1295,8 +1302,6 @@ void SampleLightGrid(vec3 position, vec3 *ambientLight, vec3 *directedLight, vec (*directedLight) *= totalFactor; } - //*ambientLight = util::OverbrightenColor(*ambientLight); - //*directedLight = util::OverbrightenColor(*directedLight); (*lightDir) = direction; lightDir->normalizeFast(); }