- Improved dynamic lights on models

This commit is contained in:
Magnus Norddahl 2017-07-25 23:00:09 +02:00
parent d2e0933a81
commit 0c0f0789c2
8 changed files with 53 additions and 12 deletions

View file

@ -58,7 +58,7 @@ struct FDynLightData
bool gl_GetLight(int group, Plane & p, ADynamicLight * light, bool checkside, FDynLightData &data);
bool gl_GetLight(int group, Plane & p, ADynamicLight * light, bool checkside, FDynLightData &data, bool planecheck = true);
void gl_UploadLights(FDynLightData &data);

View file

@ -63,22 +63,24 @@ CVAR(Int, gl_attenuate, -1, 0); // This is mainly a debug option.
// Sets up the parameters to render one dynamic light onto one plane
//
//==========================================================================
bool gl_GetLight(int group, Plane & p, ADynamicLight * light, bool checkside, FDynLightData &ldata)
bool gl_GetLight(int group, Plane & p, ADynamicLight * light, bool checkside, FDynLightData &ldata, bool planecheck)
{
int i = 0;
DVector3 pos = light->PosRelative(group);
float dist = fabsf(p.DistToPoint(pos.X, pos.Z, pos.Y));
float radius = (light->GetRadius());
if (radius <= 0.f) return false;
if (dist > radius) return false;
if (checkside && gl_lights_checkside && p.PointOnSide(pos.X, pos.Z, pos.Y))
{
return false;
}
if (planecheck)
{
float dist = fabsf(p.DistToPoint(pos.X, pos.Z, pos.Y));
if (radius <= 0.f) return false;
if (dist > radius) return false;
if (checkside && gl_lights_checkside && p.PointOnSide(pos.X, pos.Z, pos.Y))
{
return false;
}
}
float cs;
if (light->IsAdditive())

View file

@ -40,6 +40,8 @@
#include "gl/shaders/gl_shader.h"
#include "gl/data/gl_vertexbuffer.h"
extern int modellightindex;
static float avertexnormals[NUMVERTEXNORMALS][3] = {
#include "tab_anorms.h"
};
@ -379,6 +381,7 @@ void FDMDModel::RenderFrame(FTexture * skin, int frameno, int frameno2, double i
gl_RenderState.SetInterpolationFactor((float)inter);
gl_RenderState.Apply();
if (modellightindex != -1) gl_RenderState.ApplyLightIndex(modellightindex);
mVBuf->SetupFrame(frames[frameno].vindex, frames[frameno2].vindex, lodInfo[0].numTriangles * 3);
glDrawArrays(GL_TRIANGLES, 0, lodInfo[0].numTriangles * 3);
gl_RenderState.SetInterpolationFactor(0.f);

View file

@ -35,6 +35,8 @@
#define MAX_QPATH 64
extern int modellightindex;
//===========================================================================
//
// decode the lat/lng normal to a 3 float normal
@ -372,6 +374,7 @@ void FMD3Model::RenderFrame(FTexture * skin, int frameno, int frameno2, double i
gl_RenderState.SetMaterial(tex, CLAMP_NONE, translation, -1, false);
gl_RenderState.Apply();
if (modellightindex != -1) gl_RenderState.ApplyLightIndex(modellightindex);
mVBuf->SetupFrame(surf->vindex + frameno * surf->numVertices, surf->vindex + frameno2 * surf->numVertices, surf->numVertices);
glDrawElements(GL_TRIANGLES, surf->numTriangles * 3, GL_UNSIGNED_INT, (void*)(intptr_t)(surf->iindex * sizeof(unsigned int)));
}

View file

@ -50,6 +50,7 @@
#include "gl/utility/gl_convert.h"
#include "gl/renderer/gl_renderstate.h"
extern int modellightindex;
//===========================================================================
//
@ -445,6 +446,7 @@ void FVoxelModel::RenderFrame(FTexture * skin, int frame, int frame2, double int
gl_RenderState.SetMaterial(tex, CLAMP_NOFILTER, translation, -1, false);
gl_RenderState.Apply();
if (modellightindex != -1) gl_RenderState.ApplyLightIndex(modellightindex);
mVBuf->SetupFrame(0, 0, 0);
glDrawElements(GL_TRIANGLES, mNumIndices, GL_UNSIGNED_INT, (void*)(intptr_t)0);
}

View file

@ -326,7 +326,10 @@ void GLSprite::Draw(int pass)
{
if (gl_lights && GLRenderer->mLightCount && mDrawer->FixedColormap == CM_DEFAULT && !fullbright)
{
gl_SetDynSpriteLight(gl_light_sprites ? actor : NULL, gl_light_particles ? particle : NULL);
if (modelframe && !particle)
gl_SetDynModelLight(gl_light_sprites ? actor : NULL, actor->X(), actor->Y(), actor->Center(), actor->subsector);
else
gl_SetDynSpriteLight(gl_light_sprites ? actor : NULL, gl_light_particles ? particle : NULL);
}
sector_t *cursec = actor ? actor->Sector : particle ? particle->subsector->sector : nullptr;
if (cursec != nullptr)

View file

@ -42,7 +42,10 @@
#include "gl/scene/gl_portal.h"
#include "gl/shaders/gl_shader.h"
#include "gl/textures/gl_material.h"
#include "gl/dynlights/gl_lightbuffer.h"
FDynLightData modellightdata;
int modellightindex = -1;
//==========================================================================
//
@ -114,6 +117,7 @@ void gl_SetDynSpriteLight(AActor *self, float x, float y, float z, subsector_t *
node = node->nextLight;
}
gl_RenderState.SetDynLight(out[0], out[1], out[2]);
modellightindex = -1;
}
void gl_SetDynSpriteLight(AActor *thing, particle_t *particle)
@ -127,3 +131,26 @@ void gl_SetDynSpriteLight(AActor *thing, particle_t *particle)
gl_SetDynSpriteLight(NULL, particle->Pos.X, particle->Pos.Y, particle->Pos.Z, particle->subsector);
}
}
void gl_SetDynModelLight(AActor *self, float x, float y, float z, subsector_t * subsec)
{
Plane p;
p.Set(subsec->sector->ceilingplane); // Is this correct?
modellightdata.Clear();
// Go through both light lists
FLightNode * node = subsec->lighthead;
while (node)
{
ADynamicLight *light = node->lightsource;
if (light->visibletoplayer && !(light->flags2&MF2_DORMANT) && (!(light->lightflags&LF_DONTLIGHTSELF) || light->target != self) && !(light->lightflags&LF_DONTLIGHTACTORS))
{
gl_GetLight(subsec->sector->PortalGroup, p, node->lightsource, false, modellightdata, false);
}
node = node->nextLight;
}
gl_RenderState.SetDynLight(0, 0, 0);
modellightindex = GLRenderer->mLights->UploadLights(modellightdata);
}

View file

@ -422,5 +422,6 @@ inline float Dist2(float x1,float y1,float x2,float y2)
void gl_SetDynSpriteLight(AActor *self, float x, float y, float z, subsector_t *subsec);
void gl_SetDynSpriteLight(AActor *actor, particle_t *particle);
void gl_SetDynModelLight(AActor *self, float x, float y, float z, subsector_t * subsec);
#endif