From 649799dac6deb687609d80d2a64eb8092e274e8f Mon Sep 17 00:00:00 2001 From: havoc Date: Fri, 27 Nov 2009 07:42:13 +0000 Subject: [PATCH] more work on mod_generatelightmaps: calculate bent normal for light dir instead of trying to convert sh1 use half-angle shading (soft lighting) instead of hard shading git-svn-id: svn://svn.icculus.org/twilight/trunk/darkplaces@9519 d7cf8633-e32d-0410-b094-e92efae38249 --- model_shared.c | 51 ++++++++++++++++++++++++++++---------------------- r_shadow.c | 14 +++++++++----- 2 files changed, 38 insertions(+), 27 deletions(-) diff --git a/model_shared.c b/model_shared.c index ae8060aa..44a86b00 100644 --- a/model_shared.c +++ b/model_shared.c @@ -3034,25 +3034,31 @@ lightmaptriangle_t; lightmaptriangle_t *mod_generatelightmaps_lightmaptriangles; -extern void R_SampleRTLights(const float *pos, float *sh1); +extern void R_SampleRTLights(const float *pos, float *sample); -static void Mod_GenerateLightmaps_SamplePoint(const float *pos, float *sh1) +static void Mod_GenerateLightmaps_SamplePoint(const float *pos, float *sample) { int i; - for (i = 0;i < 4*3;i++) - sh1[i] = 0.0f; - R_SampleRTLights(pos, sh1); + for (i = 0;i < 5*3;i++) + sample[i] = 0.0f; + R_SampleRTLights(pos, sample); } static void Mod_GenerateLightmaps_LightmapSample(const float *pos, const float *normal, unsigned char *lm_bgr, unsigned char *lm_dir) { - float sh1[4*3]; + float sample[5*3]; float color[3]; float dir[3]; - Mod_GenerateLightmaps_SamplePoint(pos, sh1); - VectorSet(dir, VectorLength(sh1 + 3), VectorLength(sh1 + 6), VectorLength(sh1 + 9)); + float f; + Mod_GenerateLightmaps_SamplePoint(pos, sample); + //VectorSet(dir, sample[3] + sample[4] + sample[5], sample[6] + sample[7] + sample[8], sample[9] + sample[10] + sample[11]); + VectorCopy(sample + 12, dir); VectorNormalize(dir); - VectorScale(sh1, 127.5f, color); + VectorAdd(dir, normal, dir); + VectorNormalize(dir); + f = DotProduct(dir, normal); + f = max(0, f) * 255.0f; + VectorScale(sample, f, color); //VectorCopy(normal, dir); if (r_test.integer & 1) dir[0] *= -1.0f; if (r_test.integer & 2) dir[1] *= -1.0f; @@ -3062,35 +3068,36 @@ static void Mod_GenerateLightmaps_LightmapSample(const float *pos, const float * lm_bgr[1] = (unsigned char)bound(0.0f, color[1], 255.0f); lm_bgr[2] = (unsigned char)bound(0.0f, color[0], 255.0f); lm_bgr[3] = 255; - lm_dir[0] = (unsigned char)dir[0]; + lm_dir[0] = (unsigned char)dir[2]; lm_dir[1] = (unsigned char)dir[1]; - lm_dir[2] = (unsigned char)dir[2]; + lm_dir[2] = (unsigned char)dir[0]; lm_dir[3] = 255; } static void Mod_GenerateLightmaps_VertexSample(const float *pos, const float *normal, float *vertex_color) { - float sh1[4*3]; - Mod_GenerateLightmaps_SamplePoint(pos, sh1); - VectorCopy(sh1, vertex_color); + float sample[5*3]; + Mod_GenerateLightmaps_SamplePoint(pos, sample); + VectorCopy(sample, vertex_color); } static void Mod_GenerateLightmaps_GridSample(const float *pos, q3dlightgrid_t *s) { - float sh1[4*3]; + float sample[5*3]; float ambient[3]; float diffuse[3]; float dir[3]; - Mod_GenerateLightmaps_SamplePoint(pos, sh1); - // calculate the direction we'll use to reduce the sh1 to a directional light source - VectorSet(dir, VectorLength(sh1 + 3), VectorLength(sh1 + 6), VectorLength(sh1 + 9)); + Mod_GenerateLightmaps_SamplePoint(pos, sample); + // calculate the direction we'll use to reduce the sample to a directional light source + VectorCopy(sample + 12, dir); + //VectorSet(dir, sample[3] + sample[4] + sample[5], sample[6] + sample[7] + sample[8], sample[9] + sample[10] + sample[11]); VectorNormalize(dir); // scale the ambient from 0-2 to 0-255 - VectorScale(sh1, 127.5f, ambient); + VectorScale(sample, 255.0f, ambient); // extract the diffuse color along the chosen direction and scale it - diffuse[0] = (dir[0]*sh1[3] + dir[1]*sh1[6] + dir[2]*sh1[ 9] + sh1[0]) * 127.5f; - diffuse[1] = (dir[0]*sh1[4] + dir[1]*sh1[7] + dir[2]*sh1[10] + sh1[1]) * 127.5f; - diffuse[2] = (dir[0]*sh1[5] + dir[1]*sh1[8] + dir[2]*sh1[11] + sh1[2]) * 127.5f; + diffuse[0] = (dir[0]*sample[3] + dir[1]*sample[6] + dir[2]*sample[ 9] + sample[0]) * 255.0f; + diffuse[1] = (dir[0]*sample[4] + dir[1]*sample[7] + dir[2]*sample[10] + sample[1]) * 255.0f; + diffuse[2] = (dir[0]*sample[5] + dir[1]*sample[8] + dir[2]*sample[11] + sample[2]) * 255.0f; // encode to the grid format s->ambientrgb[0] = (unsigned char)bound(0.0f, ambient[0], 255.0f); s->ambientrgb[1] = (unsigned char)bound(0.0f, ambient[1], 255.0f); diff --git a/r_shadow.c b/r_shadow.c index 293500fd..b1f99d18 100644 --- a/r_shadow.c +++ b/r_shadow.c @@ -5098,7 +5098,7 @@ void R_Shadow_DrawLightSprites(void) R_MeshQueue_AddTransparent(r_editlights_cursorlocation, R_Shadow_DrawCursor_TransparentCallback, NULL, 0, NULL); } -void R_SampleRTLights(const float *pos, float *sh1) +void R_SampleRTLights(const float *pos, float *sample) { int flag; size_t lightindex; @@ -5129,12 +5129,16 @@ void R_SampleRTLights(const float *pos, float *sh1) intensity = dist < 1 ? ((1.0f - dist) * r_shadow_lightattenuationlinearscale.value / (r_shadow_lightattenuationdividebias.value + dist*dist)) : 0; if (intensity <= 0) continue; + // scale down intensity to add to both ambient and diffuse + intensity *= 0.5f; VectorNormalize(relativepoint); VectorScale(rtlight->color, intensity, color); - VectorMA(sh1 , 0.5f , color, sh1 ); - VectorMA(sh1 + 3, relativepoint[0], color, sh1 + 3); - VectorMA(sh1 + 6, relativepoint[1], color, sh1 + 6); - VectorMA(sh1 + 9, relativepoint[2], color, sh1 + 9); + VectorMA(sample , 1.0f , color, sample ); + VectorMA(sample + 3, relativepoint[0], color, sample + 3); + VectorMA(sample + 6, relativepoint[1], color, sample + 6); + VectorMA(sample + 9, relativepoint[2], color, sample + 9); + intensity *= VectorLength(color); + VectorMA(sample + 12, intensity, relativepoint, sample + 12); } } -- 2.39.2