summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--vcl/Package_opengl.mk4
-rw-r--r--vcl/inc/opengl/program.hxx19
-rw-r--r--vcl/opengl/combinedFragmentShader.glsl45
-rw-r--r--vcl/opengl/combinedTextureFragmentShader.glsl64
-rw-r--r--vcl/opengl/combinedTextureVertexShader.glsl32
-rw-r--r--vcl/opengl/combinedVertexShader.glsl47
-rw-r--r--vcl/opengl/gdiimpl.cxx69
-rw-r--r--vcl/opengl/program.cxx18
8 files changed, 273 insertions, 25 deletions
diff --git a/vcl/Package_opengl.mk b/vcl/Package_opengl.mk
index a0f6e9a27128..2fa917eeac42 100644
--- a/vcl/Package_opengl.mk
+++ b/vcl/Package_opengl.mk
@@ -21,6 +21,10 @@ $(eval $(call gb_Package_add_files,vcl_opengl_shader,$(LIBO_ETC_FOLDER)/opengl,\
invert50FragmentShader.glsl \
convolutionFragmentShader.glsl \
linearGradientFragmentShader.glsl \
+ combinedTextureFragmentShader.glsl \
+ combinedTextureVertexShader.glsl \
+ combinedFragmentShader.glsl \
+ combinedVertexShader.glsl \
lineFragmentShader.glsl \
lineVertexShader.glsl \
maskFragmentShader.glsl \
diff --git a/vcl/inc/opengl/program.hxx b/vcl/inc/opengl/program.hxx
index 5944c72be127..2fab98c6b4d5 100644
--- a/vcl/inc/opengl/program.hxx
+++ b/vcl/inc/opengl/program.hxx
@@ -27,6 +27,21 @@
typedef std::unordered_map< OString, GLuint, OStringHash > UniformCache;
typedef std::list< OpenGLTexture > TextureList;
+enum class TextureShaderType
+{
+ Normal = 0,
+ Blend,
+ Masked,
+ Diff,
+ MaskedColor
+};
+
+enum class DrawShaderType
+{
+ Normal = 0,
+ Line
+};
+
class VCL_PLUGIN_PUBLIC OpenGLProgram
{
private:
@@ -78,6 +93,10 @@ public:
void SetTransform( const OString& rName, const OpenGLTexture& rTexture,
const basegfx::B2DPoint& rNull, const basegfx::B2DPoint& rX,
const basegfx::B2DPoint& rY );
+ void SetIdentityTransform(const OString& rName);
+ void SetShaderType(TextureShaderType eTextureShaderType);
+ void SetShaderType(DrawShaderType eDrawShaderType);
+
void SetBlendMode( GLenum nSFactor, GLenum nDFactor );
void ApplyMatrix(float fWidth, float fHeight, float fPixelOffset = 0.0f);
diff --git a/vcl/opengl/combinedFragmentShader.glsl b/vcl/opengl/combinedFragmentShader.glsl
new file mode 100644
index 000000000000..c44e75c09373
--- /dev/null
+++ b/vcl/opengl/combinedFragmentShader.glsl
@@ -0,0 +1,45 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+varying float fade_factor; // 0->1 fade factor used for AA
+uniform vec4 color;
+
+uniform float line_width;
+uniform float feather;
+
+#define TYPE_NORMAL 0
+#define TYPE_LINE 1
+
+uniform int type;
+
+void main()
+{
+ float alpha = 1.0;
+
+ if (type == TYPE_LINE)
+ {
+ float start = (line_width / 2.0) - feather; // where we start to apply alpha
+ float end = (line_width / 2.0) + feather; // where we end to apply alpha
+
+ // Calculate the multiplier so we can transform the 0->1 fade factor
+ // to take feather and line width into account.
+ float multiplied = 1.0 / (1.0 - (start / end));
+
+ float dist = (1.0 - abs(fade_factor)) * multiplied;
+
+ alpha = clamp(dist, 0.0, 1.0);
+ }
+
+ vec4 result_color = color;
+ result_color.a = result_color.a * alpha;
+
+ gl_FragColor = result_color;
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/opengl/combinedTextureFragmentShader.glsl b/vcl/opengl/combinedTextureFragmentShader.glsl
new file mode 100644
index 000000000000..d8864cfe21c5
--- /dev/null
+++ b/vcl/opengl/combinedTextureFragmentShader.glsl
@@ -0,0 +1,64 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+varying vec2 tex_coord;
+varying vec2 alpha_coord;
+varying vec2 mask_coord;
+
+uniform sampler2D texture;
+uniform sampler2D mask;
+uniform sampler2D alpha;
+
+uniform vec4 color;
+
+uniform int type;
+
+#define TYPE_NORMAL 0
+#define TYPE_BLEND 1
+#define TYPE_MASKED 2
+#define TYPE_DIFF 3
+#define TYPE_MASKED_COLOR 4
+
+void main()
+{
+ vec4 texelTexture = texture2D(texture, tex_coord);
+
+ if (type == TYPE_NORMAL)
+ {
+ gl_FragColor = texelTexture;
+ }
+ else if (type == TYPE_BLEND)
+ {
+ vec4 texelMask = texture2D(mask, mask_coord);
+ vec4 texelAlpha = texture2D(alpha, alpha_coord);
+ gl_FragColor = texelTexture;
+ gl_FragColor.a = 1.0 - (1.0 - floor(texelAlpha.r)) * texelMask.r;
+ }
+ else if (type == TYPE_MASKED)
+ {
+ vec4 texelMask = texture2D(mask, mask_coord);
+ gl_FragColor = texelTexture;
+ gl_FragColor.a = 1.0 - texelMask.r;
+ }
+ else if (type == TYPE_DIFF)
+ {
+ vec4 texelMask = texture2D(mask, mask_coord);
+ float alpha = 1.0 - abs(texelTexture.r - texelMask.r);
+ if (alpha > 0.0)
+ gl_FragColor = texelMask / alpha;
+ gl_FragColor.a = alpha;
+ }
+ else if (type == TYPE_MASKED_COLOR)
+ {
+ gl_FragColor = color;
+ gl_FragColor.a = 1.0 - texelTexture.r;
+ }
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/opengl/combinedTextureVertexShader.glsl b/vcl/opengl/combinedTextureVertexShader.glsl
new file mode 100644
index 000000000000..883ec631fa73
--- /dev/null
+++ b/vcl/opengl/combinedTextureVertexShader.glsl
@@ -0,0 +1,32 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+attribute vec4 position;
+attribute vec2 tex_coord_in;
+attribute vec2 mask_coord_in;
+attribute vec2 alpha_coord_in;
+
+varying vec2 tex_coord;
+varying vec2 mask_coord;
+varying vec2 alpha_coord;
+
+uniform mat4 mvp;
+uniform mat4 transform;
+
+uniform int type;
+
+void main()
+{
+ gl_Position = mvp * transform * position;
+ tex_coord = tex_coord_in;
+ mask_coord = mask_coord_in;
+ alpha_coord = alpha_coord_in;
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/opengl/combinedVertexShader.glsl b/vcl/opengl/combinedVertexShader.glsl
new file mode 100644
index 000000000000..9272544c33ef
--- /dev/null
+++ b/vcl/opengl/combinedVertexShader.glsl
@@ -0,0 +1,47 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+attribute vec2 position;
+attribute vec4 extrusion_vectors;
+
+varying float fade_factor; // fade factor for anti-aliasing
+
+uniform float line_width;
+uniform float feather; // width where we fade the line
+
+uniform mat4 mvp;
+
+#define TYPE_NORMAL 0
+#define TYPE_LINE 1
+
+uniform int type;
+
+void main()
+{
+ vec4 final_position = vec4(position, 0.0, 1.0);
+
+ if (type == TYPE_LINE)
+ {
+ vec2 extrusion_vector = extrusion_vectors.xy;
+ // miter factor to additionaly lenghten the distance of vertex (needed for miter)
+ // if 1.0 - miter_factor has no effect
+ float miter_factor = 1.0f / abs(extrusion_vectors.z);
+ // fade factor is always -1.0 or 1.0 -> we transport that info together with length
+ fade_factor = sign(extrusion_vectors.z);
+
+ float rendered_thickness = (line_width + feather * 2.0) * miter_factor;
+
+ // lengthen the vertex in directon of the extrusion vector by line width.
+ final_position = vec4(position + (extrusion_vector * (rendered_thickness / 2.0) ), 0.0, 1.0);
+ }
+
+ gl_Position = mvp * final_position;
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/opengl/gdiimpl.cxx b/vcl/opengl/gdiimpl.cxx
index a92e5b3fca5e..58b4d62cca2e 100644
--- a/vcl/opengl/gdiimpl.cxx
+++ b/vcl/opengl/gdiimpl.cxx
@@ -544,8 +544,9 @@ bool OpenGLSalGraphicsImpl::UseSolid( SalColor nColor, sal_uInt8 nTransparency )
{
if( nColor == SALCOLOR_NONE )
return false;
- if( !UseProgram( "dumbVertexShader", "solidFragmentShader" ) )
+ if (!UseProgram("combinedVertexShader", "combinedFragmentShader"))
return false;
+ mpProgram->SetShaderType(DrawShaderType::Normal);
mpProgram->SetColor( "color", nColor, nTransparency );
#ifdef DBG_UTIL
mProgramIsSolidColor = true;
@@ -560,8 +561,9 @@ bool OpenGLSalGraphicsImpl::UseSolid( SalColor nColor, double fTransparency )
{
if( nColor == SALCOLOR_NONE )
return false;
- if( !UseProgram( "dumbVertexShader", "solidFragmentShader" ) )
+ if (!UseProgram("combinedVertexShader", "combinedFragmentShader"))
return false;
+ mpProgram->SetShaderType(DrawShaderType::Normal);
mpProgram->SetColorf( "color", nColor, fTransparency );
#ifdef DBG_UTIL
mProgramIsSolidColor = true;
@@ -925,12 +927,13 @@ bool OpenGLSalGraphicsImpl::UseLine(SalColor nColor, double fTransparency, GLflo
{
if( nColor == SALCOLOR_NONE )
return false;
- if( !UseProgram( "lineVertexShader", "lineFragmentShader" ) )
+ if (!UseProgram("combinedVertexShader", "combinedFragmentShader"))
return false;
+ mpProgram->SetShaderType(DrawShaderType::Line);
mpProgram->SetColorf("color", nColor, fTransparency);
mpProgram->SetUniform1f("line_width", fLineWidth);
// The width of the feather - area we make lineary transparent in VS.
- // Good AA value is 0.5
+ // Good AA value is 0.5f, no AA if feather 0.0f
mpProgram->SetUniform1f("feather", bUseAA ? 0.5f : 0.0f);
// We need blending or AA won't work correctly
mpProgram->SetBlendMode( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
@@ -970,7 +973,7 @@ void OpenGLSalGraphicsImpl::DrawConvexPolygon( sal_uInt32 nPoints, const SalPoin
#endif
SalColor lastSolidColor = mProgramSolidColor;
double lastSolidTransparency = mProgramSolidTransparency;
- if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f ,true))
+ if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f, true))
{
for( i = 0; i < nPoints; ++i )
{
@@ -1013,7 +1016,7 @@ void OpenGLSalGraphicsImpl::DrawConvexPolygon( const tools::Polygon& rPolygon, b
#endif
SalColor lastSolidColor = mProgramSolidColor;
double lastSolidTransparency = mProgramSolidTransparency;
- if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f ,true))
+ if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f, true))
{
for( i = 0; i < nPoints; ++i )
{
@@ -1063,7 +1066,7 @@ void OpenGLSalGraphicsImpl::DrawTrapezoid( const basegfx::B2DTrapezoid& trapezoi
#endif
SalColor lastSolidColor = mProgramSolidColor;
double lastSolidTransparency = mProgramSolidTransparency;
- if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f ,true))
+ if (UseLine(lastSolidColor, lastSolidTransparency, 1.0f, true))
{
for( i = 0; i < nPoints; ++i )
{
@@ -1184,9 +1187,11 @@ void OpenGLSalGraphicsImpl::DrawTexture( OpenGLTexture& rTexture, const SalTwoRe
SAL_INFO("vcl.opengl", "draw texture");
- if( !UseProgram( "textureVertexShader", "textureFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
- mpProgram->SetTexture( "sampler", rTexture );
+ mpProgram->SetShaderType(TextureShaderType::Normal);
+ mpProgram->SetIdentityTransform("transform");
+ mpProgram->SetTexture("texture", rTexture);
DrawTextureRect( rTexture, pPosAry, bInverted );
mpProgram->Clean();
}
@@ -1393,9 +1398,11 @@ void OpenGLSalGraphicsImpl::DrawAlphaTexture( OpenGLTexture& rTexture, const Sal
{
OpenGLZone aZone;
- if( !UseProgram( "textureVertexShader", "textureFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
- mpProgram->SetTexture( "sampler", rTexture );
+ mpProgram->SetShaderType(TextureShaderType::Normal);
+ mpProgram->SetIdentityTransform("transform");
+ mpProgram->SetTexture("texture", rTexture);
mpProgram->SetBlendMode( bPremultiplied ? GL_ONE : GL_SRC_ALPHA,
GL_ONE_MINUS_SRC_ALPHA );
DrawTextureRect( rTexture, rPosAry, bInverted );
@@ -1406,8 +1413,10 @@ void OpenGLSalGraphicsImpl::DrawTextureDiff( OpenGLTexture& rTexture, OpenGLText
{
OpenGLZone aZone;
- if( !UseProgram( "maskedTextureVertexShader", "diffTextureFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
+ mpProgram->SetShaderType(TextureShaderType::Diff);
+ mpProgram->SetIdentityTransform("transform");
mpProgram->SetTexture( "texture", rTexture );
mpProgram->SetTexture( "mask", rMask );
mpProgram->SetBlendMode( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
@@ -1424,9 +1433,11 @@ void OpenGLSalGraphicsImpl::DrawTextureWithMask( OpenGLTexture& rTexture, OpenGL
{
OpenGLZone aZone;
- if( !UseProgram( "maskedTextureVertexShader", "maskedTextureFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
- mpProgram->SetTexture( "sampler", rTexture );
+ mpProgram->SetShaderType(TextureShaderType::Masked);
+ mpProgram->SetIdentityTransform("transform");
+ mpProgram->SetTexture( "texture", rTexture );
mpProgram->SetTexture( "mask", rMask );
mpProgram->SetBlendMode( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
@@ -1446,9 +1457,10 @@ void OpenGLSalGraphicsImpl::DrawBlendedTexture( OpenGLTexture& rTexture, OpenGLT
{
OpenGLZone aZone;
- if( !UseProgram( "blendedTextureVertexShader", "blendedTextureFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
- mpProgram->SetTexture( "sampler", rTexture );
+ mpProgram->SetShaderType(TextureShaderType::Blend);
+ mpProgram->SetTexture( "texture", rTexture );
mpProgram->SetTexture( "mask", rMask );
mpProgram->SetTexture( "alpha", rAlpha );
@@ -1469,10 +1481,12 @@ void OpenGLSalGraphicsImpl::DrawMask( OpenGLTexture& rMask, SalColor nMaskColor,
{
OpenGLZone aZone;
- if( !UseProgram( "textureVertexShader", "maskFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
+ mpProgram->SetShaderType(TextureShaderType::MaskedColor);
+ mpProgram->SetIdentityTransform("transform");
mpProgram->SetColor( "color", nMaskColor, 0 );
- mpProgram->SetTexture( "sampler", rMask );
+ mpProgram->SetTexture("texture", rMask);
mpProgram->SetBlendMode( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
DrawTextureRect( rMask, pPosAry );
mpProgram->Clean();
@@ -1530,15 +1544,16 @@ void OpenGLSalGraphicsImpl::FlushDeferredDrawing()
}
#endif
- if( !UseProgram( "textureVertexShader", "maskFragmentShader" ) )
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return;
-
+ mpProgram->SetShaderType(TextureShaderType::MaskedColor);
+ mpProgram->SetIdentityTransform("transform");
mpProgram->SetBlendMode(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
for (auto& rPair : mpAccumulatedTextures->getAccumulatedTexturesMap())
{
OpenGLTexture& rTexture = rPair.second->maTexture;
- mpProgram->SetTexture("sampler", rTexture);
+ mpProgram->SetTexture("texture", rTexture);
for (auto& rColorTwoRectPair: rPair.second->maColorTextureDrawParametersMap)
{
mpProgram->SetColor("color", rColorTwoRectPair.first, 0);
@@ -2048,11 +2063,13 @@ bool OpenGLSalGraphicsImpl::blendBitmap(
VCL_GL_INFO( "::blendBitmap" );
PreDraw();
- if (!UseProgram("textureVertexShader", "textureFragmentShader"))
+ if (!UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader"))
return true;
+ mpProgram->SetShaderType(TextureShaderType::Normal);
+ mpProgram->SetIdentityTransform("transform");
+ mpProgram->SetTexture("texture", rTexture);
mpProgram->SetBlendMode(GL_ZERO, GL_SRC_COLOR);
- mpProgram->SetTexture("sampler", rTexture);
DrawTextureRect(rTexture, rPosAry);
mpProgram->Clean();
@@ -2332,12 +2349,14 @@ void OpenGLSalGraphicsImpl::doFlush()
VCL_GL_INFO( "Texture height " << maOffscreenTex.GetHeight() << " vs. window height " << GetHeight() );
OpenGLProgram *pProgram =
- mpWindowContext->UseProgram( "textureVertexShader", "textureFragmentShader", "// flush shader\n" ); // flush helps profiling
+ mpWindowContext->UseProgram("combinedTextureVertexShader", "combinedTextureFragmentShader", "// flush shader\n" ); // flush helps profiling
if( !pProgram )
VCL_GL_INFO( "Can't compile simple copying shader !" );
else
{
- pProgram->SetTexture( "sampler", maOffscreenTex );
+ pProgram->SetShaderType(TextureShaderType::Normal);
+ pProgram->SetIdentityTransform("transform");
+ pProgram->SetTexture("texture", maOffscreenTex);
SalTwoRect aPosAry( 0, 0, maOffscreenTex.GetWidth(), maOffscreenTex.GetHeight(),
0, 0, maOffscreenTex.GetWidth(), maOffscreenTex.GetHeight() );
diff --git a/vcl/opengl/program.cxx b/vcl/opengl/program.cxx
index 71530cbf75cb..2331080d28c1 100644
--- a/vcl/opengl/program.cxx
+++ b/vcl/opengl/program.cxx
@@ -135,6 +135,16 @@ void OpenGLProgram::SetExtrusionVectors(const GLvoid* pData)
SetVertexAttrib(mnNormalAttrib, "extrusion_vectors", pData, 3);
}
+void OpenGLProgram::SetShaderType(TextureShaderType eTextureShaderType)
+{
+ SetUniform1i("type", GLint(eTextureShaderType));
+}
+
+void OpenGLProgram::SetShaderType(DrawShaderType eDrawShaderType)
+{
+ SetUniform1i("type", GLint(eDrawShaderType));
+}
+
GLuint OpenGLProgram::GetUniformLocation( const OString& rName )
{
auto it = maUniformLocations.find( rName );
@@ -286,6 +296,14 @@ void OpenGLProgram::SetTransform(
CHECK_GL_ERROR();
}
+void OpenGLProgram::SetIdentityTransform(const OString& rName)
+{
+ GLuint nUniform = GetUniformLocation(rName);
+ glm::mat4 aMatrix = glm::mat4();
+ glUniformMatrix4fv(nUniform, 1, GL_FALSE, glm::value_ptr( aMatrix ) );
+ CHECK_GL_ERROR();
+}
+
void OpenGLProgram::ApplyMatrix(float fWidth, float fHeight, float fPixelOffset)
{