diff --git a/src/graphics/opengl/gl21device.cpp b/src/graphics/opengl/gl21device.cpp index 7c1c9cbb..0cebf824 100644 --- a/src/graphics/opengl/gl21device.cpp +++ b/src/graphics/opengl/gl21device.cpp @@ -166,65 +166,55 @@ bool CGL21Device::Create() { GetLogger()->Info("Creating CDevice - OpenGL 2.1\n"); - static bool glewInited = false; - - if (!glewInited) + if (!InitializeGLEW()) { - glewInited = true; + m_errorMessage = "An error occured while initializing GLEW."; + return false; + } - glewExperimental = GL_TRUE; + // Extract OpenGL version + int glMajor, glMinor; + int glVersion = GetOpenGLVersion(glMajor, glMinor); - if (glewInit() != GLEW_OK) - { - GetLogger()->Error("GLEW initialization failed\n"); - m_errorMessage = "An error occured while initializing GLEW."; - return false; - } + if (glVersion < 20) + { + GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", glMajor, glMinor); + GetLogger()->Error("OpenGL 2.0 or newer is required to use this engine.\n"); + m_errorMessage = "It seems your graphics card does not support OpenGL 2.0.\n"; + m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n"; + m_errorMessage += "(OpenGL 2.0 is roughly equivalent to Direct3D 9)\n\n"; + m_errorMessage += GetHardwareInfo(); + return false; + } - // Extract OpenGL version - const char *version = reinterpret_cast(glGetString(GL_VERSION)); - sscanf(version, "%d.%d", &m_glMajor, &m_glMinor); + GetLogger()->Info("OpenGL %d.%d\n", glMajor, glMinor); - if (m_glMajor < 2) - { - GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", m_glMajor, m_glMinor); - GetLogger()->Error("OpenGL 2.0 or newer is required to use this engine.\n"); - m_errorMessage = "It seems your graphics card does not support OpenGL 2.0.\n"; - m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n"; - m_errorMessage += "(OpenGL 2.0 is roughly equivalent to Direct3D 9)\n\n"; - m_errorMessage += GetHardwareInfo(false); - return false; - } + // Detect support of anisotropic filtering + m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); + if(m_anisotropyAvailable) + { + // Obtain maximum anisotropy level available + float level; + glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); + m_maxAnisotropy = static_cast(level); - GetLogger()->Info("OpenGL %d.%d\n", m_glMajor, m_glMinor); + GetLogger()->Info("Anisotropic filtering available\n"); + GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); + } + else + { + GetLogger()->Info("Anisotropic filtering not available\n"); + } - // Detect support of anisotropic filtering - m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); - if(m_anisotropyAvailable) - { - // Obtain maximum anisotropy level available - float level; - glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); - m_maxAnisotropy = static_cast(level); - - GetLogger()->Info("Anisotropic filtering available\n"); - GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); - } - else - { - GetLogger()->Info("Anisotropic filtering not available\n"); - } - - // Read maximum sample count for MSAA - if(glewIsSupported("GL_ARB_multisample")) - { - glGetIntegerv(GL_MAX_SAMPLES_EXT, &m_maxSamples); - GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); - } - else - { - GetLogger()->Info("Multisampling not supported\n"); - } + // Read maximum sample count for MSAA + if(glewIsSupported("GL_EXT_framebuffer_multisample")) + { + glGetIntegerv(GL_MAX_SAMPLES_EXT, &m_maxSamples); + GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); + } + else + { + GetLogger()->Info("Multisampling not supported\n"); } // This is mostly done in all modern hardware by default @@ -237,8 +227,8 @@ bool CGL21Device::Create() glViewport(0, 0, m_config.size.x, m_config.size.y); - int numLights = 0; - glGetIntegerv(GL_MAX_LIGHTS, &numLights); + // this is set in shader + int numLights = 8; m_lights = std::vector(numLights, Light()); m_lightsEnabled = std::vector (numLights, false); @@ -247,20 +237,24 @@ bool CGL21Device::Create() glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, &maxTextures); GetLogger()->Info("Maximum texture image units: %d\n", maxTextures); + m_framebufferSupport = DetectFramebufferSupport(); + if (m_framebufferSupport != FBS_NONE) + GetLogger()->Info("Framebuffer supported\n"); + m_currentTextures = std::vector (maxTextures, Texture()); m_texturesEnabled = std::vector (maxTextures, false); m_textureStageParams = std::vector(maxTextures, TextureStageParams()); int value; - if (CConfigFile::GetInstance().GetIntProperty("Setup", "PerPixelLighting", value)) + if (GetConfigFile().GetIntProperty("Setup", "PerPixelLighting", value)) { m_perPixelLighting = value > 0; } if (m_perPixelLighting) - CLogger::GetInstance().Info("Using per-pixel lighting\n"); + GetLogger()->Info("Using per-pixel lighting\n"); else - CLogger::GetInstance().Info("Using per-vertex lighting\n"); + GetLogger()->Info("Using per-vertex lighting\n"); // Create normal shader program @@ -301,7 +295,6 @@ bool CGL21Device::Create() glDeleteShader(shaders[0]); glDeleteShader(shaders[1]); - // Obtain uniform locations uni_ProjectionMatrix = glGetUniformLocation(m_program, "uni_ProjectionMatrix"); uni_ViewMatrix = glGetUniformLocation(m_program, "uni_ViewMatrix"); @@ -399,10 +392,6 @@ bool CGL21Device::Create() m_framebuffers["default"] = MakeUnique(framebufferParams); - m_framebufferSupport = DetectFramebufferSupport(); - if (m_framebufferSupport != FBS_NONE) - GetLogger()->Debug("Framebuffer supported\n"); - GetLogger()->Info("CDevice created successfully\n"); return true; diff --git a/src/graphics/opengl/gl21device.h b/src/graphics/opengl/gl21device.h index f2b3bc42..a0b5f499 100644 --- a/src/graphics/opengl/gl21device.h +++ b/src/graphics/opengl/gl21device.h @@ -236,8 +236,6 @@ private: }; //! Detected capabilities - //! OpenGL version - int m_glMajor = 1, m_glMinor = 1; //! Whether anisotropic filtering is available bool m_anisotropyAvailable = false; //! Maximum anisotropy level diff --git a/src/graphics/opengl/gl33device.cpp b/src/graphics/opengl/gl33device.cpp index 61023d80..5bcafd27 100644 --- a/src/graphics/opengl/gl33device.cpp +++ b/src/graphics/opengl/gl33device.cpp @@ -168,79 +168,63 @@ bool CGL33Device::Create() static bool glewInited = false; - if (!glewInited) + if (!InitializeGLEW()) { - glewInited = true; - - glewExperimental = GL_TRUE; - - if (glewInit() != GLEW_OK) - { - GetLogger()->Error("GLEW initialization failed\n"); - m_errorMessage = "An error occured while initializing GLEW."; - return false; - } - - // Extract OpenGL version - const char *version = reinterpret_cast(glGetString(GL_VERSION)); - sscanf(version, "%d.%d", &m_glMajor, &m_glMinor); - - int glVersion = 10 * m_glMajor + m_glMinor; - if (glVersion < 32) - { - GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", m_glMajor, m_glMinor); - GetLogger()->Error("OpenGL 3.2 or newer is required to use this engine.\n"); - m_errorMessage = "It seems your graphics card does not support OpenGL 3.2.\n"; - m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n"; - m_errorMessage += "(OpenGL 3.2 is roughly equivalent to Direct3D 10)\n\n"; - m_errorMessage += GetHardwareInfo(false); - return false; - } - else if (glVersion < 33) - { - GetLogger()->Warn("Partially supported OpenGL version: %d.%d\n", m_glMajor, m_glMinor); - GetLogger()->Warn("You may experience problems while running the game on this engine.\n"); - GetLogger()->Warn("OpenGL 3.3 or newer is recommended.\n"); - } - else - { - GetLogger()->Info("OpenGL %d.%d\n", m_glMajor, m_glMinor); - } - - // Detect support of anisotropic filtering - m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); - if(m_anisotropyAvailable) - { - // Obtain maximum anisotropy level available - float level; - glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); - m_maxAnisotropy = static_cast(level); - - GetLogger()->Info("Anisotropic filtering available\n"); - GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); - } - else - { - GetLogger()->Info("Anisotropic filtering not available\n"); - } - - // Read maximum sample count for MSAA - if(glewIsSupported("GL_ARB_multisample")) - { - glGetIntegerv(GL_MAX_SAMPLES_EXT, &m_maxSamples); - GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); - } - else - { - GetLogger()->Info("Multisampling not supported\n"); - } + m_errorMessage = "An error occured while initializing GLEW."; + return false; } + // Extract OpenGL version + int glMajor, glMinor; + int glVersion = GetOpenGLVersion(glMajor, glMinor); + + if (glVersion < 32) + { + GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", glMajor, glMinor); + GetLogger()->Error("OpenGL 3.2 or newer is required to use this engine.\n"); + m_errorMessage = "It seems your graphics card does not support OpenGL 3.2.\n"; + m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n"; + m_errorMessage += "(OpenGL 3.2 is roughly equivalent to Direct3D 10)\n\n"; + m_errorMessage += GetHardwareInfo(); + return false; + } + else if (glVersion < 33) + { + GetLogger()->Warn("Partially supported OpenGL version: %d.%d\n", glMajor, glMinor); + GetLogger()->Warn("You may experience problems while running the game on this engine.\n"); + GetLogger()->Warn("OpenGL 3.3 or newer is recommended.\n"); + } + else + { + GetLogger()->Info("OpenGL %d.%d\n", glMajor, glMinor); + } + + // Detect support of anisotropic filtering + m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); + if(m_anisotropyAvailable) + { + // Obtain maximum anisotropy level available + float level; + glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); + m_maxAnisotropy = static_cast(level); + + GetLogger()->Info("Anisotropic filtering available\n"); + GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); + } + else + { + GetLogger()->Info("Anisotropic filtering not available\n"); + } + + glGetIntegerv(GL_MAX_FRAMEBUFFER_SAMPLES, &m_maxSamples); + GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); + // Set just to be sure glClearColor(0.0f, 0.0f, 0.0f, 0.0f); glViewport(0, 0, m_config.size.x, m_config.size.y); + // this is set in shader int numLights = 8; m_lights = std::vector(numLights, Light()); diff --git a/src/graphics/opengl/gl33device.h b/src/graphics/opengl/gl33device.h index b701276f..44db526d 100644 --- a/src/graphics/opengl/gl33device.h +++ b/src/graphics/opengl/gl33device.h @@ -254,8 +254,6 @@ private: }; //! Detected capabilities - //! OpenGL version - int m_glMajor = 1, m_glMinor = 1; //! Whether anisotropic filtering is available bool m_anisotropyAvailable = false; //! Maximum anisotropy level diff --git a/src/graphics/opengl/gldevice.cpp b/src/graphics/opengl/gldevice.cpp index cf0e71ed..1df95c67 100644 --- a/src/graphics/opengl/gldevice.cpp +++ b/src/graphics/opengl/gldevice.cpp @@ -162,118 +162,107 @@ bool CGLDevice::Create() { GetLogger()->Info("Creating CDevice - OpenGL 1.4\n"); - static bool glewInited = false; - - if (!glewInited) + if (!InitializeGLEW()) { - glewInited = true; + m_errorMessage = "An error occured while initializing GLEW."; + return false; + } - glewExperimental = GL_TRUE; + // Extract OpenGL version + int glMajor, glMinor; + int glVersion = GetOpenGLVersion(glMajor, glMinor); - if (glewInit() != GLEW_OK) - { - GetLogger()->Error("GLEW initialization failed\n"); - m_errorMessage = "An error occured while initializing GLEW."; - return false; - } + if (glVersion < 13) + { + GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", glMajor, glMinor); + GetLogger()->Error("OpenGL 1.3 or newer is required to use this engine.\n"); + m_errorMessage = "It seems your graphics card does not support OpenGL 1.3.\n"; + m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n\n"; + m_errorMessage += GetHardwareInfo(); + return false; + } - // Extract OpenGL version - const char *version = reinterpret_cast(glGetString(GL_VERSION)); - sscanf(version, "%d.%d", &m_glMajor, &m_glMinor); + GetLogger()->Info("OpenGL %d.%d\n", glMajor, glMinor); - int glVersion = 10 * m_glMajor + m_glMinor; - if (glVersion < 13) - { - GetLogger()->Error("Unsupported OpenGL version: %d.%d\n", m_glMajor, m_glMinor); - GetLogger()->Error("OpenGL 1.3 or newer is required to use this engine.\n"); - m_errorMessage = "It seems your graphics card does not support OpenGL 1.3.\n"; - m_errorMessage += "Please make sure you have appropriate hardware and newest drivers installed.\n\n"; - m_errorMessage += GetHardwareInfo(false); - return false; - } + // Detect multitexture support + m_multitextureAvailable = glewIsSupported("GL_ARB_multitexture GL_ARB_texture_env_combine"); + if (!m_multitextureAvailable) + GetLogger()->Warn("GLEW reports multitexturing not supported - graphics quality will be degraded!\n"); - GetLogger()->Info("OpenGL %d.%d\n", m_glMajor, m_glMinor); + // Detect Shadow mapping support + if (glVersion >= 14) // Core depth texture+shadow, OpenGL 1.4+ + { + m_shadowMappingSupport = SMS_CORE; + GetLogger()->Info("Shadow mapping available (core)\n"); + } + else if (glewIsSupported("GL_ARB_depth_texture GL_ARB_shadow")) // ARB depth texture + shadow + { + m_shadowMappingSupport = SMS_ARB; + GetLogger()->Info("Shadow mapping available (ARB)\n"); + } + else // No Shadow mapping + { + m_shadowMappingSupport = SMS_NONE; + GetLogger()->Info("Shadow mapping not available\n"); + } - // Detect multitexture support - m_multitextureAvailable = glewIsSupported("GL_ARB_multitexture GL_ARB_texture_env_combine"); - if (!m_multitextureAvailable) - GetLogger()->Warn("GLEW reports multitexturing not supported - graphics quality will be degraded!\n"); + m_shadowAmbientSupported = glewIsSupported("GL_ARB_shadow_ambient"); + if (m_shadowAmbientSupported) + GetLogger()->Info("Shadow ambient supported\n"); - // Detect Shadow mapping support - if (m_glMajor > 1 || m_glMinor >= 4) // Core depth texture+shadow, OpenGL 1.4+ - { - m_shadowMappingSupport = SMS_CORE; - GetLogger()->Info("Shadow mapping available (core)\n"); - } - else if (glewIsSupported("GL_ARB_depth_texture GL_ARB_shadow")) // ARB depth texture + shadow - { - m_shadowMappingSupport = SMS_ARB; - GetLogger()->Info("Shadow mapping available (ARB)\n"); - } - else // No Shadow mapping - { - m_shadowMappingSupport = SMS_NONE; - GetLogger()->Info("Shadow mapping not available\n"); - } + // Detect support of anisotropic filtering + m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); + if(m_anisotropyAvailable) + { + // Obtain maximum anisotropy level available + float level; + glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); + m_maxAnisotropy = static_cast(level); - m_shadowAmbientSupported = glewIsSupported("GL_ARB_shadow_ambient"); - if (m_shadowAmbientSupported) - GetLogger()->Info("Shadow ambient supported\n"); + GetLogger()->Info("Anisotropic filtering available\n"); + GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); + } + else + { + GetLogger()->Info("Anisotropic filtering not available\n"); + } - // Detect support of anisotropic filtering - m_anisotropyAvailable = glewIsSupported("GL_EXT_texture_filter_anisotropic"); - if(m_anisotropyAvailable) - { - // Obtain maximum anisotropy level available - float level; - glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); - m_maxAnisotropy = static_cast(level); + // Read maximum sample count for MSAA + if(glewIsSupported("GL_EXT_framebuffer_multisample")) + { + glGetIntegerv(GL_MAX_SAMPLES_EXT, &m_maxSamples); + GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); + } + else + { + GetLogger()->Info("Multisampling not supported\n"); + } - GetLogger()->Info("Anisotropic filtering available\n"); - GetLogger()->Info("Maximum anisotropy: %d\n", m_maxAnisotropy); - } - else - { - GetLogger()->Info("Anisotropic filtering not available\n"); - } + // check for glMultiDrawArrays() + if (glVersion >= 14) + m_multiDrawArrays = true; - // Read maximum sample count for MSAA - if(glewIsSupported("GL_ARB_multisample GL_EXT_framebuffer_multisample")) - { - glGetIntegerv(GL_MAX_SAMPLES_EXT, &m_maxSamples); - GetLogger()->Info("Multisampling supported, max samples: %d\n", m_maxSamples); - } - else - { - GetLogger()->Info("Multisampling not supported\n"); - } + GetLogger()->Info("Auto-detecting VBO support\n"); - // check for glMultiDrawArrays() - if (glVersion >= 14) - m_multiDrawArrays = true; + // detecting VBO ARB extension + bool vboARB = glewIsSupported("GL_ARB_vertex_buffer_object"); - GetLogger()->Info("Auto-detecting VBO support\n"); - - // detecting VBO ARB extension - bool vboARB = glewIsSupported("GL_ARB_vertex_buffer_object"); - - // VBO is core OpenGL feature since 1.5 - // everything below 1.5 means no VBO support - if (m_glMajor > 1 || m_glMinor > 4) - { - GetLogger()->Info("Core VBO supported\n", m_glMajor, m_glMinor); - m_vertexBufferType = VBT_VBO_CORE; - } - else if(vboARB) // VBO ARB extension available - { - GetLogger()->Info("ARB VBO supported\n"); - m_vertexBufferType = VBT_VBO_ARB; - } - else // no VBO support - { - GetLogger()->Info("VBO not supported\n"); - m_vertexBufferType = VBT_DISPLAY_LIST; - } + // VBO is core OpenGL feature since 1.5 + // everything below 1.5 means no VBO support + if (glVersion >= 15) + { + GetLogger()->Info("Core VBO supported\n", glMajor, glMinor); + m_vertexBufferType = VBT_VBO_CORE; + } + else if (vboARB) // VBO ARB extension available + { + GetLogger()->Info("ARB VBO supported\n"); + m_vertexBufferType = VBT_VBO_ARB; + } + else // no VBO support + { + GetLogger()->Info("VBO not supported\n"); + m_vertexBufferType = VBT_DISPLAY_LIST; } // This is mostly done in all modern hardware by default @@ -332,6 +321,7 @@ bool CGLDevice::Create() { GetLogger()->Info("Framebuffer not supported\n"); } + GetLogger()->Info("CDevice created successfully\n"); return true; @@ -502,17 +492,15 @@ void CGLDevice::UpdateLightPosition(int index) glMatrixMode(GL_MODELVIEW); glPushMatrix(); - if (m_lights[index].type == LIGHT_POINT) + Light &light = m_lights[index]; + + if (light.type == LIGHT_POINT) { glLoadIdentity(); glScalef(1.0f, 1.0f, -1.0f); glMultMatrixf(m_viewMat.Array()); - GLfloat position[4] = { m_lights[index].position.x, - m_lights[index].position.y, - m_lights[index].position.z, - 1.0f }; - + GLfloat position[4] = { light.position.x, light.position.y, light.position.z, 1.0f }; glLightfv(GL_LIGHT0 + index, GL_POSITION, position); } else @@ -525,22 +513,14 @@ void CGLDevice::UpdateLightPosition(int index) mat.Set(3, 4, 0.0f); glMultMatrixf(mat.Array()); - if (m_lights[index].type == LIGHT_SPOT) + if (light.type == LIGHT_SPOT) { - GLfloat direction[4] = { -m_lights[index].direction.x, - -m_lights[index].direction.y, - -m_lights[index].direction.z, - 1.0f }; - + GLfloat direction[4] = { -light.direction.x, -light.direction.y, -light.direction.z, 1.0f }; glLightfv(GL_LIGHT0 + index, GL_SPOT_DIRECTION, direction); } - else if (m_lights[index].type == LIGHT_DIRECTIONAL) + else if (light.type == LIGHT_DIRECTIONAL) { - GLfloat position[4] = { -m_lights[index].direction.x, - -m_lights[index].direction.y, - -m_lights[index].direction.z, - 0.0f }; - + GLfloat position[4] = { -light.direction.x, -light.direction.y, -light.direction.z, 0.0f }; glLightfv(GL_LIGHT0 + index, GL_POSITION, position); } } @@ -553,8 +533,6 @@ void CGLDevice::UpdateLightPositions() glMatrixMode(GL_MODELVIEW); glPushMatrix(); - int lightCount = m_lights.size(); - // update spotlights and directional lights glLoadIdentity(); glScalef(1.0f, 1.0f, -1.0f); @@ -564,25 +542,25 @@ void CGLDevice::UpdateLightPositions() mat.Set(3, 4, 0.0f); glMultMatrixf(mat.Array()); - for (int index = 0; index < lightCount; index++) - { - if (m_lights[index].type == LIGHT_SPOT) - { - GLfloat direction[4] = { -m_lights[index].direction.x, - -m_lights[index].direction.y, - -m_lights[index].direction.z, - 1.0f }; + int lightIndex = 0; - glLightfv(GL_LIGHT0 + index, GL_SPOT_DIRECTION, direction); - } - else if (m_lights[index].type == LIGHT_DIRECTIONAL) + for (const Light &light : m_lights) + { + if (m_lightsEnabled[lightIndex]) { - GLfloat position[4] = { -m_lights[index].direction.x, - -m_lights[index].direction.y, - -m_lights[index].direction.z, - 0.0f }; - glLightfv(GL_LIGHT0 + index, GL_POSITION, position); + if (light.type == LIGHT_SPOT) + { + GLfloat direction[4] = { -light.direction.x, -light.direction.y, -light.direction.z, 1.0f }; + glLightfv(GL_LIGHT0 + lightIndex, GL_SPOT_DIRECTION, direction); + } + else if (light.type == LIGHT_DIRECTIONAL) + { + GLfloat position[4] = { -light.direction.x, -light.direction.y, -light.direction.z, 0.0f }; + glLightfv(GL_LIGHT0 + lightIndex, GL_POSITION, position); + } } + + lightIndex++; } // update point lights @@ -590,17 +568,20 @@ void CGLDevice::UpdateLightPositions() glScalef(1.0f, 1.0f, -1.0f); glMultMatrixf(m_viewMat.Array()); - for (int index = 0; index < lightCount; index++) - { - if (m_lights[index].type == LIGHT_POINT) - { - GLfloat position[4] = { m_lights[index].position.x, - m_lights[index].position.y, - m_lights[index].position.z, - 1.0f }; + lightIndex = 0; - glLightfv(GL_LIGHT0 + index, GL_POSITION, position); + for (const Light &light : m_lights) + { + if (m_lightsEnabled[lightIndex]) + { + if (light.type == LIGHT_POINT) + { + GLfloat position[4] = { light.position.x, light.position.y, light.position.z, 1.0f }; + glLightfv(GL_LIGHT0 + lightIndex, GL_POSITION, position); + } } + + lightIndex++; } glPopMatrix(); diff --git a/src/graphics/opengl/gldevice.h b/src/graphics/opengl/gldevice.h index fe0635c9..24df9229 100644 --- a/src/graphics/opengl/gldevice.h +++ b/src/graphics/opengl/gldevice.h @@ -256,8 +256,6 @@ private: }; //! Detected capabilities - //! OpenGL version - int m_glMajor = 1, m_glMinor = 1; //! Depth texture support ShadowMappingSupport m_shadowMappingSupport = SMS_NONE; //! Shadow ambient support diff --git a/src/graphics/opengl/glutil.cpp b/src/graphics/opengl/glutil.cpp index 72ea019a..b28caad7 100644 --- a/src/graphics/opengl/glutil.cpp +++ b/src/graphics/opengl/glutil.cpp @@ -28,6 +28,7 @@ #include #include +#include // Graphics module namespace namespace Gfx @@ -36,6 +37,26 @@ namespace Gfx GLuint textureCoordinates[] = { GL_S, GL_T, GL_R, GL_Q }; GLuint textureCoordGen[] = { GL_TEXTURE_GEN_S, GL_TEXTURE_GEN_T, GL_TEXTURE_GEN_R, GL_TEXTURE_GEN_Q }; +bool InitializeGLEW() +{ + static bool glewInited = false; + + if (!glewInited) + { + glewExperimental = GL_TRUE; + + if (glewInit() != GLEW_OK) + { + GetLogger()->Error("GLEW initialization failed\n"); + return false; + } + + glewInited = true; + } + + return true; +} + FramebufferSupport DetectFramebufferSupport() { if (GetOpenGLVersion() >= 30) return FBS_ARB; @@ -64,9 +85,15 @@ std::unique_ptr CreateDevice(const DeviceConfig &config, const std::str } int GetOpenGLVersion() +{ + int major, minor; + + return GetOpenGLVersion(major, minor); +} + +int GetOpenGLVersion(int &major, int &minor) { const char *version = reinterpret_cast(glGetString(GL_VERSION)); - int major = 0, minor = 0; sscanf(version, "%d.%d", &major, &minor); @@ -77,24 +104,126 @@ std::string GetHardwareInfo(bool full) { int glversion = GetOpenGLVersion(); + std::stringstream result; + + // basic hardware information const char* version = reinterpret_cast(glGetString(GL_VERSION)); const char* vendor = reinterpret_cast(glGetString(GL_VENDOR)); const char* renderer = reinterpret_cast(glGetString(GL_RENDERER)); - std::string result; - - result += std::string("Hardware information:\n\n"); - result += "Version:\t" + std::string(version) + '\n'; - result += "Vendor:\t" + std::string(vendor) + '\n'; - result += "Renderer:\t" + std::string(renderer) + '\n'; + result << "Hardware information:\n\n"; + result << "OpenGL Version:\t\t" << version << '\n'; + result << "Hardware Vendor:\t\t" << vendor << '\n'; + result << "Renderer:\t\t\t" << renderer << '\n'; + // GLSL version if available if (glversion >= 20) { const char* glslVersion = reinterpret_cast(glGetString(GL_SHADING_LANGUAGE_VERSION)); - result += "Shading Language:\t" + std::string(glslVersion) + '\n'; + result << "Shading Language Version:\t" << glslVersion << '\n'; } - return result; + if (!full) return result.str(); + + // extended hardware information + int value = 0; + + result << "\nCapabilities:\n\n"; + + // texture size + glGetIntegerv(GL_MAX_TEXTURE_SIZE, &value); + result << "Max Texture Size:\t\t" << value << '\n'; + + if (glewIsSupported("GL_EXT_texture_filter_anisotropic")) + { + result << "Anisotropic filtering:\t\tsupported\n"; + + float level; + glGetFloatv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &level); + + result << " Max Level:\t\t" << static_cast(level) << '\n'; + } + else + { + result << "Anisotropic filtering:\t\tunsupported\n"; + } + + // multitexturing + if (glversion >= 13) + { + result << "Multitexturing:\t\tsupported\n"; + glGetIntegerv(GL_MAX_TEXTURE_UNITS, &value); + result << " Max Texture Units:\t\t" << value << '\n'; + + if (glversion >= 20) + { + glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, &value); + result << " Max Texture Image Units:\t" << value << '\n'; + } + } + else + { + result << "Multitexturing:\t\tunsupported\n"; + } + + // FBO support + FramebufferSupport framebuffer = DetectFramebufferSupport(); + + if (framebuffer == FBS_ARB) + { + result << "Framebuffer Object:\t\tsupported\n"; + result << " Type:\t\t\tCore/ARB\n"; + + glGetIntegerv(GL_MAX_RENDERBUFFER_SIZE, &value); + result << " Max Renderbuffer Size:\t" << value << '\n'; + + glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS, &value); + result << " Max Color Attachments:\t" << value << '\n'; + + result << "Multisampling:\t\tsupported\n"; + + glGetIntegerv(GL_MAX_FRAMEBUFFER_SAMPLES, &value); + result << " Max Framebuffer Samples:\t" << value << '\n'; + } + else if (framebuffer == FBS_EXT) + { + result << "Framebuffer Object:\tsupported\n"; + result << " Type:\tEXT\n"; + + glGetIntegerv(GL_MAX_RENDERBUFFER_SIZE_EXT, &value); + result << " Max Renderbuffer Size:\t" << value << '\n'; + + glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS_EXT, &value); + result << " Max Color Attachments:\t" << value << '\n'; + + if (glewIsSupported("GL_EXT_framebuffer_multisample")) + { + result << "Multisampling:\tsupported\n"; + + glGetIntegerv(GL_MAX_SAMPLES_EXT, &value); + result << " Max Framebuffer Samples:\t" << value << '\n'; + } + } + else + { + result << "Framebuffer Object:\tunsupported\n"; + } + + // VBO support + if (glversion >= 15) + { + result << "VBO:\t\t\tsupported (core)\n"; + } + else if (glewIsSupported("GL_ARB_vertex_buffer_object")) + { + result << "VBO:\t\t\tsupported (ARB)\n"; + } + else + { + result << "VBO:\t\t\tunsupported\n"; + } + + return result.str(); } GLenum TranslateGfxPrimitive(PrimitiveType type) diff --git a/src/graphics/opengl/glutil.h b/src/graphics/opengl/glutil.h index 5ae4ff1b..97b5c2cc 100644 --- a/src/graphics/opengl/glutil.h +++ b/src/graphics/opengl/glutil.h @@ -45,17 +45,23 @@ enum FramebufferSupport FBS_ARB, }; +bool InitializeGLEW(); + FramebufferSupport DetectFramebufferSupport(); //! Creates OpenGL device std::unique_ptr CreateDevice(const DeviceConfig &config, const std::string& name); -//! Returns OpenGL version as one number. -// First digit is major part, second digit is minor part. +//! Returns OpenGL version +// \return First digit is major part, second digit is minor part. int GetOpenGLVersion(); +//! Returns OpenGL version +// \return First digit is major part, second digit is minor part. +int GetOpenGLVersion(int &major, int &minor); + //! Returns information about graphics card -std::string GetHardwareInfo(bool full); +std::string GetHardwareInfo(bool full = false); //! Translate Gfx primitive type to OpenGL primitive type GLenum TranslateGfxPrimitive(PrimitiveType type);