diff options
author | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2009-06-09 17:51:32 +0400 |
---|---|---|
committer | Brecht Van Lommel <brechtvanlommel@pandora.be> | 2009-06-09 17:51:32 +0400 |
commit | e29c9bc4da59a8e8db933e1a53a181e396f4706b (patch) | |
tree | f77ce5061bd6d019a8b95d05b49eb96fdba52ee3 /source/gameengine/Ketsji/KX_Light.cpp | |
parent | 20eaa1466dbb530e583699e189c9f8b8597b7eb4 (diff) |
Fix for bug #18900: game engine lights in non-glsl mode did move
anymore, missing matrix update. Also move some code to KX_LightObject
to avoid duplication with player.
Diffstat (limited to 'source/gameengine/Ketsji/KX_Light.cpp')
-rw-r--r-- | source/gameengine/Ketsji/KX_Light.cpp | 97 |
1 files changed, 95 insertions, 2 deletions
diff --git a/source/gameengine/Ketsji/KX_Light.cpp b/source/gameengine/Ketsji/KX_Light.cpp index fe575384a35..274d8f26d78 100644 --- a/source/gameengine/Ketsji/KX_Light.cpp +++ b/source/gameengine/Ketsji/KX_Light.cpp @@ -35,6 +35,8 @@ #pragma warning (disable : 4786) #endif +#include "GL/glew.h" + #include "KX_Light.h" #include "KX_Camera.h" #include "RAS_IRasterizer.h" @@ -43,6 +45,7 @@ #include "KX_PyMath.h" #include "DNA_object_types.h" +#include "DNA_scene_types.h" #include "GPU_material.h" KX_LightObject::KX_LightObject(void* sgReplicationInfo,SG_Callbacks callbacks, @@ -56,8 +59,8 @@ KX_LightObject::KX_LightObject(void* sgReplicationInfo,SG_Callbacks callbacks, m_rendertools(rendertools) { m_lightobj = lightobj; - m_lightobj.m_worldmatrix = GetOpenGLMatrixPtr(); m_lightobj.m_scene = sgReplicationInfo; + m_lightobj.m_light = this; m_rendertools->AddLight(&m_lightobj); m_glsl = glsl; m_blenderscene = ((KX_Scene*)sgReplicationInfo)->GetBlenderScene(); @@ -84,12 +87,102 @@ CValue* KX_LightObject::GetReplica() replica->ProcessReplica(); - replica->m_lightobj.m_worldmatrix = replica->GetOpenGLMatrixPtr(); + replica->m_lightobj.m_light = replica; m_rendertools->AddLight(&replica->m_lightobj); return replica; } +bool KX_LightObject::ApplyLight(KX_Scene *kxscene, int oblayer, int slot) +{ + KX_Scene* lightscene = (KX_Scene*)m_lightobj.m_scene; + float vec[4]; + int scenelayer = ~0; + + if(kxscene && kxscene->GetBlenderScene()) + scenelayer = kxscene->GetBlenderScene()->lay; + + /* only use lights in the same layer as the object */ + if(!(m_lightobj.m_layer & oblayer)) + return false; + /* only use lights in the same scene, and in a visible layer */ + if(kxscene != lightscene || !(m_lightobj.m_layer & scenelayer)) + return false; + + // lights don't get their openGL matrix updated, do it now + if(GetSGNode()->IsDirty()) + GetOpenGLMatrix(); + + MT_CmMatrix4x4& worldmatrix= *GetOpenGLMatrixPtr(); + + vec[0] = worldmatrix(0,3); + vec[1] = worldmatrix(1,3); + vec[2] = worldmatrix(2,3); + vec[3] = 1.0f; + + if(m_lightobj.m_type==RAS_LightObject::LIGHT_SUN) { + + vec[0] = worldmatrix(0,2); + vec[1] = worldmatrix(1,2); + vec[2] = worldmatrix(2,2); + //vec[0]= base->object->obmat[2][0]; + //vec[1]= base->object->obmat[2][1]; + //vec[2]= base->object->obmat[2][2]; + vec[3]= 0.0; + glLightfv((GLenum)(GL_LIGHT0+slot), GL_POSITION, vec); + } + else { + //vec[3]= 1.0; + glLightfv((GLenum)(GL_LIGHT0+slot), GL_POSITION, vec); + glLightf((GLenum)(GL_LIGHT0+slot), GL_CONSTANT_ATTENUATION, 1.0); + glLightf((GLenum)(GL_LIGHT0+slot), GL_LINEAR_ATTENUATION, m_lightobj.m_att1/m_lightobj.m_distance); + // without this next line it looks backward compatible. + //attennuation still is acceptable + glLightf((GLenum)(GL_LIGHT0+slot), GL_QUADRATIC_ATTENUATION, m_lightobj.m_att2/(m_lightobj.m_distance*m_lightobj.m_distance)); + + if(m_lightobj.m_type==RAS_LightObject::LIGHT_SPOT) { + vec[0] = -worldmatrix(0,2); + vec[1] = -worldmatrix(1,2); + vec[2] = -worldmatrix(2,2); + //vec[0]= -base->object->obmat[2][0]; + //vec[1]= -base->object->obmat[2][1]; + //vec[2]= -base->object->obmat[2][2]; + glLightfv((GLenum)(GL_LIGHT0+slot), GL_SPOT_DIRECTION, vec); + glLightf((GLenum)(GL_LIGHT0+slot), GL_SPOT_CUTOFF, m_lightobj.m_spotsize/2.0); + glLightf((GLenum)(GL_LIGHT0+slot), GL_SPOT_EXPONENT, 128.0*m_lightobj.m_spotblend); + } + else + glLightf((GLenum)(GL_LIGHT0+slot), GL_SPOT_CUTOFF, 180.0); + } + + if (m_lightobj.m_nodiffuse) { + vec[0] = vec[1] = vec[2] = vec[3] = 0.0; + } + else { + vec[0]= m_lightobj.m_energy*m_lightobj.m_red; + vec[1]= m_lightobj.m_energy*m_lightobj.m_green; + vec[2]= m_lightobj.m_energy*m_lightobj.m_blue; + vec[3]= 1.0; + } + + glLightfv((GLenum)(GL_LIGHT0+slot), GL_DIFFUSE, vec); + if(m_lightobj.m_nospecular) + { + vec[0] = vec[1] = vec[2] = vec[3] = 0.0; + } + else if (m_lightobj.m_nodiffuse) { + vec[0]= m_lightobj.m_energy*m_lightobj.m_red; + vec[1]= m_lightobj.m_energy*m_lightobj.m_green; + vec[2]= m_lightobj.m_energy*m_lightobj.m_blue; + vec[3]= 1.0; + } + + glLightfv((GLenum)(GL_LIGHT0+slot), GL_SPECULAR, vec); + glEnable((GLenum)(GL_LIGHT0+slot)); + + return true; +} + GPULamp *KX_LightObject::GetGPULamp() { if(m_glsl) |