diff --git a/data/shaders/coloredquad.frag b/data/shaders/coloredquad.frag new file mode 100644 index 000000000..da7911156 --- /dev/null +++ b/data/shaders/coloredquad.frag @@ -0,0 +1,7 @@ +#version 130 +uniform vec4 color; + +void main() +{ + gl_FragColor = color; +} \ No newline at end of file diff --git a/data/shaders/coloredquad.vert b/data/shaders/coloredquad.vert new file mode 100644 index 000000000..53c486ce3 --- /dev/null +++ b/data/shaders/coloredquad.vert @@ -0,0 +1,11 @@ +#version 130 +uniform vec2 center; +uniform vec2 size; + +in vec2 position; + + +void main() +{ + gl_Position = vec4(position * size + center, 0., 1.); +} \ No newline at end of file diff --git a/src/graphics/glwrap.cpp b/src/graphics/glwrap.cpp index 02d96f3fd..dfdff2d79 100644 --- a/src/graphics/glwrap.cpp +++ b/src/graphics/glwrap.cpp @@ -35,6 +35,8 @@ PFNGLGETSHADERINFOLOGPROC glGetShaderInfoLog; PFNGLACTIVETEXTUREPROC glActiveTexture; PFNGLUNIFORM2FPROC glUniform2f; PFNGLUNIFORM1IPROC glUniform1i; +PFNGLUNIFORM3IPROC glUniform3i; +PFNGLUNIFORM4IPROC glUniform4i; PFNGLGETPROGRAMIVPROC glGetProgramiv; PFNGLGETPROGRAMINFOLOGPROC glGetProgramInfoLog; PFNGLGETATTRIBLOCATIONPROC glGetAttribLocation; @@ -79,6 +81,8 @@ void initGL() glGetShaderInfoLog = (PFNGLGETSHADERINFOLOGPROC)IRR_OGL_LOAD_EXTENSION("glGetShaderInfoLog"); glActiveTexture = (PFNGLACTIVETEXTUREPROC)IRR_OGL_LOAD_EXTENSION("glActiveTexture"); glUniform2f = (PFNGLUNIFORM2FPROC)IRR_OGL_LOAD_EXTENSION("glUniform2f"); + glUniform4i = (PFNGLUNIFORM4IPROC)IRR_OGL_LOAD_EXTENSION("glUniform4i"); + glUniform3i = (PFNGLUNIFORM3IPROC)IRR_OGL_LOAD_EXTENSION("glUniform3i"); glUniform1i = (PFNGLUNIFORM1IPROC)IRR_OGL_LOAD_EXTENSION("glUniform1i"); glGetProgramiv = (PFNGLGETPROGRAMIVPROC)IRR_OGL_LOAD_EXTENSION("glGetProgramiv"); glGetProgramInfoLog = (PFNGLGETPROGRAMINFOLOGPROC)IRR_OGL_LOAD_EXTENSION("glGetProgramInfoLog"); @@ -255,3 +259,72 @@ void draw2DImage(const video::ITexture* texture, const core::rect& destRect glBindBuffer(GL_ARRAY_BUFFER, 0); #endif } + +static GLuint ColoredQuadShader; +static GLuint ColoredQuadUniformCenter; +static GLuint ColoredQuadUniformSize; +static GLuint ColoredQuadUniformColor; + +void GL32_draw2DRectangle(video::SColor color, const core::rect& position, + const core::rect* clip) +{ + +#ifndef OGL32CTX + irr_driver->getVideoDriver()->draw2DImage(texture, destRect, sourceRect, clipRect, colors, useAlphaChannelOfTexture); +#else + core::dimension2d frame_size = + irr_driver->getVideoDriver()->getCurrentRenderTargetSize(); + const int screen_w = frame_size.Width; + const int screen_h = frame_size.Height; + float center_pos_x = position.UpperLeftCorner.X + position.LowerRightCorner.X; + center_pos_x /= screen_w; + center_pos_x -= 1; + float center_pos_y = position.UpperLeftCorner.Y + position.LowerRightCorner.Y; + center_pos_y /= screen_h; + center_pos_y = 1 - center_pos_y; + float width = position.LowerRightCorner.X - position.UpperLeftCorner.X; + width /= screen_w; + float height = position.LowerRightCorner.Y - position.UpperLeftCorner.Y; + height /= screen_h; + + initGL(); + const float quad_vertex[] = + { + -1., -1., 0., 1., + -1., 1., 0., 0., + 1., -1., 1., 1., + 1., 1., 1., 0. + }; + + if (color.getAlpha() < 255) + { + glEnable(GL_BLEND); + glEnable(GL_ALPHA_TEST); + glAlphaFunc(GL_GREATER, 0.f); + } + else + { + glDisable(GL_BLEND); + glDisable(GL_ALPHA_TEST); + } + + if (!ColoredQuadShader) + { + ColoredQuadShader = LoadProgram(file_manager->getAsset("shaders/coloredquad.vert").c_str(), file_manager->getAsset("shaders/coloredquad.frag").c_str()); + glGenBuffers(1, &quad_buffer); + glBindBuffer(GL_ARRAY_BUFFER, quad_buffer); + glBufferData(GL_ARRAY_BUFFER, 16 * sizeof(float), quad_vertex, GL_STATIC_DRAW); + ColoredQuadUniformColor = glGetUniformLocation(ColoredQuadShader, "color"); + } + glUseProgram(ColoredQuadShader); + glUniform2f(ColoredQuadUniformCenter, center_pos_x, center_pos_y); + glUniform2f(ColoredQuadUniformSize, width, height); + glUniform4i(ColoredQuadUniformColor, color.getRed(), color.getGreen(), color.getBlue(), color.getAlpha()); + glEnableVertexAttribArray(0); + glBindBuffer(GL_ARRAY_BUFFER, quad_buffer); + glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(float), 0); + glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); + glDisableVertexAttribArray(0); + glBindBuffer(GL_ARRAY_BUFFER, 0); +#endif +} diff --git a/src/graphics/glwrap.hpp b/src/graphics/glwrap.hpp index b961654b8..beda6dd2c 100644 --- a/src/graphics/glwrap.hpp +++ b/src/graphics/glwrap.hpp @@ -57,6 +57,8 @@ extern PFNGLGETSHADERINFOLOGPROC glGetShaderInfoLog; extern PFNGLACTIVETEXTUREPROC glActiveTexture; extern PFNGLUNIFORM2FPROC glUniform2f; extern PFNGLUNIFORM1IPROC glUniform1i; +extern PFNGLUNIFORM3IPROC glUniform3i; +extern PFNGLUNIFORM4IPROC glUniform4i; extern PFNGLGETPROGRAMIVPROC glGetProgramiv; extern PFNGLGETPROGRAMINFOLOGPROC glGetProgramInfoLog; extern PFNGLGETATTRIBLOCATIONPROC glGetAttribLocation; @@ -74,4 +76,6 @@ void draw2DImage(const irr::video::ITexture* texture, const irr::core::rect const irr::core::rect& sourceRect, const irr::core::rect* clipRect, const irr::video::SColor* const colors, bool useAlphaChannelOfTexture); +void GL32_draw2DRectangle(irr::video::SColor color, const irr::core::rect& position, + const irr::core::rect* clip = 0); #endif diff --git a/src/guiengine/skin.cpp b/src/guiengine/skin.cpp index aacaaae29..d17128d39 100644 --- a/src/guiengine/skin.cpp +++ b/src/guiengine/skin.cpp @@ -2061,12 +2061,12 @@ void Skin::draw3DSunkenPane (IGUIElement *element, video::SColor bgcolor, center.Y + (int)(((int)rect.LowerRightCorner.Y - (int)center.Y)*texture_size); } - GUIEngine::getDriver()->draw2DRectangle(focused ? border_color_focus : border_color, borderArea); + GL32_draw2DRectangle(focused ? border_color_focus : border_color, borderArea); core::recti innerArea = borderArea; innerArea.UpperLeftCorner += position2d< s32 >( 3, 3 ); innerArea.LowerRightCorner -= position2d< s32 >( 3, 3 ); - GUIEngine::getDriver()->draw2DRectangle(focused ? bg_color_focused : bg_color, innerArea); + GL32_draw2DRectangle(focused ? bg_color_focused : bg_color, innerArea); return; } else if (type == WTYPE_LIST) @@ -2130,7 +2130,7 @@ void Skin::drawBGFadeColor() SColor color = SkinConfig::m_colors["dialog_background::neutral"]; if (m_dialog_size < 1.0f) color.setAlpha( (unsigned int)(color.getAlpha()*m_dialog_size )); - GUIEngine::getDriver()->draw2DRectangle( color, + GL32_draw2DRectangle(color, core::recti(position2d< s32 >(0,0), GUIEngine::getDriver()->getCurrentRenderTargetSize()) ); } // drawBGFadeColor @@ -2178,7 +2178,7 @@ void Skin::draw3DMenuPane (IGUIElement *element, const core::recti &rect, const core::recti *clip) { SColor color = SColor(150, 96, 74, 196); - GUIEngine::getDriver()->draw2DRectangle(color, rect); + GL32_draw2DRectangle(color, rect); } // draw3DMenuPane // -----------------------------------------------------------------------------