Esempio n. 1
0
 internal Vector3 GetCameraLookAtVectorEitherWay()
 {
     if (IsFirstPersonMode && _firstPersonObject != null)
     {
         return(HelperCamera.GetLookAtVector());
     }
     else
     {
         return(GetCameraLookAtVector());
     }
 }
Esempio n. 2
0
        internal override void Draw(GameObject g, ref Matrix4 viewProjection, ref Matrix4 viewProjectionShadowBiased, ref Matrix4 viewProjectionShadowBiased2, HelperFrustum frustum, ref float[] lightColors, ref float[] lightTargets, ref float[] lightPositions, int lightCount, ref int lightShadow)
        {
            if (g == null || !g.HasModel || g.CurrentWorld == null || g.Opacity <= 0)
            {
                return;
            }

            g.IsInsideScreenSpace = frustum.SphereVsFrustum(g.GetCenterPointForAllHitboxes(), g.GetMaxDiameter() / 2);
            if (!g.IsInsideScreenSpace)
            {
                return;
            }

            GL.UseProgram(mProgramId);
            GL.Disable(EnableCap.Blend);

            lock (g)
            {
                GL.Uniform1(mUniform_BiasCoefficient, KWEngine.ShadowMapCoefficient);
                GL.Uniform4(mUniform_Glow, g.Glow.X, g.Glow.Y, g.Glow.Z, g.Glow.W);
                GL.Uniform3(mUniform_TintColor, g.Color.X, g.Color.Y, g.Color.Z);


                // How many lights are there?
                GL.Uniform1(mUniform_LightCount, lightCount);
                GL.Uniform4(mUniform_LightsColors, KWEngine.MAX_LIGHTS, lightColors);
                GL.Uniform4(mUniform_LightsTargets, KWEngine.MAX_LIGHTS, lightTargets);
                GL.Uniform4(mUniform_LightsPositions, KWEngine.MAX_LIGHTS, lightPositions);


                // Sun
                GL.Uniform4(mUniform_SunIntensity, g.CurrentWorld.GetSunColor());
                GL.Uniform3(mUniform_SunPosition, g.CurrentWorld.GetSunPosition().X, g.CurrentWorld.GetSunPosition().Y, g.CurrentWorld.GetSunPosition().Z);
                Vector3 sunDirection = g.CurrentWorld.GetSunPosition() - g.CurrentWorld.GetSunTarget();
                sunDirection.NormalizeFast();
                GL.Uniform3(mUniform_SunDirection, ref sunDirection);
                GL.Uniform1(mUniform_SunAmbient, g.CurrentWorld.SunAmbientFactor);
                GL.Uniform1(mUniform_SunAffection, g.IsAffectedBySun ? 1 : 0);
                GL.Uniform1(mUniform_LightAffection, g.IsAffectedByLight ? 1 : 0);

                // Camera
                if (!CurrentWorld.IsFirstPersonMode)
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetCameraPosition().X, g.CurrentWorld.GetCameraPosition().Y, g.CurrentWorld.GetCameraPosition().Z);
                    GL.Uniform3(mUniform_uCameraDirection, g.CurrentWorld.GetCameraLookAtVector());
                }
                else
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetFirstPersonObject().Position.X, g.CurrentWorld.GetFirstPersonObject().Position.Y + g.CurrentWorld.GetFirstPersonObject().FPSEyeOffset, g.CurrentWorld.GetFirstPersonObject().Position.Z);
                    GL.Uniform3(mUniform_uCameraDirection, HelperCamera.GetLookAtVector());
                }

                // Upload depth texture (shadow mapping)
                GL.ActiveTexture(TextureUnit.Texture3);
                GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap);
                GL.Uniform1(mUniform_TextureShadowMap, 3);

                try
                {
                    Matrix4.Mult(ref g.ModelMatrixForRenderPass[0], ref viewProjection, out _modelViewProjection);
                    Matrix4.Transpose(ref g.ModelMatrixForRenderPass[0], out _normalMatrix);
                    Matrix4.Invert(ref _normalMatrix, out _normalMatrix);
                }
                catch (Exception)
                {
                    _normalMatrix = g.ModelMatrixForRenderPass[0];
                }

                GL.UniformMatrix4(mUniform_ModelMatrix, false, ref g.ModelMatrixForRenderPass[0]);
                GL.UniformMatrix4(mUniform_NormalMatrix, false, ref _normalMatrix);
                GL.UniformMatrix4(mUniform_MVP, false, ref _modelViewProjection);

                if (lightShadow >= 0)
                {
                    Matrix4 modelViewProjectionMatrixBiased2 = g.ModelMatrixForRenderPass[0] * viewProjectionShadowBiased2;

                    GL.ActiveTexture(TextureUnit.Texture5);
                    GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap2);
                    GL.Uniform1(mUniform_TextureShadowMap2, 5);

                    GL.Uniform1(mUniform_ShadowLightPosition, lightShadow);
                    GL.UniformMatrix4(mUniform_MVPShadowMap2, false, ref modelViewProjectionMatrixBiased2);
                    GL.Uniform1(mUniform_BiasCoefficient2, CurrentWorld.GetLightObjects().ElementAt(lightShadow).ShadowMapBiasCoefficient);
                }
                else
                {
                    GL.Uniform1(mUniform_ShadowLightPosition, -1);
                    GL.ActiveTexture(TextureUnit.Texture5);
                    GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap2);
                    GL.Uniform1(mUniform_TextureShadowMap2, 5);
                }

                foreach (string meshName in g.Model.Meshes.Keys)
                {
                    GeoMesh mesh = g.Model.Meshes[meshName];

                    GL.Uniform1(mUniform_SpecularPower, mesh.Material.SpecularPower);
                    GL.Uniform1(mUniform_SpecularArea, mesh.Material.SpecularArea);

                    // Shadow mapping
                    Matrix4 modelViewProjectionMatrixBiased = g.ModelMatrixForRenderPass[0] * viewProjectionShadowBiased;
                    GL.UniformMatrix4(mUniform_MVPShadowMap, false, ref modelViewProjectionMatrixBiased);

                    GL.Uniform2(mUniform_TextureTransform, mesh.Terrain.mTexX, mesh.Terrain.mTexY);
                    int texId = mesh.Material.TextureDiffuse.OpenGLID;
                    if (texId > 0)
                    {
                        GL.ActiveTexture(TextureUnit.Texture0);
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_Texture, 0);
                        GL.Uniform1(mUniform_TextureUse, 1);
                    }
                    else
                    {
                        GL.Uniform1(mUniform_TextureUse, 0);
                    }



                    texId = mesh.Material.TextureNormal.OpenGLID;
                    if (texId > 0)
                    {
                        GL.ActiveTexture(TextureUnit.Texture1);
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_TextureNormalMap, 1);
                        GL.Uniform1(mUniform_TextureUseNormalMap, 1);
                    }
                    else
                    {
                        GL.Uniform1(mUniform_TextureUseNormalMap, 0);
                    }


                    texId = mesh.Material.TextureSpecular.OpenGLID;
                    if (texId > 0)
                    {
                        GL.ActiveTexture(TextureUnit.Texture2);
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_TextureSpecularMap, 2);
                        GL.Uniform1(mUniform_TextureUseSpecularMap, 1);
                    }
                    else
                    {
                        GL.Uniform1(mUniform_TextureUseSpecularMap, 0);
                    }

                    // Blendmapping:
                    if (mesh.Terrain._texBlend > 0 && mesh.Terrain._texBlend != KWEngine.TextureBlack)
                    {
                        GL.ActiveTexture(TextureUnit.Texture10);
                        GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texBlend);
                        GL.Uniform1(mUniform_TextureBlend, 10);

                        GL.ActiveTexture(TextureUnit.Texture11);
                        GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texR);
                        GL.Uniform1(mUniform_TextureRed, 11);

                        if (mesh.Terrain._texG > 0 && mesh.Terrain._texG != KWEngine.TextureAlpha)
                        {
                            GL.ActiveTexture(TextureUnit.Texture12);
                            GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texG);
                            GL.Uniform1(mUniform_TextureGreen, 12);
                        }

                        if (mesh.Terrain._texB > 0 && mesh.Terrain._texB != KWEngine.TextureAlpha)
                        {
                            GL.ActiveTexture(TextureUnit.Texture13);
                            GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texB);
                            GL.Uniform1(mUniform_TextureBlue, 13);
                        }

                        GL.Uniform1(mUniform_UseBlend, 1);
                    }
                    else
                    {
                        GL.Uniform1(mUniform_UseBlend, 0);
                    }

                    GL.BindVertexArray(mesh.VAO);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, mesh.VBOIndex);
                    GL.DrawElements(mesh.Primitive, mesh.IndexCount, DrawElementsType.UnsignedInt, 0);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, 0);

                    GL.BindTexture(TextureTarget.Texture2D, 0);

                    GL.BindVertexArray(0);
                }
            }

            GL.UseProgram(0);
        }
Esempio n. 3
0
        internal override void Draw(GameObject g, ref Matrix4 viewProjection, ref Matrix4 viewProjectionShadowBiased, ref Matrix4 viewProjectionShadowBiased2, HelperFrustum frustum, ref float[] lightColors, ref float[] lightTargets, ref float[] lightPositions, int lightCount, ref int lightShadow)
        {
            if (g == null || !g.HasModel || g.CurrentWorld == null || g.Opacity <= 0)
            {
                return;
            }

            g.IsInsideScreenSpace = frustum.VolumeVsFrustum(g.GetCenterPointForAllHitboxes(), g.GetMaxDimensions().X, g.GetMaxDimensions().Y, g.GetMaxDimensions().Z);
            if (!g.IsInsideScreenSpace)
            {
                return;
            }

            GL.UseProgram(mProgramId);

            lock (g)
            {
                GL.Uniform1(mUniform_BiasCoefficient, KWEngine.ShadowMapCoefficient);

                GL.Uniform4(mUniform_Glow, g.Glow);
                GL.Uniform4(mUniform_Outline, g.ColorOutline);
                GL.Uniform3(mUniform_TintColor, g.Color);

                // How many lights are there?
                GL.Uniform1(mUniform_LightCount, lightCount);
                GL.Uniform4(mUniform_LightsColors, KWEngine.MAX_LIGHTS, lightColors);
                GL.Uniform4(mUniform_LightsTargets, KWEngine.MAX_LIGHTS, lightTargets);
                GL.Uniform4(mUniform_LightsPositions, KWEngine.MAX_LIGHTS, lightPositions);

                // Sun
                GL.Uniform4(mUniform_SunIntensity, g.CurrentWorld.GetSunColor());
                GL.Uniform3(mUniform_SunPosition, g.CurrentWorld.GetSunPosition().X, g.CurrentWorld.GetSunPosition().Y, g.CurrentWorld.GetSunPosition().Z);
                Vector3 sunDirection = g.CurrentWorld.GetSunPosition() - g.CurrentWorld.GetSunTarget();
                sunDirection.NormalizeFast();
                GL.Uniform3(mUniform_SunDirection, ref sunDirection);
                GL.Uniform1(mUniform_SunAmbient, g.CurrentWorld.SunAmbientFactor);

                GL.Uniform1(mUniform_SunAffection, g.IsAffectedBySun ? 1 : 0);
                GL.Uniform1(mUniform_LightAffection, g.IsAffectedByLight ? 1 : 0);

                // Camera
                if (!CurrentWorld.IsFirstPersonMode)
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetCameraPosition().X, g.CurrentWorld.GetCameraPosition().Y, g.CurrentWorld.GetCameraPosition().Z);
                    GL.Uniform3(mUniform_uCameraDirection, g.CurrentWorld.GetCameraLookAtVector());
                }
                else
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetFirstPersonObject().Position.X, g.CurrentWorld.GetFirstPersonObject().Position.Y + g.CurrentWorld.GetFirstPersonObject().FPSEyeOffset, g.CurrentWorld.GetFirstPersonObject().Position.Z);
                    GL.Uniform3(mUniform_uCameraDirection, HelperCamera.GetLookAtVector());
                }



                // Upload depth texture (shadow mapping)
                GL.ActiveTexture(TextureUnit.Texture3);
                GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap);
                GL.Uniform1(mUniform_TextureShadowMap, 3);

                if (lightShadow >= 0)
                {
                    GL.ActiveTexture(TextureUnit.Texture5);
                    GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap2);
                    GL.Uniform1(mUniform_TextureShadowMap2, 5);

                    GL.Uniform1(mUniform_ShadowLightPosition, lightShadow);
                    GL.Uniform1(mUniform_BiasCoefficient2, CurrentWorld.GetLightObjects().ElementAt(lightShadow).ShadowMapBiasCoefficient);
                }
                else
                {
                    GL.ActiveTexture(TextureUnit.Texture5);
                    GL.BindTexture(TextureTarget.Texture2D, GLWindow.CurrentWindow.TextureShadowMap2);
                    GL.Uniform1(mUniform_TextureShadowMap2, 5);
                    GL.Uniform1(mUniform_ShadowLightPosition, -1);
                }

                int index = 0;
                foreach (string meshName in g.Model.Meshes.Keys)
                {
                    if (g._cubeModel is GeoModelCube6)
                    {
                        index = 0;
                    }

                    // Matrices:
                    try
                    {
                        Matrix4.Mult(ref g.ModelMatrixForRenderPass[index], ref viewProjection, out _modelViewProjection);
                        Matrix4.Transpose(ref g.ModelMatrixForRenderPass[index], out _normalMatrix);
                        Matrix4.Invert(ref _normalMatrix, out _normalMatrix);
                    }
                    catch (Exception)
                    {
                        continue;
                    }

                    GL.UniformMatrix4(mUniform_ModelMatrix, false, ref g.ModelMatrixForRenderPass[index]);
                    GL.UniformMatrix4(mUniform_NormalMatrix, false, ref _normalMatrix);
                    GL.UniformMatrix4(mUniform_MVP, false, ref _modelViewProjection);

                    // Shadow mapping
                    Matrix4 modelViewProjectionMatrixBiased = g.ModelMatrixForRenderPass[index] * viewProjectionShadowBiased;
                    GL.UniformMatrix4(mUniform_MVPShadowMap, false, ref modelViewProjectionMatrixBiased);

                    if (lightShadow >= 0)
                    {
                        Matrix4 modelViewProjectionMatrixBiased2 = g.ModelMatrixForRenderPass[index] * viewProjectionShadowBiased2;
                        GL.UniformMatrix4(mUniform_MVPShadowMap2, false, ref modelViewProjectionMatrixBiased2);
                    }
                    index++;


                    GL.Disable(EnableCap.Blend);
                    GeoMesh mesh = g.Model.Meshes[meshName];
                    if (mesh.Material.Opacity <= 0)
                    {
                        continue;
                    }

                    if (mesh.Material.Opacity < 1 || g.Opacity < 1)
                    {
                        GL.Enable(EnableCap.Blend);
                    }
                    if (g.Opacity < mesh.Material.Opacity)
                    {
                        GL.Uniform1(mUniform_Opacity, g.Opacity);
                    }
                    else
                    {
                        GL.Uniform1(mUniform_Opacity, mesh.Material.Opacity);
                    }

                    Dictionary <GameObject.Override, object> overrides = null;
                    if (g._overrides.ContainsKey(mesh.Name))
                    {
                        overrides = g._overrides[mesh.Name];
                    }

                    if (mesh.BoneNames.Count > 0 && g.AnimationID >= 0 && g.Model.Animations != null && g.Model.Animations.Count > 0)
                    {
                        GL.Uniform1(mUniform_UseAnimations, 1);
                        for (int i = 0; i < g.BoneTranslationMatrices[meshName].Length; i++)
                        {
                            Matrix4 tmp = g.BoneTranslationMatrices[meshName][i];
                            GL.UniformMatrix4(mUniform_BoneTransforms + i, false, ref tmp);
                        }
                    }
                    else
                    {
                        GL.Uniform1(mUniform_UseAnimations, 0);
                    }

                    if (g._cubeModel != null)
                    {
                        GL.Uniform1(mUniform_SpecularPower, g._cubeModel.SpecularPower);
                        GL.Uniform1(mUniform_SpecularArea, g._cubeModel.SpecularArea);
                    }
                    else
                    {
                        if (overrides == null || overrides.Count == 0)
                        {
                            GL.Uniform1(mUniform_SpecularPower, mesh.Material.SpecularPower);
                        }
                        else
                        {
                            bool found = overrides.TryGetValue(GameObject.Override.SpecularPower, out object value);
                            if (found)
                            {
                                GL.Uniform1(mUniform_SpecularPower, (float)value);
                            }
                            else
                            {
                                GL.Uniform1(mUniform_SpecularPower, mesh.Material.SpecularPower);
                            }
                        }

                        if (overrides == null || overrides.Count == 0)
                        {
                            GL.Uniform1(mUniform_SpecularArea, mesh.Material.SpecularArea);
                        }
                        else
                        {
                            bool found = overrides.TryGetValue(GameObject.Override.SpecularArea, out object value);
                            if (found)
                            {
                                GL.Uniform1(mUniform_SpecularArea, (float)value);
                            }
                            else
                            {
                                GL.Uniform1(mUniform_SpecularArea, mesh.Material.SpecularArea);
                            }
                        }
                    }



                    if (g._cubeModel != null)
                    {
                        UploadMaterialForKWCube(g._cubeModel, mesh, g);
                        GL.Uniform1(mUniform_TextureUseLightMap, 0);
                    }
                    else
                    {
                        if (mesh.Material.TextureLight.OpenGLID > 0)
                        {
                            GL.ActiveTexture(TextureUnit.Texture8);
                            GL.BindTexture(TextureTarget.Texture2D, mesh.Material.TextureLight.OpenGLID);
                            GL.Uniform1(mUniform_TextureLightMap, 8);
                            GL.Uniform1(mUniform_TextureUseLightMap, 1);
                        }
                        else
                        {
                            GL.Uniform1(mUniform_TextureUseLightMap, 0);
                        }



                        bool   found         = false;
                        object overrideValue = null;
                        if (overrides != null && overrides.Count > 0)
                        {
                            found = overrides.TryGetValue(GameObject.Override.TextureTransform, out overrideValue);
                        }

                        if (found)
                        {
                            Vector2 uvTransform = (Vector2)overrideValue;
                            GL.Uniform2(mUniform_TextureTransform, uvTransform.X, uvTransform.Y);
                        }
                        else
                        {
                            GL.Uniform2(mUniform_TextureTransform, mesh.Material.TextureDiffuse.UVTransform.X, mesh.Material.TextureDiffuse.UVTransform.Y);
                        }

                        // Diffuse texture:
                        overrideValue = null;
                        found         = false;
                        int texId = -1;
                        if (overrides != null && overrides.Count > 0)
                        {
                            found = overrides.TryGetValue(GameObject.Override.TextureDiffuse, out overrideValue);
                        }
                        if (found)
                        {
                            texId = ((GeoTexture)overrideValue).OpenGLID;
                        }
                        else
                        {
                            texId = mesh.Material.TextureDiffuse.OpenGLID;
                        }

                        if (texId > 0)
                        {
                            GL.ActiveTexture(TextureUnit.Texture0);
                            GL.BindTexture(TextureTarget.Texture2D, texId);
                            GL.Uniform1(mUniform_Texture, 0);
                            GL.Uniform1(mUniform_TextureUse, 1);
                            GL.Uniform3(mUniform_BaseColor, 1f, 1f, 1f);
                        }
                        else
                        {
                            GL.Uniform1(mUniform_TextureUse, 0);
                            GL.Uniform3(mUniform_BaseColor, mesh.Material.ColorDiffuse.X, mesh.Material.ColorDiffuse.Y, mesh.Material.ColorDiffuse.Z);
                        }

                        overrideValue = null;
                        found         = false;
                        texId         = -1;
                        if (overrides != null && overrides.Count > 0)
                        {
                            found = overrides.TryGetValue(GameObject.Override.TextureNormal, out overrideValue);
                        }
                        if (found)
                        {
                            texId = ((GeoTexture)overrideValue).OpenGLID;
                        }
                        else
                        {
                            texId = mesh.Material.TextureNormal.OpenGLID;
                        }
                        if (texId > 0)
                        {
                            GL.ActiveTexture(TextureUnit.Texture1);
                            GL.BindTexture(TextureTarget.Texture2D, texId);
                            GL.Uniform1(mUniform_TextureNormalMap, 1);
                            GL.Uniform1(mUniform_TextureUseNormalMap, 1);
                        }
                        else
                        {
                            GL.Uniform1(mUniform_TextureUseNormalMap, 0);
                        }

                        overrideValue = null;
                        found         = false;
                        texId         = -1;
                        if (overrides != null)
                        {
                            found = overrides.TryGetValue(GameObject.Override.TextureSpecular, out overrideValue);
                        }
                        if (found)
                        {
                            texId = ((GeoTexture)overrideValue).OpenGLID;
                        }
                        else
                        {
                            texId = mesh.Material.TextureSpecular.OpenGLID;
                        }
                        if (texId > 0)
                        {
                            GL.ActiveTexture(TextureUnit.Texture2);
                            GL.BindTexture(TextureTarget.Texture2D, texId);
                            GL.Uniform1(mUniform_TextureSpecularMap, 2);
                            GL.Uniform1(mUniform_TextureUseSpecularMap, 1);
                            if (!found && mesh.Material.TextureSpecularIsRoughness)
                            {
                                GL.Uniform1(mUniform_TextureSpecularIsRoughness, mesh.Material.TextureSpecularIsRoughness ? 1 : 0);
                            }
                            else
                            {
                                GL.Uniform1(mUniform_TextureSpecularIsRoughness, 0);
                            }
                        }
                        else
                        {
                            GL.Uniform1(mUniform_TextureUseSpecularMap, 0);
                            GL.Uniform1(mUniform_TextureSpecularIsRoughness, 0);
                        }


                        if (mesh.Material.TextureEmissive.OpenGLID > 0)
                        {
                            GL.ActiveTexture(TextureUnit.Texture4);
                            GL.BindTexture(TextureTarget.Texture2D, mesh.Material.TextureEmissive.OpenGLID);
                            GL.Uniform1(mUniform_TextureEmissiveMap, 4);
                            GL.Uniform1(mUniform_TextureUseEmissiveMap, 1);
                        }
                        else
                        {
                            GL.Uniform1(mUniform_TextureUseEmissiveMap, 0);
                        }

                        if (g.ColorEmissive.W > 0)
                        {
                            GL.Uniform4(mUniform_EmissiveColor, g.ColorEmissive);
                        }
                        else
                        {
                            GL.Uniform4(mUniform_EmissiveColor, mesh.Material.ColorEmissive);
                        }
                    }

                    GL.BindVertexArray(mesh.VAO);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, mesh.VBOIndex);
                    GL.DrawElements(mesh.Primitive, mesh.IndexCount, DrawElementsType.UnsignedInt, 0);
                    //HelperGL.CheckGLErrors();
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, 0);
                    GL.BindVertexArray(0);
                    GL.BindTexture(TextureTarget.Texture2D, 0);
                }
            }
            GL.BindTexture(TextureTarget.Texture2D, 0);
            GL.UseProgram(0);
        }
Esempio n. 4
0
        internal void DrawAttachedModel(GameObject g, GeoModel attachedModel, ref Matrix4 viewProjection, int textureIndex, ref Matrix4 attachedModelMatrix)
        {
            lock (g)
            {
                GL.Uniform4(mUniform_Glow, g.Glow);
                GL.Uniform4(mUniform_Outline, g.ColorOutline);
                GL.Uniform3(mUniform_TintColor, g.Color);

                GL.Uniform1(mUniform_LightAffection, g.IsAffectedByLight ? 1 : 0);

                // Camera
                if (!CurrentWorld.IsFirstPersonMode)
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetCameraPosition().X, g.CurrentWorld.GetCameraPosition().Y, g.CurrentWorld.GetCameraPosition().Z);
                    GL.Uniform3(mUniform_uCameraDirection, g.CurrentWorld.GetCameraLookAtVector());
                }
                else
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetFirstPersonObject().Position.X, g.CurrentWorld.GetFirstPersonObject().Position.Y + g.CurrentWorld.GetFirstPersonObject().FPSEyeOffset, g.CurrentWorld.GetFirstPersonObject().Position.Z);
                    GL.Uniform3(mUniform_uCameraDirection, HelperCamera.GetLookAtVector());
                }

                int index = 0;
                for (int i = 0; i < attachedModel.Meshes.Keys.Count; i++)
                {
                    string meshName = attachedModel.Meshes.Keys.ElementAt(i);
                    if (g.Model.IsKWCube6)
                    {
                        index = 0;
                    }

                    // Matrices:
                    Matrix4 mmPlusAttached = Matrix4.Identity;
                    try
                    {
                        mmPlusAttached = attachedModelMatrix * g.ModelMatrixForRenderPass[index];
                        Matrix4.Mult(ref mmPlusAttached, ref viewProjection, out _modelViewProjection);
                        Matrix4.Transpose(ref mmPlusAttached, out _normalMatrix);
                        Matrix4.Invert(ref _normalMatrix, out _normalMatrix);
                    }
                    catch (Exception)
                    {
                        continue;
                    }

                    GL.UniformMatrix4(mUniform_ModelMatrix, false, ref mmPlusAttached);
                    GL.UniformMatrix4(mUniform_NormalMatrix, false, ref _normalMatrix);
                    GL.UniformMatrix4(mUniform_MVP, false, ref _modelViewProjection);

                    index++;



                    GeoMesh     mesh         = attachedModel.Meshes.Values.ElementAt(i);
                    GeoMaterial meshMaterial = g._materials[i];
                    if (meshMaterial.Opacity <= 0)
                    {
                        continue;
                    }

                    if (meshMaterial.Opacity < 1 || g.Opacity < 1)
                    {
                        GL.Enable(EnableCap.Blend);
                    }
                    else
                    {
                        GL.Disable(EnableCap.Blend);
                    }

                    if (g.ColorEmissive.W > 0)
                    {
                        GL.Uniform4(mUniform_EmissiveColor, g.ColorEmissive);
                    }
                    else
                    {
                        GL.Uniform4(mUniform_EmissiveColor, meshMaterial.ColorEmissive.X, meshMaterial.ColorEmissive.Y, meshMaterial.ColorEmissive.Z, meshMaterial.ColorEmissive.W);
                    }
                    GL.Uniform1(mUniform_Opacity, meshMaterial.Opacity * g.Opacity);
                    GL.Uniform1(mUniform_UseAnimations, 0);

                    GL.Uniform1(mUniform_Roughness, meshMaterial.Roughness);
                    GL.Uniform1(mUniform_Metalness, meshMaterial.Metalness);
                    GL.Uniform2(mUniform_TextureTransform, meshMaterial.TextureAlbedo.UVTransform.X == 0 ? 1 : meshMaterial.TextureAlbedo.UVTransform.X, meshMaterial.TextureAlbedo.UVTransform.Y == 0 ? 1 : meshMaterial.TextureAlbedo.UVTransform.Y);

                    // albedo map:
                    int texId = meshMaterial.TextureAlbedo.OpenGLID;
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    if (texId > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_Texture, textureIndex);
                        GL.Uniform1(mUniform_TextureUse, 1);
                        GL.Uniform3(mUniform_BaseColor, 1f, 1f, 1f);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_Texture, textureIndex);
                        GL.Uniform1(mUniform_TextureUse, 0);
                        GL.Uniform3(mUniform_BaseColor, meshMaterial.ColorAlbedo.X, meshMaterial.ColorAlbedo.Y, meshMaterial.ColorAlbedo.Z);
                    }

                    // normal map:
                    texId = meshMaterial.TextureNormal.OpenGLID;
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 1);
                    if (texId > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_TextureNormalMap, textureIndex + 1);
                        GL.Uniform1(mUniform_TextureUseNormalMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureNormalMap, textureIndex + 1);
                        GL.Uniform1(mUniform_TextureUseNormalMap, 0);
                    }

                    // roughness map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 2);
                    if (meshMaterial.TextureRoughness.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureRoughness.OpenGLID);
                        GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                        GL.Uniform1(mUniform_TextureUseRoughnessMap, 1);
                        GL.Uniform1(mUniform_TextureRoughnessIsSpecular, meshMaterial.TextureRoughnessIsSpecular ? 1 : 0);
                    }
                    else
                    {
                        if (meshMaterial.TextureRoughnessInMetalness && meshMaterial.TextureMetalness.OpenGLID > 0)
                        {
                            GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                            GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                            GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                            GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 1);
                        }
                        else
                        {
                            GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                            GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                            GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                            GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 0);
                        }
                    }

                    // metalness map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 3);
                    if (meshMaterial.TextureMetalness.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureMetalness.OpenGLID);
                        GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex + 3);
                        GL.Uniform1(mUniform_TextureUseMetalnessMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                        GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex + 3);
                        GL.Uniform1(mUniform_TextureUseMetalnessMap, 0);
                    }

                    // emissive map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 4);
                    if (meshMaterial.TextureEmissive.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureEmissive.OpenGLID);
                        GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex + 4);
                        GL.Uniform1(mUniform_TextureUseEmissiveMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                        GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex + 4);
                        GL.Uniform1(mUniform_TextureUseEmissiveMap, 0);
                    }

                    // light map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 5);
                    if (meshMaterial.TextureLight.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureLight.OpenGLID);
                        GL.Uniform1(mUniform_TextureLightMap, textureIndex + 5);
                        GL.Uniform1(mUniform_TextureUseLightMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureLightMap, textureIndex + 5);
                        GL.Uniform1(mUniform_TextureUseLightMap, 0);
                    }

                    GL.BindVertexArray(mesh.VAO);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, mesh.VBOIndex);
                    GL.DrawElements(mesh.Primitive, mesh.IndexCount, DrawElementsType.UnsignedInt, 0);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, 0);
                    GL.BindVertexArray(0);
                    GL.BindTexture(TextureTarget.Texture2D, 0);
                    HelperGeneral.CheckGLErrors();
                }
            }
        }
Esempio n. 5
0
        internal void Draw(GameObject g, ref Matrix4 viewProjection, int textureIndex, FPVModelObject fpModelObject = null)
        {
            lock (g)
            {
                GL.Uniform4(mUniform_Glow, g.Glow);
                GL.Uniform4(mUniform_Outline, g.ColorOutline);
                GL.Uniform3(mUniform_TintColor, g.Color);

                GL.Uniform1(mUniform_LightAffection, g.IsAffectedByLight ? 1 : 0);

                // Camera
                if (!CurrentWorld.IsFirstPersonMode)
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetCameraPosition().X, g.CurrentWorld.GetCameraPosition().Y, g.CurrentWorld.GetCameraPosition().Z);
                    GL.Uniform3(mUniform_uCameraDirection, g.CurrentWorld.GetCameraLookAtVector());
                }
                else
                {
                    if (fpModelObject != null)
                    {
                        GL.Uniform3(mUniform_uCameraPos, fpModelObject._tmpLAVStartPos);
                        GL.Uniform3(mUniform_uCameraDirection, fpModelObject._tmpLAV);
                    }
                    else
                    {
                        GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetFirstPersonObject().Position.X, g.CurrentWorld.GetFirstPersonObject().Position.Y + g.CurrentWorld.GetFirstPersonObject().FPSEyeOffset, g.CurrentWorld.GetFirstPersonObject().Position.Z);
                        GL.Uniform3(mUniform_uCameraDirection, HelperCamera.GetLookAtVector());
                    }
                }

                int index = 0;
                for (int i = 0; i < g.Model.Meshes.Keys.Count; i++)
                {
                    string meshName = g.Model.Meshes.Keys.ElementAt(i);
                    if (g.Model.IsKWCube6)
                    {
                        index = 0;
                    }

                    // Matrices:
                    try
                    {
                        Matrix4.Mult(ref g.ModelMatrixForRenderPass[index], ref viewProjection, out _modelViewProjection);
                        Matrix4.Transpose(ref g.ModelMatrixForRenderPass[index], out _normalMatrix);
                        Matrix4.Invert(ref _normalMatrix, out _normalMatrix);
                    }
                    catch (Exception)
                    {
                        continue;
                    }

                    GL.UniformMatrix4(mUniform_ModelMatrix, false, ref g.ModelMatrixForRenderPass[index]);
                    GL.UniformMatrix4(mUniform_NormalMatrix, false, ref _normalMatrix);
                    GL.UniformMatrix4(mUniform_MVP, false, ref _modelViewProjection);

                    index++;

                    GL.Disable(EnableCap.Blend);
                    GeoMesh mesh = g.Model.Meshes.Values.ElementAt(i);

                    GeoMaterial meshMaterial = g._materials[i];

                    if (meshMaterial.Opacity <= 0)
                    {
                        continue;
                    }

                    if (meshMaterial.Opacity < 1 || g.Opacity < 1 || g.Model.Name == "kwquad.obj")
                    {
                        GL.Enable(EnableCap.Blend);
                    }

                    if (g.ColorEmissive.W > 0)
                    {
                        GL.Uniform4(mUniform_EmissiveColor, g.ColorEmissive);
                    }
                    else
                    {
                        GL.Uniform4(mUniform_EmissiveColor, meshMaterial.ColorEmissive.X, meshMaterial.ColorEmissive.Y, meshMaterial.ColorEmissive.Z, meshMaterial.ColorEmissive.W);
                    }
                    GL.Uniform1(mUniform_Opacity, meshMaterial.Opacity * g.Opacity);

                    if (mesh.BoneNames.Count > 0 && g.AnimationID >= 0 && g.Model.Animations != null && g.Model.Animations.Count > 0)
                    {
                        GL.Uniform1(mUniform_UseAnimations, 1);
                        for (int j = 0; j < g.BoneTranslationMatrices[meshName].Length; j++)
                        {
                            Matrix4 tmp = g.BoneTranslationMatrices[meshName][j];
                            GL.UniformMatrix4(mUniform_BoneTransforms + j, false, ref tmp);
                        }
                    }
                    else
                    {
                        GL.Uniform1(mUniform_UseAnimations, 0);
                    }

                    GL.Uniform1(mUniform_Roughness, meshMaterial.Roughness);
                    GL.Uniform1(mUniform_Metalness, meshMaterial.Metalness);
                    Vector4 texTransform = new Vector4(meshMaterial.TextureAlbedo.UVTransform.X == 0 ? 1 : meshMaterial.TextureAlbedo.UVTransform.X, meshMaterial.TextureAlbedo.UVTransform.Y == 0 ? 1 : meshMaterial.TextureAlbedo.UVTransform.Y, g.mTextureOffset.X, g.mTextureOffset.Y);
                    GL.Uniform4(mUniform_TextureTransform, texTransform);

                    // albedo map:
                    int texId = meshMaterial.TextureAlbedo.OpenGLID;
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    if (texId > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_Texture, textureIndex);
                        GL.Uniform1(mUniform_TextureUse, 1);
                        GL.Uniform3(mUniform_BaseColor, 1f, 1f, 1f);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_Texture, textureIndex);
                        GL.Uniform1(mUniform_TextureUse, 0);
                        GL.Uniform3(mUniform_BaseColor, meshMaterial.ColorAlbedo.X, meshMaterial.ColorAlbedo.Y, meshMaterial.ColorAlbedo.Z);
                    }

                    // normal map:
                    texId = meshMaterial.TextureNormal.OpenGLID;
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 1);
                    if (texId > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, texId);
                        GL.Uniform1(mUniform_TextureNormalMap, textureIndex + 1);
                        GL.Uniform1(mUniform_TextureUseNormalMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureNormalMap, textureIndex + 1);
                        GL.Uniform1(mUniform_TextureUseNormalMap, 0);
                    }

                    // roughness map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 2);
                    if (meshMaterial.TextureRoughness.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureRoughness.OpenGLID);
                        GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                        GL.Uniform1(mUniform_TextureUseRoughnessMap, 1);
                        GL.Uniform1(mUniform_TextureRoughnessIsSpecular, meshMaterial.TextureRoughnessIsSpecular ? 1 : 0);
                    }
                    else
                    {
                        if (meshMaterial.TextureRoughnessInMetalness && meshMaterial.TextureMetalness.OpenGLID > 0)
                        {
                            GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                            GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                            GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                            GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 1);
                        }
                        else
                        {
                            GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                            GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex + 2);
                            GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                            GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 0);
                        }
                    }

                    // metalness map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 3);
                    if (meshMaterial.TextureMetalness.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureMetalness.OpenGLID);
                        GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex + 3);
                        GL.Uniform1(mUniform_TextureUseMetalnessMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                        GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex + 3);
                        GL.Uniform1(mUniform_TextureUseMetalnessMap, 0);
                    }

                    // emissive map:
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 4);
                    if (meshMaterial.TextureEmissive.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureEmissive.OpenGLID);
                        GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex + 4);
                        GL.Uniform1(mUniform_TextureUseEmissiveMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                        GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex + 4);
                        GL.Uniform1(mUniform_TextureUseEmissiveMap, 0);
                    }



                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex + 5);
                    if (meshMaterial.TextureLight.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureLight.OpenGLID);
                        GL.Uniform1(mUniform_TextureLightMap, textureIndex + 5);
                        GL.Uniform1(mUniform_TextureUseLightMap, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureLightMap, textureIndex + 5);
                        GL.Uniform1(mUniform_TextureUseLightMap, 0);
                    }

                    GL.Uniform1(mUniform_TextureFullAlpha, g.Model.Name == "kwquad.obj" ? 1 : 0);

                    GL.BindVertexArray(mesh.VAO);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, mesh.VBOIndex);
                    GL.DrawElements(mesh.Primitive, mesh.IndexCount, DrawElementsType.UnsignedInt, 0);
                    GL.BindBuffer(BufferTarget.ElementArrayBuffer, 0);
                    GL.BindVertexArray(0);
                    GL.BindTexture(TextureTarget.Texture2D, 0);
                }
            }
        }
Esempio n. 6
0
        internal static void PrepareLightsForRenderPass(List <LightObject> lights, ref float[] colors, ref float[] targets, ref float[] positions, ref float[] meta, ref float[] nearFar, ref int count)
        {
            int countTemp = 0;
            IEnumerator <LightObject> enumerator = lights.GetEnumerator();

            enumerator.Reset();

            Vector3 viewDirection;
            Vector3 camPosition;

            if (KWEngine.CurrentWorld.IsFirstPersonMode)
            {
                viewDirection = HelperCamera.GetLookAtVector();
                camPosition   = KWEngine.CurrentWorld.GetFirstPersonObject().Position;
            }
            else
            {
                viewDirection = KWEngine.CurrentWorld.GetCameraLookAtVector();
                camPosition   = KWEngine.CurrentWorld.GetCameraPosition();
            }

            for (int i = 0, twocounter = 0, threecounter = 0, arraycounter = 0; i < lights.Count; i++)
            {
                bool isInFrustum = true;
                enumerator.MoveNext();
                LightObject l = enumerator.Current;

                Vector3 cameraToLight          = Vector3.NormalizeFast(l.Position - camPosition);
                float   dotProductViewAndLight = Vector3.Dot(viewDirection, cameraToLight);

                if (dotProductViewAndLight < -0.125f && (camPosition - l.Position).LengthFast > (l.Type != LightType.Sun ? l._zFar * 5 : (KWEngine.CurrentWorld.ZFar * 5)))
                {
                    isInFrustum = false;
                }

                if (isInFrustum)
                {
                    colors[arraycounter + 0] = l.Color.X;
                    colors[arraycounter + 1] = l.Color.Y;
                    colors[arraycounter + 2] = l.Color.Z;
                    colors[arraycounter + 3] = l.Color.W; // Intensity of color

                    targets[arraycounter + 0] = l.Target.X;
                    targets[arraycounter + 1] = l.Target.Y;
                    targets[arraycounter + 2] = l.Target.Z;
                    if (l.Type == LightType.Point)
                    {
                        targets[arraycounter + 3] = 0; // Point
                    }
                    else if (l.Type == LightType.Directional)
                    {
                        targets[arraycounter + 3] = 1; // Directional
                    }
                    else
                    {
                        targets[arraycounter + 3] = -1; // Sun
                    }

                    positions[arraycounter + 0] = l.Position.X;
                    positions[arraycounter + 1] = l.Position.Y;
                    positions[arraycounter + 2] = l.Position.Z;
                    positions[arraycounter + 3] = l._zFar;

                    meta[threecounter]     = l._shadowMapBiasCoefficient;
                    meta[threecounter + 1] = l.IsShadowCaster ? 1 : 0;
                    meta[threecounter + 2] = l._shadowHardness;

                    nearFar[twocounter]     = l._zNear;
                    nearFar[twocounter + 1] = l._zFar;

                    countTemp++;
                    arraycounter += 4;
                    threecounter += 3;
                    twocounter   += 2;
                }
            }

            count = countTemp;
        }
Esempio n. 7
0
        internal void Draw(GameObject g, ref Matrix4 viewProjection, HelperFrustum frustum, int textureIndex)
        {
            if (g == null || !g.HasModel || g.CurrentWorld == null || g.Opacity <= 0)
            {
                return;
            }

            if (KWEngine.Projection == ProjectionType.Perspective)
            {
                g.IsInsideScreenSpace = frustum.SphereVsFrustum(g.GetCenterPointForAllHitboxes(), g.GetMaxDiameter() / 2);
            }
            else
            {
                Vector3 lookAt       = CurrentWorld.GetCameraLookAtVectorEitherWay();
                Vector3 camPos       = CurrentWorld.GetCameraPositionEitherWay();
                Vector3 objectCenter = g.GetCenterPointForAllHitboxes();
                float   dot          = Vector3.Dot(objectCenter - camPos, lookAt);
                g.IsInsideScreenSpace = dot > 0;
            }
            if (!g.IsInsideScreenSpace)
            {
                return;
            }

            GL.Disable(EnableCap.Blend);
            lock (g)
            {
                if (g.Opacity < 1)
                {
                    GL.Enable(EnableCap.Blend);
                }

                GL.Uniform4(mUniform_Glow, g.Glow);
                GL.Uniform4(mUniform_Outline, g.ColorOutline);
                GL.Uniform3(mUniform_TintColor, g.Color);

                GL.Uniform1(mUniform_LightAffection, g.IsAffectedByLight ? 1 : 0);

                // Camera
                if (!CurrentWorld.IsFirstPersonMode)
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetCameraPosition().X, g.CurrentWorld.GetCameraPosition().Y, g.CurrentWorld.GetCameraPosition().Z);
                    GL.Uniform3(mUniform_uCameraDirection, g.CurrentWorld.GetCameraLookAtVector());
                }
                else
                {
                    GL.Uniform3(mUniform_uCameraPos, g.CurrentWorld.GetFirstPersonObject().Position.X, g.CurrentWorld.GetFirstPersonObject().Position.Y + g.CurrentWorld.GetFirstPersonObject().FPSEyeOffset, g.CurrentWorld.GetFirstPersonObject().Position.Z);
                    GL.Uniform3(mUniform_uCameraDirection, HelperCamera.GetLookAtVector());
                }

                Matrix4.Mult(ref g.ModelMatrixForRenderPass[0], ref viewProjection, out _modelViewProjection);
                Matrix4.Transpose(ref g.ModelMatrixForRenderPass[0], out _normalMatrix);
                Matrix4.Invert(ref _normalMatrix, out _normalMatrix);

                GL.UniformMatrix4(mUniform_ModelMatrix, false, ref g.ModelMatrixForRenderPass[0]);
                GL.UniformMatrix4(mUniform_NormalMatrix, false, ref _normalMatrix);
                GL.UniformMatrix4(mUniform_MVP, false, ref _modelViewProjection);

                if (g.ColorEmissive.W > 0)
                {
                    GL.Uniform4(mUniform_EmissiveColor, g.ColorEmissive);
                }
                else
                {
                    GL.Uniform4(mUniform_EmissiveColor, Vector4.Zero);
                }

                string      meshName     = g.Model.Meshes.Keys.ElementAt(0);
                GeoMesh     mesh         = g.Model.Meshes[meshName];
                GeoMaterial meshMaterial = mesh.Material;

                GL.Uniform1(mUniform_Roughness, meshMaterial.Roughness);
                GL.Uniform1(mUniform_Metalness, meshMaterial.Metalness);


                GL.Uniform4(mUniform_TextureTransform, mesh.Terrain.mTexX, mesh.Terrain.mTexY, g.mTextureOffset.X, g.mTextureOffset.Y);

                // albedo map:
                int texId = -1;
                texId = mesh.Material.TextureAlbedo.OpenGLID;
                GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                GL.BindTexture(TextureTarget.Texture2D, texId > 0 ? texId : KWEngine.TextureWhite);
                GL.Uniform1(mUniform_Texture, textureIndex);
                GL.Uniform1(mUniform_TextureUse, texId > 0 ? 1 : 0);
                GL.Uniform3(mUniform_BaseColor, texId > 0 ? new Vector3(1f, 1f, 1f) : new Vector3(meshMaterial.ColorAlbedo.X, meshMaterial.ColorAlbedo.Y, meshMaterial.ColorAlbedo.Z));
                textureIndex++;

                // normal map:
                texId = meshMaterial.TextureNormal.OpenGLID;
                GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                GL.BindTexture(TextureTarget.Texture2D, texId > 0 ? texId : KWEngine.TextureWhite);
                GL.Uniform1(mUniform_TextureNormalMap, textureIndex);
                GL.Uniform1(mUniform_TextureUseNormalMap, texId > 0 ? 1 : 0);
                textureIndex++;

                // roughness map:
                GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                if (meshMaterial.TextureRoughness.OpenGLID > 0)
                {
                    GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureRoughness.OpenGLID);
                    GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex);
                    GL.Uniform1(mUniform_TextureUseRoughnessMap, 1);
                    GL.Uniform1(mUniform_TextureRoughnessIsSpecular, meshMaterial.TextureRoughnessIsSpecular ? 1 : 0);
                }
                else
                {
                    if (meshMaterial.TextureRoughnessInMetalness && meshMaterial.TextureMetalness.OpenGLID > 0)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex);
                        GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                        GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 1);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureWhite);
                        GL.Uniform1(mUniform_TextureRoughnessMap, textureIndex);
                        GL.Uniform1(mUniform_TextureUseRoughnessMap, 0);
                        GL.Uniform1(mUniform_TextureRoughnessIsSpecular, 0);
                    }
                }
                textureIndex++;

                // metalness map:
                GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                if (meshMaterial.TextureMetalness.OpenGLID > 0)
                {
                    GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureMetalness.OpenGLID);
                    GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex);
                    GL.Uniform1(mUniform_TextureUseMetalnessMap, 1);
                }
                else
                {
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureMetalnessMap, textureIndex);
                    GL.Uniform1(mUniform_TextureUseMetalnessMap, 0);
                }
                textureIndex++;

                // emissive map:
                GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                if (meshMaterial.TextureEmissive.OpenGLID > 0)
                {
                    GL.BindTexture(TextureTarget.Texture2D, meshMaterial.TextureEmissive.OpenGLID);
                    GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex);
                    GL.Uniform1(mUniform_TextureUseEmissiveMap, 1);
                }
                else
                {
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureEmissiveMap, textureIndex);
                    GL.Uniform1(mUniform_TextureUseEmissiveMap, 0);
                }
                textureIndex++;

                // Blendmapping:
                if (mesh.Terrain._texBlend > 0 && mesh.Terrain._texBlend != KWEngine.TextureBlack)
                {
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texBlend);
                    GL.Uniform1(mUniform_TextureBlend, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texR);
                    GL.Uniform1(mUniform_TextureRed, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    if (mesh.Terrain._texG > 0 && mesh.Terrain._texG != KWEngine.TextureAlpha)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texG);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureAlpha);
                    }
                    GL.Uniform1(mUniform_TextureGreen, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    if (mesh.Terrain._texB > 0 && mesh.Terrain._texB != KWEngine.TextureAlpha)
                    {
                        GL.BindTexture(TextureTarget.Texture2D, mesh.Terrain._texB);
                    }
                    else
                    {
                        GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureAlpha);
                    }
                    GL.Uniform1(mUniform_TextureBlue, textureIndex);
                    textureIndex++;


                    GL.Uniform1(mUniform_UseBlend, 1);
                }
                else
                {
                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureBlend, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureRed, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureGreen, textureIndex);
                    textureIndex++;

                    GL.ActiveTexture(TextureUnit.Texture0 + textureIndex);
                    GL.BindTexture(TextureTarget.Texture2D, KWEngine.TextureBlack);
                    GL.Uniform1(mUniform_TextureBlue, textureIndex);
                    textureIndex++;

                    GL.Uniform1(mUniform_UseBlend, 0);
                }

                GL.BindVertexArray(mesh.VAO);
                GL.BindBuffer(BufferTarget.ElementArrayBuffer, mesh.VBOIndex);
                GL.DrawElements(mesh.Primitive, mesh.IndexCount, DrawElementsType.UnsignedInt, 0);
                GL.BindBuffer(BufferTarget.ElementArrayBuffer, 0);
                GL.BindVertexArray(0);
            }

            if (g.Opacity < 1)
            {
                GL.Disable(EnableCap.Blend);
            }
        }