Apply BGE patch 11137: Render objects with negative scaling correctly (as in Blender)
authorBenoit Bolsee <benoit.bolsee@online.be>
Sun, 25 May 2008 14:37:39 +0000 (14:37 +0000)
committerBenoit Bolsee <benoit.bolsee@online.be>
Sun, 25 May 2008 14:37:39 +0000 (14:37 +0000)
source/gameengine/BlenderRoutines/KX_BlenderRenderTools.cpp
source/gameengine/BlenderRoutines/KX_BlenderRenderTools.h
source/gameengine/GamePlayer/common/GPC_RenderTools.cpp
source/gameengine/GamePlayer/common/GPC_RenderTools.h
source/gameengine/Ketsji/KX_GameObject.cpp
source/gameengine/Ketsji/KX_GameObject.h
source/gameengine/Rasterizer/RAS_IRenderTools.h
source/gameengine/Rasterizer/RAS_MaterialBucket.cpp

index a656c5e5523c0f00dfd46902c6fd7b604cc0488d..ffd66655069a076e89811f6506aa6c00b8f282a2 100644 (file)
@@ -125,6 +125,22 @@ void KX_BlenderRenderTools::BeginFrame(RAS_IRasterizer* rasty)
 
 }
 
+void KX_BlenderRenderTools::SetClientObject(void* obj)
+{
+       if (m_clientobject != obj)
+       {
+               if (obj == NULL || !((KX_GameObject*)obj)->IsNegativeScaling())
+               {
+                       glFrontFace(GL_CCW);
+               } else 
+               {
+                       glFrontFace(GL_CW);
+               }
+               m_clientobject = obj;
+               m_modified = true;
+       }
+}
+
 bool KX_BlenderRenderTools::RayHit(KX_ClientObjectInfo* client, MT_Point3& hit_point, MT_Vector3& hit_normal, void * const data)
 {
        double* const oglmatrix = (double* const) data;
index 662f5bd9af14383f6b0dad0ed673a1500df5b823..31eaa14d66b980aff754a45667d48cf2a0950b89 100644 (file)
@@ -105,6 +105,8 @@ public:
 
        virtual void Render2DFilters(RAS_ICanvas* canvas);
 
+       virtual void SetClientObject(void* obj);
+
 };
 
 #endif //__KX_BLENDERRENDERTOOLS
index edda7657ef950dd3c8fb6b3ba094e5042e049caa..885981a2898dd90de87411ac65ed953c25029f74 100644 (file)
@@ -462,6 +462,22 @@ int GPC_RenderTools::applyLights(int objectlayer)
 
 }
 
+void GPC_RenderTools::SetClientObject(void* obj)
+{
+       if (m_clientobject != obj)
+       {
+               if (obj == NULL || !((KX_GameObject*)obj)->IsNegativeScaling())
+               {
+                       glFrontFace(GL_CCW);
+               } else 
+               {
+                       glFrontFace(GL_CW);
+               }
+               m_clientobject = obj;
+               m_modified = true;
+       }
+}
+
 bool GPC_RenderTools::RayHit(KX_ClientObjectInfo* client, MT_Point3& hit_point, MT_Vector3& hit_normal, void * const data)
 {
        double* const oglmatrix = (double* const) data;
index 9b86869af733cd13049ab1f0507d141cb2f8b0a6..ee0212da6438597509cb1b3483b118fafbacdac4 100644 (file)
@@ -153,6 +153,8 @@ public:
 
        virtual void Render2DFilters(RAS_ICanvas* canvas);
 
+       virtual void SetClientObject(void* obj);
+
 protected:
        /** 
         * Copied from KX_BlenderGL.cpp in KX_blenderhook
index 5fd5d2d54926fcf8c17a63e3a05c81bfaf9e2d54..dada47e2fa46a54185cc151e2a6c0123373b21e5 100644 (file)
@@ -77,6 +77,7 @@ KX_GameObject::KX_GameObject(
        m_layer(0),
        m_bSuspendDynamics(false),
        m_bUseObjectColor(false),
+       m_bIsNegativeScaling(false),
        m_bVisible(true),
        m_pPhysicsController1(NULL),
        m_pPhysicsEnvironment(NULL),
@@ -335,7 +336,7 @@ double*     KX_GameObject::GetOpenGLMatrix()
        trans.setBasis(GetSGNode()->GetWorldOrientation());
        
        MT_Vector3 scaling = GetSGNode()->GetWorldScaling();
-       
+       m_bIsNegativeScaling = ((scaling[0] < 0.0) ^ (scaling[1] < 0.0) ^ (scaling[2] < 0.0)) ? true : false;
        trans.scale(scaling[0], scaling[1], scaling[2]);
        trans.getValue(fl);
 
index 6e765978821e7a1c4d2231d5679d77dc9f796d79..3758651f53dee8f50609a6f93635b718f50e1f5d 100644 (file)
@@ -75,6 +75,7 @@ protected:
        
        bool                                                            m_bSuspendDynamics;
        bool                                                            m_bUseObjectColor;
+       bool                                                            m_bIsNegativeScaling;
        MT_Vector4                                                      m_objectColor;
 
        // Is this object set to be visible? Only useful for the
@@ -598,6 +599,14 @@ public:
                void
        );
                
+       /**
+        * Get the negative scaling state
+        */
+               bool
+       IsNegativeScaling(
+               void
+       ) { return m_bIsNegativeScaling; }
+
        /**
         * @section Logic bubbling methods.
         */
index 16e15653c826e44d66c1a499bd7cb9b3fb50e669..bcbf907741b1be74842a4cd65d0e21aa93990967 100644 (file)
@@ -146,6 +146,7 @@ public:
                int layer
        )=0;
 
+       virtual
                void    
        SetClientObject(
                void* obj
index 02e84f8a243d29edc64570441d5e5665a8347306..96ce220ae4d65af8e52e632d5e8b72079acca2c9 100644 (file)
@@ -325,6 +325,8 @@ void RAS_MaterialBucket::Render(const MT_Transform& cameratrans,
                while (ActivateMaterial(cameratrans, rasty, rendertools, drawmode))
                        RenderMeshSlot(cameratrans, rasty, rendertools, *it, drawmode);
        }
+       // to reset the eventual GL_CW mode
+       rendertools->SetClientObject(NULL);
 }