[Libreoffice-commits] core.git: Branch 'libreoffice-5-0' - vcl/opengl vcl/win

Tomaž Vajngerl tomaz.vajngerl at collabora.com
Mon Dec 14 03:11:15 PST 2015


 vcl/opengl/salbmp.cxx          |  109 ++++++++++++++++++++++++++---------------
 vcl/win/source/gdi/salgdi2.cxx |   72 +++++++++++++++++++++++++--
 2 files changed, 140 insertions(+), 41 deletions(-)

New commits:
commit f625f1e1ff3b557fbe16c281baaf35fdb48eb048
Author: Tomaž Vajngerl <tomaz.vajngerl at collabora.com>
Date:   Thu Dec 10 13:41:36 2015 +0100

    tdf#94851 can't use OpenGLSalBitmap with WinSalGraphics
    
    Printing is done with the WinSalGraphics and not with
    WinOpenGLSalGraphics on Windows even when OpenGL is enabled, but
    the SalBitmap is still using the OpenGLSalBitmap which can't be
    used with WinSalGraphics. So detect when the implementation of
    SalGraphic is "wrong" and convert.
    
    (cherry picked from commit 1cc30679765ce996a009865e6bad3e5b74b96b41)
    
    also includes commit:
    tdf#94851 use BGR color order in Windows
    
    (cherry picked from commit 8a498fad249b3a92f275f33b683f242cb8d68b7b)
    
    and commit:
    tdf#94851 check SalBitmap & convert in all drawBitmap methods
    
    (cherry picked from commit 917d59a84124d1022bd1912874e7a53c674784f1)
    
    Change-Id: I67c730514a8a016c828b5cafdf6e70ddeca450ec
    Reviewed-on: https://gerrit.libreoffice.org/20659
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Caolán McNamara <caolanm at redhat.com>
    Tested-by: Caolán McNamara <caolanm at redhat.com>

diff --git a/vcl/opengl/salbmp.cxx b/vcl/opengl/salbmp.cxx
index cbf60c2..ce03ccf 100644
--- a/vcl/opengl/salbmp.cxx
+++ b/vcl/opengl/salbmp.cxx
@@ -37,6 +37,44 @@
 namespace
 {
 
+inline bool determineTextureFormat(sal_uInt16 nBits, GLenum& nFormat, GLenum& nType)
+{
+    switch(nBits)
+    {
+    case 8:
+        nFormat = GL_LUMINANCE;
+        nType = GL_UNSIGNED_BYTE;
+        return true;
+    case 16:
+#ifdef WNT
+        nFormat = GL_BGR;
+#else
+        nFormat = GL_RGB;
+#endif
+        nType = GL_UNSIGNED_SHORT_5_6_5;
+        return true;
+    case 24:
+#ifdef WNT
+        nFormat = GL_BGR;
+#else
+        nFormat = GL_RGB;
+#endif
+        nType = GL_UNSIGNED_BYTE;
+        return true;
+    case 32:
+#ifdef WNT
+        nFormat = GL_BGRA;
+#else
+        nFormat = GL_RGBA;
+#endif
+        nType = GL_UNSIGNED_BYTE;
+        return true;
+    default:
+        break;
+    }
+    return false;
+}
+
 static bool isValidBitCount( sal_uInt16 nBitCount )
 {
     return (nBitCount == 1) || (nBitCount == 4) || (nBitCount == 8) || (nBitCount == 16) || (nBitCount == 24) || (nBitCount == 32);
@@ -396,18 +434,7 @@ GLuint OpenGLSalBitmap::CreateTexture()
             // no conversion needed for truecolor
             pData = maUserBuffer.get();
 
-            switch( mnBits )
-            {
-            case 16:    nFormat = GL_RGB;
-                        nType = GL_UNSIGNED_SHORT_5_6_5;
-                        break;
-            case 24:    nFormat = GL_RGB;
-                        nType = GL_UNSIGNED_BYTE;
-                        break;
-            case 32:    nFormat = GL_RGBA;
-                        nType = GL_UNSIGNED_BYTE;
-                        break;
-            }
+            determineTextureFormat(mnBits, nFormat, nType);
         }
         else if( mnBits == 8 && maPalette.IsGreyPalette() )
         {
@@ -421,8 +448,8 @@ GLuint OpenGLSalBitmap::CreateTexture()
             // convert to 32 bits RGBA using palette
             pData = new sal_uInt8[mnBufHeight * mnBufWidth * 4];
             bAllocated = true;
-            nFormat = GL_RGBA;
-            nType = GL_UNSIGNED_BYTE;
+
+            determineTextureFormat(32, nFormat, nType);
 
             ImplPixelFormat* pSrcFormat = ImplPixelFormat::GetFormat( mnBits, maPalette );
             sal_uInt8* pSrcData = maUserBuffer.get();
@@ -469,31 +496,18 @@ bool OpenGLSalBitmap::ReadTexture()
 {
     sal_uInt8* pData = maUserBuffer.get();
 
+
     SAL_INFO( "vcl.opengl", "::ReadTexture " << mnWidth << "x" << mnHeight );
 
+    GLenum nFormat = GL_RGBA;
+    GLenum nType = GL_UNSIGNED_BYTE;
+
     if( pData == NULL )
         return false;
 
     if (mnBits == 8 || mnBits == 16 || mnBits == 24 || mnBits == 32)
     {
-        GLenum nFormat = GL_RGBA;
-        GLenum nType = GL_UNSIGNED_BYTE;
-
-        switch( mnBits )
-        {
-        case 8:     nFormat = GL_LUMINANCE;
-                    nType = GL_UNSIGNED_BYTE;
-                    break;
-        case 16:    nFormat = GL_RGB;
-                    nType = GL_UNSIGNED_SHORT_5_6_5;
-                    break;
-        case 24:    nFormat = GL_RGB;
-                    nType = GL_UNSIGNED_BYTE;
-                    break;
-        case 32:    nFormat = GL_RGBA;
-                    nType = GL_UNSIGNED_BYTE;
-                    break;
-        }
+        determineTextureFormat(mnBits, nFormat, nType);
 
         makeCurrent();
         maTexture.Read(nFormat, nType, pData);
@@ -506,7 +520,8 @@ bool OpenGLSalBitmap::ReadTexture()
         std::vector<sal_uInt8> aBuffer(mnWidth * mnHeight * 3);
         makeCurrent();
         sal_uInt8* pBuffer = aBuffer.data();
-        maTexture.Read(GL_RGB, GL_UNSIGNED_BYTE, pBuffer);
+        determineTextureFormat(24, nFormat, nType);
+        maTexture.Read(nFormat, nType, pBuffer);
 
         int nShift = 7;
         size_t nIndex = 0;
@@ -719,12 +734,30 @@ BitmapBuffer* OpenGLSalBitmap::AcquireBuffer( BitmapAccessMode nMode )
     case 1:     pBuffer->mnFormat = BMP_FORMAT_1BIT_MSB_PAL; break;
     case 4:     pBuffer->mnFormat = BMP_FORMAT_4BIT_MSN_PAL; break;
     case 8:     pBuffer->mnFormat = BMP_FORMAT_8BIT_PAL; break;
-    case 16:    pBuffer->mnFormat = BMP_FORMAT_16BIT_TC_MSB_MASK;
-                pBuffer->maColorMask  = ColorMask( 0xf800, 0x07e0, 0x001f );
+    case 16:
+#ifdef WNT
+                pBuffer->mnFormat = BMP_FORMAT_16BIT_TC_MSB_MASK;
+                pBuffer->maColorMask = ColorMask(0x7c00, 0x03e0, 0x001f);
+#else
+                pBuffer->mnFormat = BMP_FORMAT_16BIT_TC_MSB_MASK;
+                pBuffer->maColorMask = ColorMask(0xf800, 0x07e0, 0x001f);
+#endif
+                break;
+    case 24:
+#ifdef WNT
+                pBuffer->mnFormat = BMP_FORMAT_24BIT_TC_BGR;
+#else
+                pBuffer->mnFormat = BMP_FORMAT_24BIT_TC_RGB;
+#endif
                 break;
-    case 24:    pBuffer->mnFormat = BMP_FORMAT_24BIT_TC_RGB; break;
-    case 32:    pBuffer->mnFormat = BMP_FORMAT_32BIT_TC_RGBA;
-                pBuffer->maColorMask  = ColorMask( 0xff000000, 0x00ff0000, 0x0000ff00 );
+    case 32:
+#ifdef WNT
+                pBuffer->mnFormat = BMP_FORMAT_32BIT_TC_BGRA;
+                pBuffer->maColorMask = ColorMask(0x00ff0000, 0x0000ff00, 0x000000ff);
+#else
+                pBuffer->mnFormat = BMP_FORMAT_32BIT_TC_RGBA;
+                pBuffer->maColorMask = ColorMask(0xff000000, 0x00ff0000, 0x0000ff00);
+#endif
                 break;
     }
 
diff --git a/vcl/win/source/gdi/salgdi2.cxx b/vcl/win/source/gdi/salgdi2.cxx
index f009451..dae658d 100644
--- a/vcl/win/source/gdi/salgdi2.cxx
+++ b/vcl/win/source/gdi/salgdi2.cxx
@@ -34,6 +34,8 @@
 #include "vcl/bmpacc.hxx"
 #include "outdata.hxx"
 #include "salgdiimpl.hxx"
+#include "opengl/win/gdiimpl.hxx"
+
 
 bool WinSalGraphics::supportsOperation( OutDevSupportType eType ) const
 {
@@ -69,23 +71,87 @@ void WinSalGraphics::copyArea( long nDestX, long nDestY,
             nSrcWidth, nSrcHeight, nFlags );
 }
 
+namespace
+{
+
+void convertToWinSalBitmap(SalBitmap& rSalBitmap, WinSalBitmap& rWinSalBitmap)
+{
+        BitmapBuffer* pRead = rSalBitmap.AcquireBuffer(BITMAP_READ_ACCESS);
+
+        rWinSalBitmap.Create(rSalBitmap.GetSize(), rSalBitmap.GetBitCount(), BitmapPalette());
+        BitmapBuffer* pWrite = rWinSalBitmap.AcquireBuffer(BITMAP_WRITE_ACCESS);
+
+        sal_uInt8* pSource(pRead->mpBits);
+        sal_uInt8* pDestination(pWrite->mpBits);
+
+        for (long y = 0; y < pRead->mnHeight; y++)
+        {
+            memcpy(pDestination, pSource, pRead->mnScanlineSize);
+            pSource += pRead->mnScanlineSize;
+            pDestination += pWrite->mnScanlineSize;
+        }
+        rWinSalBitmap.ReleaseBuffer(pWrite, BITMAP_WRITE_ACCESS);
+
+        rSalBitmap.ReleaseBuffer(pRead, BITMAP_READ_ACCESS);
+}
+
+} // end anonymous namespace
+
 void WinSalGraphics::drawBitmap(const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap)
 {
-    mpImpl->drawBitmap( rPosAry, rSalBitmap );
+    if (dynamic_cast<WinOpenGLSalGraphicsImpl*>(mpImpl.get()) == nullptr &&
+        dynamic_cast<const WinSalBitmap*>(&rSalBitmap) == nullptr)
+    {
+        std::unique_ptr<WinSalBitmap> pWinSalBitmap(new WinSalBitmap());
+        SalBitmap& rConstBitmap = const_cast<SalBitmap&>(rSalBitmap);
+        convertToWinSalBitmap(rConstBitmap, *pWinSalBitmap.get());
+        mpImpl->drawBitmap(rPosAry, *pWinSalBitmap.get());
+    }
+    else
+    {
+        mpImpl->drawBitmap(rPosAry, rSalBitmap);
+    }
 }
 
 void WinSalGraphics::drawBitmap( const SalTwoRect& rPosAry,
                               const SalBitmap& rSSalBitmap,
                               SalColor nTransparentColor )
 {
-    mpImpl->drawBitmap( rPosAry, rSSalBitmap, nTransparentColor );
+    if (dynamic_cast<WinOpenGLSalGraphicsImpl*>(mpImpl.get()) == nullptr &&
+        dynamic_cast<const WinSalBitmap*>(&rSSalBitmap) == nullptr)
+    {
+        std::unique_ptr<WinSalBitmap> pWinSalBitmap(new WinSalBitmap());
+        SalBitmap& rConstBitmap = const_cast<SalBitmap&>(rSSalBitmap);
+        convertToWinSalBitmap(rConstBitmap, *pWinSalBitmap.get());
+        mpImpl->drawBitmap(rPosAry, *pWinSalBitmap.get(), nTransparentColor);
+    }
+    else
+    {
+        mpImpl->drawBitmap(rPosAry, rSSalBitmap, nTransparentColor);
+    }
 }
 
 void WinSalGraphics::drawBitmap( const SalTwoRect& rPosAry,
                               const SalBitmap& rSSalBitmap,
                               const SalBitmap& rSTransparentBitmap )
 {
-    mpImpl->drawBitmap( rPosAry, rSSalBitmap, rSTransparentBitmap );
+    if (dynamic_cast<WinOpenGLSalGraphicsImpl*>(mpImpl.get()) == nullptr &&
+        dynamic_cast<const WinSalBitmap*>(&rSSalBitmap) == nullptr)
+    {
+        std::unique_ptr<WinSalBitmap> pWinSalBitmap(new WinSalBitmap());
+        SalBitmap& rConstBitmap = const_cast<SalBitmap&>(rSSalBitmap);
+        convertToWinSalBitmap(rConstBitmap, *pWinSalBitmap.get());
+
+        std::unique_ptr<WinSalBitmap> pWinTransparentSalBitmap(new WinSalBitmap());
+        SalBitmap& rConstTransparentBitmap = const_cast<SalBitmap&>(rSTransparentBitmap);
+        convertToWinSalBitmap(rConstTransparentBitmap, *pWinTransparentSalBitmap.get());
+
+        mpImpl->drawBitmap(rPosAry, *pWinSalBitmap.get(), *pWinTransparentSalBitmap.get());
+    }
+    else
+    {
+        mpImpl->drawBitmap(rPosAry, rSSalBitmap, rSTransparentBitmap);
+    }
 }
 
 bool WinSalGraphics::drawAlphaRect( long nX, long nY, long nWidth,


More information about the Libreoffice-commits mailing list