summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTomaž Vajngerl <tomaz.vajngerl@collabora.co.uk>2016-11-03 23:05:25 +0100
committerMichael Meeks <michael.meeks@collabora.com>2016-11-11 11:06:54 +0000
commitd05b11e5f590272b0036cf09cf8721c37db33791 (patch)
tree8da16be50adaf18936699c8e6653324169569156
parent74eebc7a0768659426911541e16973bdf037c157 (diff)
tdf#103803 change from BGRA to RGBA color arrangement on Windows
BGRA is native color arrangement on Windows however some intel drivers have problems with large textures if they read from a BGRA buffer. So with this commit we switch to RGBA color arrangement. This shouldn't cause much performance differences, but we need to convert from RGBA to BGRA when printing. + fix: wrong GL format for RGBA image buffers commit: ed42212f53b2e52238346e64dae31a931d6c90a1 Reviewed-on: https://gerrit.libreoffice.org/30544 Tested-by: Jenkins <ci@libreoffice.org> Reviewed-by: Tomaž Vajngerl <quikee@gmail.com> (cherry picked from commit 6b571ae4608ac15256eb7582f442ce69975370f3) Change-Id: Ic112dc6a6c5d8b70e96041d0de15a03bbbdc406f Reviewed-on: https://gerrit.libreoffice.org/30763 Tested-by: Jenkins <ci@libreoffice.org> Reviewed-by: Michael Meeks <michael.meeks@collabora.com> Tested-by: Michael Meeks <michael.meeks@collabora.com>
-rw-r--r--vcl/opengl/salbmp.cxx38
-rw-r--r--vcl/win/gdi/salgdi2.cxx67
2 files changed, 63 insertions, 42 deletions
diff --git a/vcl/opengl/salbmp.cxx b/vcl/opengl/salbmp.cxx
index ef081ee9fd4d..f9b800565268 100644
--- a/vcl/opengl/salbmp.cxx
+++ b/vcl/opengl/salbmp.cxx
@@ -55,27 +55,15 @@ inline bool determineTextureFormat(sal_uInt16 nBits, GLenum& nFormat, GLenum& nT
nType = GL_UNSIGNED_BYTE;
return true;
case 16:
-#ifdef _WIN32
- nFormat = GL_BGR;
-#else
nFormat = GL_RGB;
-#endif
nType = GL_UNSIGNED_SHORT_5_6_5;
return true;
case 24:
-#ifdef _WIN32
- nFormat = GL_BGR;
-#else
nFormat = GL_RGB;
-#endif
nType = GL_UNSIGNED_BYTE;
return true;
case 32:
-#ifdef _WIN32
- nFormat = GL_BGRA;
-#else
nFormat = GL_RGBA;
-#endif
nType = GL_UNSIGNED_BYTE;
return true;
default:
@@ -816,16 +804,6 @@ BitmapBuffer* OpenGLSalBitmap::AcquireBuffer( BitmapAccessMode nMode )
break;
case 16:
{
-#ifdef _WIN32
- pBuffer->mnFormat = ScanlineFormat::N16BitTcLsbMask;
- ColorMaskElement aRedMask(0x00007c00);
- aRedMask.CalcMaskShift();
- ColorMaskElement aGreenMask(0x000003e0);
- aGreenMask.CalcMaskShift();
- ColorMaskElement aBlueMask(0x0000001f);
- aBlueMask.CalcMaskShift();
- pBuffer->maColorMask = ColorMask(aRedMask, aGreenMask, aBlueMask);
-#else
pBuffer->mnFormat = ScanlineFormat::N16BitTcMsbMask;
ColorMaskElement aRedMask(0x0000f800);
aRedMask.CalcMaskShift();
@@ -834,30 +812,15 @@ BitmapBuffer* OpenGLSalBitmap::AcquireBuffer( BitmapAccessMode nMode )
ColorMaskElement aBlueMask(0x0000001f);
aBlueMask.CalcMaskShift();
pBuffer->maColorMask = ColorMask(aRedMask, aGreenMask, aBlueMask);
-#endif
break;
}
case 24:
{
-#ifdef _WIN32
- pBuffer->mnFormat = ScanlineFormat::N24BitTcBgr;
-#else
pBuffer->mnFormat = ScanlineFormat::N24BitTcRgb;
-#endif
break;
}
case 32:
{
-#ifdef _WIN32
- pBuffer->mnFormat = ScanlineFormat::N32BitTcBgra;
- ColorMaskElement aRedMask(0x00ff0000);
- aRedMask.CalcMaskShift();
- ColorMaskElement aGreenMask(0x0000ff00);
- aGreenMask.CalcMaskShift();
- ColorMaskElement aBlueMask(0x000000ff);
- aBlueMask.CalcMaskShift();
- pBuffer->maColorMask = ColorMask(aRedMask, aGreenMask, aBlueMask);
-#else
pBuffer->mnFormat = ScanlineFormat::N32BitTcRgba;
ColorMaskElement aRedMask(0xff000000);
aRedMask.CalcMaskShift();
@@ -866,7 +829,6 @@ BitmapBuffer* OpenGLSalBitmap::AcquireBuffer( BitmapAccessMode nMode )
ColorMaskElement aBlueMask(0x0000ff00);
aBlueMask.CalcMaskShift();
pBuffer->maColorMask = ColorMask(aRedMask, aGreenMask, aBlueMask);
-#endif
break;
}
}
diff --git a/vcl/win/gdi/salgdi2.cxx b/vcl/win/gdi/salgdi2.cxx
index 8514e73c1523..751b8c93de24 100644
--- a/vcl/win/gdi/salgdi2.cxx
+++ b/vcl/win/gdi/salgdi2.cxx
@@ -73,6 +73,45 @@ void WinSalGraphics::copyArea( long nDestX, long nDestY,
namespace
{
+class ColorScanlineConverter
+{
+public:
+ ScanlineFormat meSourceFormat;
+ ScanlineFormat meDestinationFormat;
+
+ int mnComponentSize;
+ int mnComponentExchangeIndex;
+
+ long mnScanlineSize;
+
+ ColorScanlineConverter(ScanlineFormat eSourceFormat, ScanlineFormat eDestinationFormat, int nComponentSize, long nScanlineSize)
+ : meSourceFormat(eSourceFormat)
+ , meDestinationFormat(eDestinationFormat)
+ , mnComponentSize(nComponentSize)
+ , mnComponentExchangeIndex(0)
+ , mnScanlineSize(nScanlineSize)
+ {
+ if (meSourceFormat == ScanlineFormat::N32BitTcAbgr ||
+ meSourceFormat == ScanlineFormat::N32BitTcArgb)
+ {
+ mnComponentExchangeIndex = 1;
+ }
+ }
+
+ void convertScanline(sal_uInt8* pSource, sal_uInt8* pDestination)
+ {
+ for (int x = 0; x < mnScanlineSize; x += mnComponentSize)
+ {
+ for (int i = 0; i < mnComponentSize; ++i)
+ {
+ pDestination[x + i] = pSource[x + i];
+ }
+ pDestination[x + mnComponentExchangeIndex + 0] = pSource[x + mnComponentExchangeIndex + 2];
+ pDestination[x + mnComponentExchangeIndex + 2] = pSource[x + mnComponentExchangeIndex + 0];
+ }
+ }
+};
+
void convertToWinSalBitmap(SalBitmap& rSalBitmap, WinSalBitmap& rWinSalBitmap)
{
BitmapPalette aBitmapPalette;
@@ -90,11 +129,31 @@ void convertToWinSalBitmap(SalBitmap& rSalBitmap, WinSalBitmap& rWinSalBitmap)
sal_uInt8* pSource(pRead->mpBits);
sal_uInt8* pDestination(pWrite->mpBits);
- for (long y = 0; y < pRead->mnHeight; y++)
+ std::unique_ptr<ColorScanlineConverter> pConverter;
+
+ if (pRead->mnFormat == ScanlineFormat::N24BitTcRgb)
+ pConverter.reset(new ColorScanlineConverter(ScanlineFormat::N24BitTcRgb, ScanlineFormat::N24BitTcBgr,
+ 3, pRead->mnScanlineSize));
+ else if (pRead->mnFormat == ScanlineFormat::N32BitTcRgba)
+ pConverter.reset(new ColorScanlineConverter(ScanlineFormat::N32BitTcRgba, ScanlineFormat::N32BitTcBgra,
+ 4, pRead->mnScanlineSize));
+ if (pConverter)
+ {
+ for (long y = 0; y < pRead->mnHeight; y++)
+ {
+ pConverter->convertScanline(pSource, pDestination);
+ pSource += pRead->mnScanlineSize;
+ pDestination += pWrite->mnScanlineSize;
+ }
+ }
+ else
{
- memcpy(pDestination, pSource, pRead->mnScanlineSize);
- pSource += pRead->mnScanlineSize;
- pDestination += pWrite->mnScanlineSize;
+ for (long y = 0; y < pRead->mnHeight; y++)
+ {
+ memcpy(pDestination, pSource, pRead->mnScanlineSize);
+ pSource += pRead->mnScanlineSize;
+ pDestination += pWrite->mnScanlineSize;
+ }
}
rWinSalBitmap.ReleaseBuffer(pWrite, BitmapAccessMode::Write);