vcl/headless/CairoCommon.cxx                    |  226 ++++++++++++
 vcl/headless/SvpGraphicsBackend.cxx             |  207 -----------
 vcl/inc/headless/CairoCommon.hxx                |   12 
 vcl/unx/generic/app/salinst.cxx                 |    5 
 vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx |   30 +
 vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.hxx |   26 +
 vcl/unx/generic/gdi/gdiimpl.cxx                 |  434 ------------------------
 vcl/unx/generic/gdi/gdiimpl.hxx                 |   36 -
 8 files changed, 299 insertions(+), 677 deletions(-)

New commits:
commit 6d1ba1877ac1e8d77748b238a7706e3a4f8d9ed4
Author:     Caolán McNamara <caol...@redhat.com>
AuthorDate: Tue Jan 10 15:18:40 2023 +0000
Commit:     Caolán McNamara <caol...@redhat.com>
CommitDate: Wed Jan 11 10:33:48 2023 +0000

    use SvpSalBitmap for X11/gen also
    
    and move bitmap draw/get into CairoCommon and reuse from
    X11CairoSalGraphicsImpl
    
    Change-Id: Ic1faf85b78a298e603279e6d318bab9240d67e77
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/145288
    Tested-by: Jenkins
    Reviewed-by: Caolán McNamara <caol...@redhat.com>

diff --git a/vcl/headless/CairoCommon.cxx b/vcl/headless/CairoCommon.cxx
index 6552460cf5e6..0aaefff4ef52 100644
--- a/vcl/headless/CairoCommon.cxx
+++ b/vcl/headless/CairoCommon.cxx
@@ -17,6 +17,7 @@
  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
  */
 
+#include <headless/BitmapHelper.hxx>
 #include <headless/CairoCommon.hxx>
 #include <dlfcn.h>
 #include <vcl/BitmapTools.hxx>
@@ -1584,6 +1585,229 @@ void CairoCommon::invert(sal_uInt32 nPoints, const 
Point* pPtAry, SalInvert nFla
     invert(aPoly, nFlags, bAntiAlias);
 }
 
+void CairoCommon::drawBitmap(const SalTwoRect& rPosAry, const SalBitmap& 
rSalBitmap,
+                             bool bAntiAlias)
+{
+    // MM02 try to access buffered BitmapHelper
+    std::shared_ptr<BitmapHelper> aSurface;
+    tryToUseSourceBuffer(rSalBitmap, aSurface);
+    cairo_surface_t* source = aSurface->getSurface(rPosAry.mnDestWidth, 
rPosAry.mnDestHeight);
+
+    if (!source)
+    {
+        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
+        return;
+    }
+
+#if 0 // LO code is not yet bitmap32-ready.
+    // if m_bSupportsBitmap32 becomes true for Svp revisit this
+    copyWithOperator(rPosAry, source, CAIRO_OPERATOR_OVER, bAntiAlias);
+#else
+    copyWithOperator(rPosAry, source, CAIRO_OPERATOR_SOURCE, bAntiAlias);
+#endif
+}
+
+bool CairoCommon::drawAlphaBitmap(const SalTwoRect& rTR, const SalBitmap& 
rSourceBitmap,
+                                  const SalBitmap& rAlphaBitmap, bool 
bAntiAlias)
+{
+    if (rAlphaBitmap.GetBitCount() != 8 && rAlphaBitmap.GetBitCount() != 1)
+    {
+        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap alpha 
depth case: "
+                                << rAlphaBitmap.GetBitCount());
+        return false;
+    }
+
+    if (!rTR.mnSrcWidth || !rTR.mnSrcHeight)
+    {
+        SAL_WARN("vcl.gdi", "not possible to stretch nothing");
+        return true;
+    }
+
+    // MM02 try to access buffered BitmapHelper
+    std::shared_ptr<BitmapHelper> aSurface;
+    tryToUseSourceBuffer(rSourceBitmap, aSurface);
+    cairo_surface_t* source = aSurface->getSurface(rTR.mnDestWidth, 
rTR.mnDestHeight);
+
+    if (!source)
+    {
+        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
+        return false;
+    }
+
+    // MM02 try to access buffered MaskHelper
+    std::shared_ptr<MaskHelper> aMask;
+    tryToUseMaskBuffer(rAlphaBitmap, aMask);
+    cairo_surface_t* mask = aMask->getSurface(rTR.mnDestWidth, 
rTR.mnDestHeight);
+
+    if (!mask)
+    {
+        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
+        return false;
+    }
+
+    cairo_t* cr = getCairoContext(false, bAntiAlias);
+    clipRegion(cr);
+
+    cairo_rectangle(cr, rTR.mnDestX, rTR.mnDestY, rTR.mnDestWidth, 
rTR.mnDestHeight);
+
+    basegfx::B2DRange extents = getClippedFillDamage(cr);
+
+    cairo_clip(cr);
+
+    cairo_pattern_t* maskpattern = cairo_pattern_create_for_surface(mask);
+    cairo_translate(cr, rTR.mnDestX, rTR.mnDestY);
+    double fXScale = static_cast<double>(rTR.mnDestWidth) / rTR.mnSrcWidth;
+    double fYScale = static_cast<double>(rTR.mnDestHeight) / rTR.mnSrcHeight;
+    cairo_scale(cr, fXScale, fYScale);
+    cairo_set_source_surface(cr, source, -rTR.mnSrcX, -rTR.mnSrcY);
+
+    cairo_pattern_t* sourcepattern = cairo_get_source(cr);
+
+    //tdf#133716 borders of upscaled images should not be blurred
+    //tdf#114117 when stretching a single or multi pixel width/height source 
to fit an area
+    //the image will be extended into that size.
+    cairo_pattern_set_extend(sourcepattern, CAIRO_EXTEND_PAD);
+    cairo_pattern_set_extend(maskpattern, CAIRO_EXTEND_PAD);
+
+    //this block is just "cairo_mask_surface", but we have to make it explicit
+    //because of the cairo_pattern_set_filter etc we may want applied
+    cairo_matrix_t matrix;
+    cairo_matrix_init_translate(&matrix, rTR.mnSrcX, rTR.mnSrcY);
+    cairo_pattern_set_matrix(maskpattern, &matrix);
+    cairo_mask(cr, maskpattern);
+
+    cairo_pattern_destroy(maskpattern);
+
+    releaseCairoContext(cr, false, extents);
+
+    return true;
+}
+
+void CairoCommon::drawMask(const SalTwoRect& rTR, const SalBitmap& rSalBitmap, 
Color nMaskColor,
+                           bool bAntiAlias)
+{
+    /** creates an image from the given rectangle, replacing all black pixels
+     *  with nMaskColor and make all other full transparent */
+    // MM02 here decided *against* using buffered BitmapHelper
+    // because the data gets somehow 'unmuliplied'. This may also be
+    // done just once, but I am not sure if this is safe to do.
+    // So for now dispense re-using data here.
+    BitmapHelper aSurface(rSalBitmap, true); // The mask is argb32
+    if (!aSurface.getSurface())
+    {
+        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawMask case");
+        return;
+    }
+    sal_Int32 nStride;
+    unsigned char* mask_data = aSurface.getBits(nStride);
+#if !ENABLE_WASM_STRIP_PREMULTIPLY
+    vcl::bitmap::lookup_table const& unpremultiply_table = 
vcl::bitmap::get_unpremultiply_table();
+#endif
+    for (tools::Long y = rTR.mnSrcY; y < rTR.mnSrcY + rTR.mnSrcHeight; ++y)
+    {
+        unsigned char* row = mask_data + (nStride * y);
+        unsigned char* data = row + (rTR.mnSrcX * 4);
+        for (tools::Long x = rTR.mnSrcX; x < rTR.mnSrcX + rTR.mnSrcWidth; ++x)
+        {
+            sal_uInt8 a = data[SVP_CAIRO_ALPHA];
+#if ENABLE_WASM_STRIP_PREMULTIPLY
+            sal_uInt8 b = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_BLUE]);
+            sal_uInt8 g = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_GREEN]);
+            sal_uInt8 r = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_RED]);
+#else
+            sal_uInt8 b = unpremultiply_table[a][data[SVP_CAIRO_BLUE]];
+            sal_uInt8 g = unpremultiply_table[a][data[SVP_CAIRO_GREEN]];
+            sal_uInt8 r = unpremultiply_table[a][data[SVP_CAIRO_RED]];
+#endif
+            if (r == 0 && g == 0 && b == 0)
+            {
+                data[0] = nMaskColor.GetBlue();
+                data[1] = nMaskColor.GetGreen();
+                data[2] = nMaskColor.GetRed();
+                data[3] = 0xff;
+            }
+            else
+            {
+                data[0] = 0;
+                data[1] = 0;
+                data[2] = 0;
+                data[3] = 0;
+            }
+            data += 4;
+        }
+    }
+    aSurface.mark_dirty();
+
+    cairo_t* cr = getCairoContext(false, bAntiAlias);
+    clipRegion(cr);
+
+    cairo_rectangle(cr, rTR.mnDestX, rTR.mnDestY, rTR.mnDestWidth, 
rTR.mnDestHeight);
+
+    basegfx::B2DRange extents = getClippedFillDamage(cr);
+
+    cairo_clip(cr);
+
+    cairo_translate(cr, rTR.mnDestX, rTR.mnDestY);
+    double fXScale = static_cast<double>(rTR.mnDestWidth) / rTR.mnSrcWidth;
+    double fYScale = static_cast<double>(rTR.mnDestHeight) / rTR.mnSrcHeight;
+    cairo_scale(cr, fXScale, fYScale);
+    cairo_set_source_surface(cr, aSurface.getSurface(), -rTR.mnSrcX, 
-rTR.mnSrcY);
+
+    if (cairo_status(cr) == CAIRO_STATUS_SUCCESS)
+    {
+        //tdf#133716 borders of upscaled images should not be blurred
+        cairo_pattern_t* sourcepattern = cairo_get_source(cr);
+        cairo_pattern_set_extend(sourcepattern, CAIRO_EXTEND_PAD);
+    }
+
+    cairo_paint(cr);
+
+    releaseCairoContext(cr, false, extents);
+}
+
+std::shared_ptr<SalBitmap> CairoCommon::getBitmap(tools::Long nX, tools::Long 
nY,
+                                                  tools::Long nWidth, 
tools::Long nHeight)
+{
+    std::shared_ptr<SvpSalBitmap> pBitmap = std::make_shared<SvpSalBitmap>();
+    BitmapPalette aPal;
+    vcl::PixelFormat ePixelFormat = vcl::PixelFormat::INVALID;
+    if (GetBitCount() == 1)
+    {
+        ePixelFormat = vcl::PixelFormat::N1_BPP;
+        aPal.SetEntryCount(2);
+        aPal[0] = COL_BLACK;
+        aPal[1] = COL_WHITE;
+    }
+    else
+    {
+        ePixelFormat = vcl::PixelFormat::N32_BPP;
+    }
+
+    if (!pBitmap->Create(Size(nWidth, nHeight), ePixelFormat, aPal))
+    {
+        SAL_WARN("vcl.gdi", "SvpSalGraphics::getBitmap, cannot create bitmap");
+        return nullptr;
+    }
+
+    cairo_surface_t* target = 
CairoCommon::createCairoSurface(pBitmap->GetBuffer());
+    if (!target)
+    {
+        SAL_WARN("vcl.gdi", "SvpSalGraphics::getBitmap, cannot create cairo 
surface");
+        return nullptr;
+    }
+    cairo_t* cr = cairo_create(target);
+
+    SalTwoRect aTR(nX, nY, nWidth, nHeight, 0, 0, nWidth, nHeight);
+    CairoCommon::renderSource(cr, aTR, m_pSurface);
+
+    cairo_destroy(cr);
+    cairo_surface_destroy(target);
+
+    Toggle1BitTransparency(*pBitmap->GetBuffer());
+
+    return pBitmap;
+}
+
 cairo_format_t getCairoFormat(const BitmapBuffer& rBuffer)
 {
     cairo_format_t nFormat;
diff --git a/vcl/headless/SvpGraphicsBackend.cxx 
b/vcl/headless/SvpGraphicsBackend.cxx
index f6674925815e..0f053bb28c17 100644
--- a/vcl/headless/SvpGraphicsBackend.cxx
+++ b/vcl/headless/SvpGraphicsBackend.cxx
@@ -177,23 +177,7 @@ void SvpGraphicsBackend::copyBits(const SalTwoRect& rTR, 
SalGraphics* pSrcGraphi
 
 void SvpGraphicsBackend::drawBitmap(const SalTwoRect& rPosAry, const 
SalBitmap& rSalBitmap)
 {
-    // MM02 try to access buffered BitmapHelper
-    std::shared_ptr<BitmapHelper> aSurface;
-    tryToUseSourceBuffer(rSalBitmap, aSurface);
-    cairo_surface_t* source = aSurface->getSurface(rPosAry.mnDestWidth, 
rPosAry.mnDestHeight);
-
-    if (!source)
-    {
-        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
-        return;
-    }
-
-#if 0 // LO code is not yet bitmap32-ready.
-    // if m_bSupportsBitmap32 becomes true for Svp revisit this
-    m_rCairoCommon.copyWithOperator(rPosAry, source, CAIRO_OPERATOR_OVER, 
getAntiAlias());
-#else
-    m_rCairoCommon.copyWithOperator(rPosAry, source, CAIRO_OPERATOR_SOURCE, 
getAntiAlias());
-#endif
+    m_rCairoCommon.drawBitmap(rPosAry, rSalBitmap, getAntiAlias());
 }
 
 void SvpGraphicsBackend::drawBitmap(const SalTwoRect& rPosAry, const 
SalBitmap& rSalBitmap,
@@ -205,126 +189,13 @@ void SvpGraphicsBackend::drawBitmap(const SalTwoRect& 
rPosAry, const SalBitmap&
 void SvpGraphicsBackend::drawMask(const SalTwoRect& rTR, const SalBitmap& 
rSalBitmap,
                                   Color nMaskColor)
 {
-    /** creates an image from the given rectangle, replacing all black pixels
-     *  with nMaskColor and make all other full transparent */
-    // MM02 here decided *against* using buffered BitmapHelper
-    // because the data gets somehow 'unmuliplied'. This may also be
-    // done just once, but I am not sure if this is safe to do.
-    // So for now dispense re-using data here.
-    BitmapHelper aSurface(rSalBitmap, true); // The mask is argb32
-    if (!aSurface.getSurface())
-    {
-        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawMask case");
-        return;
-    }
-    sal_Int32 nStride;
-    unsigned char* mask_data = aSurface.getBits(nStride);
-#if !ENABLE_WASM_STRIP_PREMULTIPLY
-    vcl::bitmap::lookup_table const& unpremultiply_table = 
vcl::bitmap::get_unpremultiply_table();
-#endif
-    for (tools::Long y = rTR.mnSrcY; y < rTR.mnSrcY + rTR.mnSrcHeight; ++y)
-    {
-        unsigned char* row = mask_data + (nStride * y);
-        unsigned char* data = row + (rTR.mnSrcX * 4);
-        for (tools::Long x = rTR.mnSrcX; x < rTR.mnSrcX + rTR.mnSrcWidth; ++x)
-        {
-            sal_uInt8 a = data[SVP_CAIRO_ALPHA];
-#if ENABLE_WASM_STRIP_PREMULTIPLY
-            sal_uInt8 b = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_BLUE]);
-            sal_uInt8 g = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_GREEN]);
-            sal_uInt8 r = vcl::bitmap::unpremultiply(a, data[SVP_CAIRO_RED]);
-#else
-            sal_uInt8 b = unpremultiply_table[a][data[SVP_CAIRO_BLUE]];
-            sal_uInt8 g = unpremultiply_table[a][data[SVP_CAIRO_GREEN]];
-            sal_uInt8 r = unpremultiply_table[a][data[SVP_CAIRO_RED]];
-#endif
-            if (r == 0 && g == 0 && b == 0)
-            {
-                data[0] = nMaskColor.GetBlue();
-                data[1] = nMaskColor.GetGreen();
-                data[2] = nMaskColor.GetRed();
-                data[3] = 0xff;
-            }
-            else
-            {
-                data[0] = 0;
-                data[1] = 0;
-                data[2] = 0;
-                data[3] = 0;
-            }
-            data += 4;
-        }
-    }
-    aSurface.mark_dirty();
-
-    cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias());
-    m_rCairoCommon.clipRegion(cr);
-
-    cairo_rectangle(cr, rTR.mnDestX, rTR.mnDestY, rTR.mnDestWidth, 
rTR.mnDestHeight);
-
-    basegfx::B2DRange extents = getClippedFillDamage(cr);
-
-    cairo_clip(cr);
-
-    cairo_translate(cr, rTR.mnDestX, rTR.mnDestY);
-    double fXScale = static_cast<double>(rTR.mnDestWidth) / rTR.mnSrcWidth;
-    double fYScale = static_cast<double>(rTR.mnDestHeight) / rTR.mnSrcHeight;
-    cairo_scale(cr, fXScale, fYScale);
-    cairo_set_source_surface(cr, aSurface.getSurface(), -rTR.mnSrcX, 
-rTR.mnSrcY);
-
-    if (cairo_status(cr) == CAIRO_STATUS_SUCCESS)
-    {
-        //tdf#133716 borders of upscaled images should not be blurred
-        cairo_pattern_t* sourcepattern = cairo_get_source(cr);
-        cairo_pattern_set_extend(sourcepattern, CAIRO_EXTEND_PAD);
-    }
-
-    cairo_paint(cr);
-
-    m_rCairoCommon.releaseCairoContext(cr, false, extents);
+    m_rCairoCommon.drawMask(rTR, rSalBitmap, nMaskColor, getAntiAlias());
 }
 
 std::shared_ptr<SalBitmap> SvpGraphicsBackend::getBitmap(tools::Long nX, 
tools::Long nY,
                                                          tools::Long nWidth, 
tools::Long nHeight)
 {
-    std::shared_ptr<SvpSalBitmap> pBitmap = std::make_shared<SvpSalBitmap>();
-    BitmapPalette aPal;
-    vcl::PixelFormat ePixelFormat = vcl::PixelFormat::INVALID;
-    if (GetBitCount() == 1)
-    {
-        ePixelFormat = vcl::PixelFormat::N1_BPP;
-        aPal.SetEntryCount(2);
-        aPal[0] = COL_BLACK;
-        aPal[1] = COL_WHITE;
-    }
-    else
-    {
-        ePixelFormat = vcl::PixelFormat::N32_BPP;
-    }
-
-    if (!pBitmap->Create(Size(nWidth, nHeight), ePixelFormat, aPal))
-    {
-        SAL_WARN("vcl.gdi", "SvpSalGraphics::getBitmap, cannot create bitmap");
-        return nullptr;
-    }
-
-    cairo_surface_t* target = 
CairoCommon::createCairoSurface(pBitmap->GetBuffer());
-    if (!target)
-    {
-        SAL_WARN("vcl.gdi", "SvpSalGraphics::getBitmap, cannot create cairo 
surface");
-        return nullptr;
-    }
-    cairo_t* cr = cairo_create(target);
-
-    SalTwoRect aTR(nX, nY, nWidth, nHeight, 0, 0, nWidth, nHeight);
-    CairoCommon::renderSource(cr, aTR, m_rCairoCommon.m_pSurface);
-
-    cairo_destroy(cr);
-    cairo_surface_destroy(target);
-
-    Toggle1BitTransparency(*pBitmap->GetBuffer());
-
-    return pBitmap;
+    return m_rCairoCommon.getBitmap(nX, nY, nWidth, nHeight);
 }
 
 void SvpGraphicsBackend::drawBitmapBuffer(const SalTwoRect& rTR, const 
BitmapBuffer* pBuffer,
@@ -373,77 +244,7 @@ bool SvpGraphicsBackend::blendAlphaBitmap(const 
SalTwoRect& /*rPosAry*/,
 bool SvpGraphicsBackend::drawAlphaBitmap(const SalTwoRect& rTR, const 
SalBitmap& rSourceBitmap,
                                          const SalBitmap& rAlphaBitmap)
 {
-    if (rAlphaBitmap.GetBitCount() != 8 && rAlphaBitmap.GetBitCount() != 1)
-    {
-        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap alpha 
depth case: "
-                                << rAlphaBitmap.GetBitCount());
-        return false;
-    }
-
-    if (!rTR.mnSrcWidth || !rTR.mnSrcHeight)
-    {
-        SAL_WARN("vcl.gdi", "not possible to stretch nothing");
-        return true;
-    }
-
-    // MM02 try to access buffered BitmapHelper
-    std::shared_ptr<BitmapHelper> aSurface;
-    tryToUseSourceBuffer(rSourceBitmap, aSurface);
-    cairo_surface_t* source = aSurface->getSurface(rTR.mnDestWidth, 
rTR.mnDestHeight);
-
-    if (!source)
-    {
-        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
-        return false;
-    }
-
-    // MM02 try to access buffered MaskHelper
-    std::shared_ptr<MaskHelper> aMask;
-    tryToUseMaskBuffer(rAlphaBitmap, aMask);
-    cairo_surface_t* mask = aMask->getSurface(rTR.mnDestWidth, 
rTR.mnDestHeight);
-
-    if (!mask)
-    {
-        SAL_WARN("vcl.gdi", "unsupported SvpSalGraphics::drawAlphaBitmap 
case");
-        return false;
-    }
-
-    cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias());
-    m_rCairoCommon.clipRegion(cr);
-
-    cairo_rectangle(cr, rTR.mnDestX, rTR.mnDestY, rTR.mnDestWidth, 
rTR.mnDestHeight);
-
-    basegfx::B2DRange extents = getClippedFillDamage(cr);
-
-    cairo_clip(cr);
-
-    cairo_pattern_t* maskpattern = cairo_pattern_create_for_surface(mask);
-    cairo_translate(cr, rTR.mnDestX, rTR.mnDestY);
-    double fXScale = static_cast<double>(rTR.mnDestWidth) / rTR.mnSrcWidth;
-    double fYScale = static_cast<double>(rTR.mnDestHeight) / rTR.mnSrcHeight;
-    cairo_scale(cr, fXScale, fYScale);
-    cairo_set_source_surface(cr, source, -rTR.mnSrcX, -rTR.mnSrcY);
-
-    cairo_pattern_t* sourcepattern = cairo_get_source(cr);
-
-    //tdf#133716 borders of upscaled images should not be blurred
-    //tdf#114117 when stretching a single or multi pixel width/height source 
to fit an area
-    //the image will be extended into that size.
-    cairo_pattern_set_extend(sourcepattern, CAIRO_EXTEND_PAD);
-    cairo_pattern_set_extend(maskpattern, CAIRO_EXTEND_PAD);
-
-    //this block is just "cairo_mask_surface", but we have to make it explicit
-    //because of the cairo_pattern_set_filter etc we may want applied
-    cairo_matrix_t matrix;
-    cairo_matrix_init_translate(&matrix, rTR.mnSrcX, rTR.mnSrcY);
-    cairo_pattern_set_matrix(maskpattern, &matrix);
-    cairo_mask(cr, maskpattern);
-
-    cairo_pattern_destroy(maskpattern);
-
-    m_rCairoCommon.releaseCairoContext(cr, false, extents);
-
-    return true;
+    return m_rCairoCommon.drawAlphaBitmap(rTR, rSourceBitmap, rAlphaBitmap, 
getAntiAlias());
 }
 
 bool SvpGraphicsBackend::drawTransformedBitmap(const basegfx::B2DPoint& rNull,
diff --git a/vcl/inc/headless/CairoCommon.hxx b/vcl/inc/headless/CairoCommon.hxx
index 733118fbd0c0..4cbe1af538ba 100644
--- a/vcl/inc/headless/CairoCommon.hxx
+++ b/vcl/inc/headless/CairoCommon.hxx
@@ -47,6 +47,7 @@ typedef struct _cairo_surface cairo_surface_t;
 typedef struct _cairo_user_data_key cairo_user_data_key_t;
 
 class Gradient;
+class SalBitmap;
 struct SalGradient;
 
 VCL_DLLPUBLIC void dl_cairo_surface_set_device_scale(cairo_surface_t* surface, 
double x_scale,
@@ -211,6 +212,17 @@ struct VCL_DLLPUBLIC CairoCommon
 
     void invert(sal_uInt32 nPoints, const Point* pPtAry, SalInvert nFlags, 
bool bAntiAlias);
 
+    void drawBitmap(const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap, 
bool bAntiAlias);
+
+    bool drawAlphaBitmap(const SalTwoRect& rTR, const SalBitmap& rSourceBitmap,
+                         const SalBitmap& rAlphaBitmap, bool bAntiAlias);
+
+    void drawMask(const SalTwoRect& rTR, const SalBitmap& rSalBitmap, Color 
nMaskColor,
+                  bool bAntiAlias);
+
+    std::shared_ptr<SalBitmap> getBitmap(tools::Long nX, tools::Long nY, 
tools::Long nWidth,
+                                         tools::Long nHeight);
+
     static cairo_surface_t* createCairoSurface(const BitmapBuffer* pBuffer);
 
     static bool supportsOperation(OutDevSupportType eType);
diff --git a/vcl/unx/generic/app/salinst.cxx b/vcl/unx/generic/app/salinst.cxx
index 502f4c7f7ec2..a77aca26482d 100644
--- a/vcl/unx/generic/app/salinst.cxx
+++ b/vcl/unx/generic/app/salinst.cxx
@@ -27,6 +27,7 @@
 #include <skia/salbmp.hxx>
 #endif
 
+#include <headless/svpbmp.hxx>
 #include <unx/saldata.hxx>
 #include <unx/saldisp.hxx>
 #include <unx/salinst.h>
@@ -35,7 +36,6 @@
 #include <unx/salframe.h>
 #include <unx/sm.hxx>
 #include <unx/i18n_im.hxx>
-#include <unx/salbmp.h>
 
 #include <vcl/inputtypes.hxx>
 
@@ -246,9 +246,8 @@ std::shared_ptr<SalBitmap> X11SalInstance::CreateSalBitmap()
 #if HAVE_FEATURE_SKIA
     if (SkiaHelper::isVCLSkiaEnabled())
         return std::make_shared<SkiaSalBitmap>();
-    else
 #endif
-        return std::make_shared<X11SalBitmap>();
+    return std::make_shared<SvpSalBitmap>();
 }
 
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx 
b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx
index d703a5e5c93f..5a2e5c99ca20 100644
--- a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx
+++ b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx
@@ -159,6 +159,36 @@ void X11CairoSalGraphicsImpl::copyBits(const SalTwoRect& 
rTR, SalGraphics* pSrcG
     mrCairoCommon.copyBitsCairo(rTR, source, getAntiAlias());
 }
 
+void X11CairoSalGraphicsImpl::drawBitmap(const SalTwoRect& rPosAry, const 
SalBitmap& rSalBitmap)
+{
+    mrCairoCommon.drawBitmap(rPosAry, rSalBitmap, getAntiAlias());
+}
+
+void X11CairoSalGraphicsImpl::drawBitmap(const SalTwoRect& rPosAry, const 
SalBitmap& rSalBitmap,
+                                         const SalBitmap& rTransparentBitmap)
+{
+    drawAlphaBitmap(rPosAry, rSalBitmap, rTransparentBitmap);
+}
+
+bool X11CairoSalGraphicsImpl::drawAlphaBitmap(const SalTwoRect& rTR, const 
SalBitmap& rSrcBitmap,
+                                              const SalBitmap& rAlphaBmp)
+{
+    return mrCairoCommon.drawAlphaBitmap(rTR, rSrcBitmap, rAlphaBmp, 
getAntiAlias());
+}
+
+void X11CairoSalGraphicsImpl::drawMask(const SalTwoRect& rTR, const SalBitmap& 
rSalBitmap,
+                                       Color nMaskColor)
+{
+    mrCairoCommon.drawMask(rTR, rSalBitmap, nMaskColor, getAntiAlias());
+}
+
+std::shared_ptr<SalBitmap> X11CairoSalGraphicsImpl::getBitmap(tools::Long nX, 
tools::Long nY,
+                                                              tools::Long 
nWidth,
+                                                              tools::Long 
nHeight)
+{
+    return mrCairoCommon.getBitmap(nX, nY, nWidth, nHeight);
+}
+
 bool X11CairoSalGraphicsImpl::drawPolyLineBezier(sal_uInt32, const Point*, 
const PolyFlags*)
 {
     return false;
diff --git a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.hxx 
b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.hxx
index 49b60f4c05c4..3dcc628cf333 100644
--- a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.hxx
+++ b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.hxx
@@ -124,6 +124,32 @@ public:
     // CopyBits() --> pSrcGraphics == NULL, then CopyBits on same Graphics
     void copyBits(const SalTwoRect& rPosAry, SalGraphics* pSrcGraphics) 
override;
 
+    void drawBitmap(const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap) 
override;
+
+    void drawBitmap(const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap,
+                    const SalBitmap& rMaskBitmap) override;
+
+    /** Render bitmap with alpha channel
+
+        @param rSourceBitmap
+        Source bitmap to blit
+
+        @param rAlphaBitmap
+        Alpha channel to use for blitting
+
+        @return true, if the operation succeeded, and false
+        otherwise. In this case, clients should try to emulate alpha
+        compositing themselves
+     */
+    bool drawAlphaBitmap(const SalTwoRect&, const SalBitmap& rSourceBitmap,
+                         const SalBitmap& rAlphaBitmap) override;
+
+    void drawMask(const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap,
+                  Color nMaskColor) override;
+
+    std::shared_ptr<SalBitmap> getBitmap(tools::Long nX, tools::Long nY, 
tools::Long nWidth,
+                                         tools::Long nHeight) override;
+
     bool drawPolyLineBezier(sal_uInt32 nPoints, const Point* pPtAry,
                             const PolyFlags* pFlgAry) override;
 
diff --git a/vcl/unx/generic/gdi/gdiimpl.cxx b/vcl/unx/generic/gdi/gdiimpl.cxx
index 5413c2b69980..31327437852b 100644
--- a/vcl/unx/generic/gdi/gdiimpl.cxx
+++ b/vcl/unx/generic/gdi/gdiimpl.cxx
@@ -49,50 +49,9 @@
 #include <basegfx/polygon/b2dtrapezoid.hxx>
 #include <basegfx/utils/systemdependentdata.hxx>
 
-#undef SALGDI2_TESTTRANS
-
-#if (OSL_DEBUG_LEVEL > 1) && defined SALGDI2_TESTTRANS
-#define DBG_TESTTRANS( _def_drawable )                              \
-{                                                                   \
-    XCopyArea( pXDisp, _def_drawable, aDrawable, GetCopyGC(),       \
-               0, 0,                                                \
-               rPosAry.mnDestWidth, rPosAry.mnDestHeight,         \
-               0, 0 );                                              \
-}
-#else // (OSL_DEBUG_LEVEL > 1) && defined SALGDI2_TESTTRANS
-#define DBG_TESTTRANS( _def_drawable )
-#endif // (OSL_DEBUG_LEVEL > 1) && defined SALGDI2_TESTTRANS
-
 /* From <X11/Intrinsic.h> */
 typedef unsigned long Pixel;
 
-namespace
-{
-    void setForeBack(XGCValues& rValues, const SalColormap& rColMap, const 
SalBitmap& rSalBitmap)
-    {
-        rValues.foreground = rColMap.GetWhitePixel();
-        rValues.background = rColMap.GetBlackPixel();
-
-        //fdo#33455 and fdo#80160 handle 1 bit depth pngs with palette entries
-        //to set fore/back colors
-        SalBitmap& rBitmap = const_cast<SalBitmap&>(rSalBitmap);
-        BitmapBuffer* pBitmapBuffer = 
rBitmap.AcquireBuffer(BitmapAccessMode::Read);
-        if (!pBitmapBuffer)
-            return;
-
-        const BitmapPalette& rPalette = pBitmapBuffer->maPalette;
-        if (rPalette.GetEntryCount() == 2)
-        {
-            const BitmapColor 
aWhite(rPalette[rPalette.GetBestIndex(COL_WHITE)]);
-            rValues.foreground = rColMap.GetPixel(aWhite);
-
-            const BitmapColor 
aBlack(rPalette[rPalette.GetBestIndex(COL_BLACK)]);
-            rValues.background = rColMap.GetPixel(aBlack);
-        }
-        rBitmap.ReleaseBuffer(pBitmapBuffer, BitmapAccessMode::Read);
-    }
-}
-
 X11SalGraphicsImpl::X11SalGraphicsImpl(X11SalGraphics& rParent):
     mrParent(rParent),
     mbCopyGC(false),
@@ -223,325 +182,6 @@ inline GC X11SalGraphicsImpl::GetStippleGC()
     return mpStippleGC;
 }
 
-void X11SalGraphicsImpl::drawBitmap( const SalTwoRect& rPosAry, const 
SalBitmap& rSalBitmap )
-{
-    const SalDisplay*   pSalDisp = mrParent.GetDisplay();
-    Display*            pXDisp = pSalDisp->GetDisplay();
-    const Drawable      aDrawable( mrParent.GetDrawable() );
-    const SalColormap&  rColMap = pSalDisp->GetColormap( mrParent.m_nXScreen );
-    const tools::Long          nDepth = mrParent.GetDisplay()->GetVisual( 
mrParent.m_nXScreen ).GetDepth();
-    GC                  aGC( GetCopyGC() );
-    XGCValues           aOldVal, aNewVal;
-    int                 nValues = GCForeground | GCBackground;
-
-    if( rSalBitmap.GetBitCount() == 1 )
-    {
-        // set foreground/background values for 1Bit bitmaps
-        XGetGCValues( pXDisp, aGC, nValues, &aOldVal );
-        setForeBack(aNewVal, rColMap, rSalBitmap);
-        XChangeGC( pXDisp, aGC, nValues, &aNewVal );
-    }
-
-    static_cast<const X11SalBitmap&>(rSalBitmap).ImplDraw( aDrawable, 
mrParent.m_nXScreen, nDepth, rPosAry, aGC );
-
-    if( rSalBitmap.GetBitCount() == 1 )
-        XChangeGC( pXDisp, aGC, nValues, &aOldVal );
-    XFlush( pXDisp );
-}
-
-void X11SalGraphicsImpl::drawBitmap( const SalTwoRect& rPosAry,
-                                 const SalBitmap& rSrcBitmap,
-                                 const SalBitmap& rMaskBitmap )
-{
-    // decide if alpha masking or transparency masking is needed
-    BitmapBuffer* pAlphaBuffer = 
const_cast<SalBitmap&>(rMaskBitmap).AcquireBuffer( BitmapAccessMode::Read );
-    if( pAlphaBuffer != nullptr )
-    {
-        ScanlineFormat nMaskFormat = pAlphaBuffer->mnFormat;
-        const_cast<SalBitmap&>(rMaskBitmap).ReleaseBuffer( pAlphaBuffer, 
BitmapAccessMode::Read );
-        if( nMaskFormat == ScanlineFormat::N8BitPal )
-            drawAlphaBitmap( rPosAry, rSrcBitmap, rMaskBitmap );
-    }
-
-    drawMaskedBitmap( rPosAry, rSrcBitmap, rMaskBitmap );
-}
-
-void X11SalGraphicsImpl::drawMaskedBitmap( const SalTwoRect& rPosAry,
-                                       const SalBitmap& rSalBitmap,
-                                       const SalBitmap& rTransBitmap )
-{
-    const SalDisplay*   pSalDisp = mrParent.GetDisplay();
-    Display*            pXDisp = pSalDisp->GetDisplay();
-    Drawable            aDrawable( mrParent.GetDrawable() );
-
-    // figure work mode depth. If this is a VDev Drawable, use its
-    // bitdepth to create pixmaps for, otherwise, XCopyArea will
-    // refuse to work.
-    const sal_uInt16    nDepth( mrParent.m_pVDev ?
-                            static_cast< X11SalVirtualDevice* 
>(mrParent.m_pVDev)->GetDepth() :
-                            pSalDisp->GetVisual( mrParent.m_nXScreen 
).GetDepth() );
-    Pixmap          aFG( limitXCreatePixmap( pXDisp, aDrawable, 
rPosAry.mnDestWidth,
-                                        rPosAry.mnDestHeight, nDepth ) );
-    Pixmap          aBG( limitXCreatePixmap( pXDisp, aDrawable, 
rPosAry.mnDestWidth,
-                                        rPosAry.mnDestHeight, nDepth ) );
-
-    if( aFG && aBG )
-    {
-        GC                  aTmpGC;
-        XGCValues           aValues;
-        setForeBack(aValues, pSalDisp->GetColormap(mrParent.m_nXScreen), 
rSalBitmap);
-        const int           nValues = GCFunction | GCForeground | GCBackground;
-        SalTwoRect          aTmpRect( rPosAry ); aTmpRect.mnDestX = 
aTmpRect.mnDestY = 0;
-
-        // draw paint bitmap in pixmap #1
-        aValues.function = GXcopy;
-        aTmpGC = XCreateGC( pXDisp, aFG, nValues, &aValues );
-        static_cast<const X11SalBitmap&>(rSalBitmap).ImplDraw( aFG, 
mrParent.m_nXScreen, nDepth, aTmpRect, aTmpGC );
-        DBG_TESTTRANS( aFG );
-
-        // draw background in pixmap #2
-        XCopyArea( pXDisp, aDrawable, aBG, aTmpGC,
-                   rPosAry.mnDestX, rPosAry.mnDestY,
-                   rPosAry.mnDestWidth, rPosAry.mnDestHeight,
-                   0, 0 );
-
-        DBG_TESTTRANS( aBG );
-
-        // mask out paint bitmap in pixmap #1 (transparent areas 0)
-        aValues.function = GXand;
-        aValues.foreground = 0x00000000;
-        aValues.background = 0xffffffff;
-        XChangeGC( pXDisp, aTmpGC, nValues, &aValues );
-        static_cast<const X11SalBitmap&>(rTransBitmap).ImplDraw( aFG, 
mrParent.m_nXScreen, 1, aTmpRect, aTmpGC );
-
-        DBG_TESTTRANS( aFG );
-
-        // #105055# For XOR mode, keep background behind bitmap intact
-        if( !mbXORMode )
-        {
-            // mask out background in pixmap #2 (nontransparent areas 0)
-            aValues.function = GXand;
-            aValues.foreground = 0xffffffff;
-            aValues.background = 0x00000000;
-            XChangeGC( pXDisp, aTmpGC, nValues, &aValues );
-            static_cast<const X11SalBitmap&>(rTransBitmap).ImplDraw( aBG, 
mrParent.m_nXScreen, 1, aTmpRect, aTmpGC );
-
-            DBG_TESTTRANS( aBG );
-        }
-
-        // merge pixmap #1 and pixmap #2 in pixmap #2
-        aValues.function = GXxor;
-        aValues.foreground = 0xffffffff;
-        aValues.background = 0x00000000;
-        XChangeGC( pXDisp, aTmpGC, nValues, &aValues );
-        XCopyArea( pXDisp, aFG, aBG, aTmpGC,
-                   0, 0,
-                   rPosAry.mnDestWidth, rPosAry.mnDestHeight,
-                   0, 0 );
-        DBG_TESTTRANS( aBG );
-
-        // #105055# Disable XOR temporarily
-        bool bOldXORMode( mbXORMode );
-        mbXORMode = false;
-
-        // copy pixmap #2 (result) to background
-        XCopyArea( pXDisp, aBG, aDrawable, GetCopyGC(),
-                   0, 0,
-                   rPosAry.mnDestWidth, rPosAry.mnDestHeight,
-                   rPosAry.mnDestX, rPosAry.mnDestY );
-
-        DBG_TESTTRANS( aBG );
-
-        mbXORMode = bOldXORMode;
-
-        XFreeGC( pXDisp, aTmpGC );
-        XFlush( pXDisp );
-    }
-    else
-        drawBitmap( rPosAry, rSalBitmap );
-
-    if( aFG )
-        XFreePixmap( pXDisp, aFG );
-
-    if( aBG )
-        XFreePixmap( pXDisp, aBG );
-}
-
-bool X11SalGraphicsImpl::drawAlphaBitmap( const SalTwoRect& rTR,
-    const SalBitmap& rSrcBitmap, const SalBitmap& rAlphaBmp )
-{
-    // non 8-bit alpha not implemented yet
-    if( rAlphaBmp.GetBitCount() != 8 )
-        return false;
-    // #i75531# the workaround below can go when
-    // X11SalGraphics::drawAlphaBitmap()'s render acceleration
-    // can handle the bitmap depth mismatch directly
-    if( rSrcBitmap.GetBitCount() < rAlphaBmp.GetBitCount() )
-        return false;
-
-    // horizontal mirroring not implemented yet
-    if( rTR.mnDestWidth < 0 )
-        return false;
-
-    // stretched conversion is not implemented yet
-    if( rTR.mnDestWidth != rTR.mnSrcWidth )
-        return false;
-    if( rTR.mnDestHeight!= rTR.mnSrcHeight )
-        return false;
-
-    // create destination picture
-    Picture aDstPic = GetXRenderPicture();
-    if( !aDstPic )
-        return false;
-
-    const SalDisplay* pSalDisp = mrParent.GetDisplay();
-    const SalVisual& rSalVis = pSalDisp->GetVisual( mrParent.m_nXScreen );
-    Display* pXDisplay = pSalDisp->GetDisplay();
-
-    // create source Picture
-    int nDepth = mrParent.m_pVDev ? static_cast< X11SalVirtualDevice* 
>(mrParent.m_pVDev)->GetDepth() : rSalVis.GetDepth();
-    const X11SalBitmap& rSrcX11Bmp = static_cast<const X11SalBitmap&>( 
rSrcBitmap );
-    ImplSalDDB* pSrcDDB = rSrcX11Bmp.ImplGetDDB( mrParent.GetDrawable(), 
mrParent.m_nXScreen, nDepth, rTR );
-    if( !pSrcDDB )
-        return false;
-
-    //#i75249# workaround for ImplGetDDB() giving us back a different depth 
than
-    // we requested. E.g. mask pixmaps are always compatible with the drawable
-    // TODO: find an appropriate picture format for these cases
-    //       then remove the workaround below and the one for #i75531#
-    if( nDepth != pSrcDDB->ImplGetDepth() )
-        return false;
-
-    Pixmap aSrcPM = pSrcDDB->ImplGetPixmap();
-    if( !aSrcPM )
-        return false;
-
-    // create source picture
-    // TODO: use scoped picture
-    Visual* pSrcXVisual = rSalVis.GetVisual();
-    XRenderPeer& rPeer = XRenderPeer::GetInstance();
-    XRenderPictFormat* pSrcVisFmt = rPeer.FindVisualFormat( pSrcXVisual );
-    if( !pSrcVisFmt )
-        return false;
-    Picture aSrcPic = rPeer.CreatePicture( aSrcPM, pSrcVisFmt, 0, nullptr );
-    if( !aSrcPic )
-        return false;
-
-    // create alpha Picture
-
-    // TODO: use SalX11Bitmap functionality and caching for the Alpha Pixmap
-    // problem is that they don't provide an 8bit Pixmap on a non-8bit display
-    BitmapBuffer* pAlphaBuffer = 
const_cast<SalBitmap&>(rAlphaBmp).AcquireBuffer( BitmapAccessMode::Read );
-
-    // an XImage needs its data top_down
-    // TODO: avoid wrongly oriented images in upper layers!
-    const int nImageSize = pAlphaBuffer->mnHeight * 
pAlphaBuffer->mnScanlineSize;
-    const char* pSrcBits = reinterpret_cast<char*>(pAlphaBuffer->mpBits);
-    char* pAlphaBits = new char[ nImageSize ];
-    if( pAlphaBuffer->mnFormat & ScanlineFormat::TopDown )
-        memcpy( pAlphaBits, pSrcBits, nImageSize );
-    else
-    {
-        char* pDstBits = pAlphaBits + nImageSize;
-        const int nLineSize = pAlphaBuffer->mnScanlineSize;
-        for(; (pDstBits -= nLineSize) >= pAlphaBits; pSrcBits += nLineSize )
-            memcpy( pDstBits, pSrcBits, nLineSize );
-    }
-
-    // the alpha values need to be inverted for XRender
-    // TODO: make upper layers use standard alpha
-    tools::Long* pLDst = reinterpret_cast<long*>(pAlphaBits);
-    for( int i = nImageSize/sizeof(long); --i >= 0; ++pLDst )
-        *pLDst = ~*pLDst;
-
-    char* pCDst = reinterpret_cast<char*>(pLDst);
-    for( int i = nImageSize & (sizeof(long)-1); --i >= 0; ++pCDst )
-        *pCDst = ~*pCDst;
-
-    const XRenderPictFormat* pAlphaFormat = rPeer.GetStandardFormatA8();
-    XImage* pAlphaImg = XCreateImage( pXDisplay, pSrcXVisual, 8, ZPixmap, 0,
-        pAlphaBits, pAlphaBuffer->mnWidth, pAlphaBuffer->mnHeight,
-        pAlphaFormat->depth, pAlphaBuffer->mnScanlineSize );
-
-    Pixmap aAlphaPM = limitXCreatePixmap( pXDisplay, mrParent.GetDrawable(),
-        rTR.mnDestWidth, rTR.mnDestHeight, 8 );
-
-    XGCValues aAlphaGCV;
-    aAlphaGCV.function = GXcopy;
-    GC aAlphaGC = XCreateGC( pXDisplay, aAlphaPM, GCFunction, &aAlphaGCV );
-    XPutImage( pXDisplay, aAlphaPM, aAlphaGC, pAlphaImg,
-        rTR.mnSrcX, rTR.mnSrcY, 0, 0, rTR.mnDestWidth, rTR.mnDestHeight );
-    XFreeGC( pXDisplay, aAlphaGC );
-    XFree( pAlphaImg );
-    if( pAlphaBits != reinterpret_cast<char*>(pAlphaBuffer->mpBits) )
-        delete[] pAlphaBits;
-
-    const_cast<SalBitmap&>(rAlphaBmp).ReleaseBuffer( pAlphaBuffer, 
BitmapAccessMode::Read );
-
-    XRenderPictureAttributes aAttr;
-    aAttr.repeat = int(true);
-    Picture aAlphaPic = rPeer.CreatePicture( aAlphaPM, pAlphaFormat, CPRepeat, 
&aAttr );
-    if( !aAlphaPic )
-        return false;
-
-    // set clipping
-    if( mrParent.mpClipRegion && !XEmptyRegion( mrParent.mpClipRegion ) )
-        rPeer.SetPictureClipRegion( aDstPic, mrParent.mpClipRegion );
-
-    // paint source * mask over destination picture
-    rPeer.CompositePicture( PictOpOver, aSrcPic, aAlphaPic, aDstPic,
-        rTR.mnSrcX, rTR.mnSrcY,
-        rTR.mnDestX, rTR.mnDestY, rTR.mnDestWidth, rTR.mnDestHeight );
-
-    rPeer.FreePicture( aAlphaPic );
-    XFreePixmap(pXDisplay, aAlphaPM);
-    rPeer.FreePicture( aSrcPic );
-    return true;
-}
-
-void X11SalGraphicsImpl::drawMask( const SalTwoRect& rPosAry,
-                               const SalBitmap &rSalBitmap,
-                               Color nMaskColor )
-{
-    const SalDisplay*   pSalDisp = mrParent.GetDisplay();
-    Display*            pXDisp = pSalDisp->GetDisplay();
-    Drawable            aDrawable( mrParent.GetDrawable() );
-    Pixmap              aStipple( limitXCreatePixmap( pXDisp, aDrawable,
-                                                 rPosAry.mnDestWidth,
-                                                 rPosAry.mnDestHeight, 1 ) );
-
-    if( aStipple )
-    {
-        SalTwoRect  aTwoRect( rPosAry ); aTwoRect.mnDestX = aTwoRect.mnDestY = 
0;
-        GC          aTmpGC;
-        XGCValues   aValues;
-
-        // create a stipple bitmap first (set bits are changed to unset bits 
and vice versa)
-        aValues.function = GXcopyInverted;
-        aValues.foreground = 1;
-        aValues.background = 0;
-        aTmpGC = XCreateGC( pXDisp, aStipple, GCFunction | GCForeground | 
GCBackground, &aValues );
-        static_cast<const X11SalBitmap&>(rSalBitmap).ImplDraw( aStipple, 
mrParent.m_nXScreen, 1, aTwoRect, aTmpGC );
-
-        XFreeGC( pXDisp, aTmpGC );
-
-        // Set stipple and draw rectangle
-        GC  aStippleGC( GetStippleGC() );
-        int nX = rPosAry.mnDestX, nY = rPosAry.mnDestY;
-
-        XSetStipple( pXDisp, aStippleGC, aStipple );
-        XSetTSOrigin( pXDisp, aStippleGC, nX, nY );
-        XSetForeground( pXDisp, aStippleGC, mrParent.GetPixel( nMaskColor ) );
-        XFillRectangle( pXDisp, aDrawable, aStippleGC,
-                        nX, nY,
-                        rPosAry.mnDestWidth, rPosAry.mnDestHeight );
-        XFreePixmap( pXDisp, aStipple );
-        XFlush( pXDisp );
-    }
-    else
-        drawBitmap( rPosAry, rSalBitmap );
-}
-
 void X11SalGraphicsImpl::ResetClipRegion()
 {
     if( !mrParent.mpClipRegion )
@@ -636,80 +276,6 @@ tools::Long X11SalGraphicsImpl::GetGraphicsHeight() const
         return 0;
 }
 
-std::shared_ptr<SalBitmap> X11SalGraphicsImpl::getBitmap( tools::Long nX, 
tools::Long nY, tools::Long nDX, tools::Long nDY )
-{
-    bool bFakeWindowBG = false;
-
-    // normalize
-    if( nDX < 0 )
-    {
-        nX += nDX;
-        nDX = -nDX;
-    }
-    if ( nDY < 0 )
-    {
-        nY += nDY;
-        nDY = -nDY;
-    }
-
-    if( mrParent.bWindow_ && !mrParent.bVirDev_ )
-    {
-        XWindowAttributes aAttrib;
-
-        XGetWindowAttributes( mrParent.GetXDisplay(), mrParent.GetDrawable(), 
&aAttrib );
-        if( aAttrib.map_state != IsViewable )
-            bFakeWindowBG = true;
-        else
-        {
-            tools::Long nOrgDX = nDX, nOrgDY = nDY;
-
-            // clip to window size
-            if ( nX < 0 )
-            {
-                nDX += nX;
-                nX   = 0;
-            }
-            if ( nY < 0 )
-            {
-                nDY += nY;
-                nY   = 0;
-            }
-            if( nX + nDX > aAttrib.width )
-                nDX = aAttrib.width  - nX;
-            if( nY + nDY > aAttrib.height )
-                nDY = aAttrib.height - nY;
-
-            // inside ?
-            if( nDX <= 0 || nDY <= 0 )
-            {
-                bFakeWindowBG = true;
-                nDX = nOrgDX;
-                nDY = nOrgDY;
-            }
-        }
-    }
-
-    std::shared_ptr<X11SalBitmap> pSalBitmap = 
std::make_shared<X11SalBitmap>();
-    sal_uInt16 nBitCount = GetBitCount();
-    vcl::PixelFormat ePixelFormat = vcl::bitDepthToPixelFormat(nBitCount);
-
-    if( &mrParent.GetDisplay()->GetColormap( mrParent.m_nXScreen ) != 
&mrParent.GetColormap() )
-    {
-        ePixelFormat = vcl::PixelFormat::N1_BPP;
-        nBitCount = 1;
-    }
-
-    if (nBitCount > 8)
-        ePixelFormat = vcl::PixelFormat::N24_BPP;
-
-    if( ! bFakeWindowBG )
-        pSalBitmap->ImplCreateFromDrawable( mrParent.GetDrawable(), 
mrParent.m_nXScreen, nBitCount, nX, nY, nDX, nDY );
-    else
-        pSalBitmap->Create( Size( nDX, nDY ), ePixelFormat, BitmapPalette( 
nBitCount > 8 ? nBitCount : 0 ) );
-
-    return pSalBitmap;
-}
-
 sal_uInt16 X11SalGraphicsImpl::GetBitCount() const
 {
     return mrParent.GetVisual().GetDepth();
diff --git a/vcl/unx/generic/gdi/gdiimpl.hxx b/vcl/unx/generic/gdi/gdiimpl.hxx
index 771dcd039c9c..cecd2a480626 100644
--- a/vcl/unx/generic/gdi/gdiimpl.hxx
+++ b/vcl/unx/generic/gdi/gdiimpl.hxx
@@ -65,10 +65,6 @@ private:
 
     tools::Long GetGraphicsHeight() const;
 
-    void drawMaskedBitmap( const SalTwoRect& rPosAry,
-                                              const SalBitmap& rSalBitmap,
-                                              const SalBitmap& 
rTransparentBitmap );
-
 public:
 
     explicit X11SalGraphicsImpl(X11SalGraphics& rParent);
@@ -90,38 +86,6 @@ public:
 
     // enable/disable XOR drawing
     virtual void SetXORMode( bool bSet, bool bInvertOnly ) override;
-
-    virtual void drawBitmap( const SalTwoRect& rPosAry, const SalBitmap& 
rSalBitmap ) override;
-
-    virtual void drawBitmap(
-                const SalTwoRect& rPosAry,
-                const SalBitmap& rSalBitmap,
-                const SalBitmap& rMaskBitmap ) override;
-
-    virtual void drawMask(
-                const SalTwoRect& rPosAry,
-                const SalBitmap& rSalBitmap,
-                Color nMaskColor ) override;
-
-    virtual std::shared_ptr<SalBitmap> getBitmap( tools::Long nX, tools::Long 
nY, tools::Long nWidth, tools::Long nHeight ) override;
-
-    /** Render bitmap with alpha channel
-
-        @param rSourceBitmap
-        Source bitmap to blit
-
-        @param rAlphaBitmap
-        Alpha channel to use for blitting
-
-        @return true, if the operation succeeded, and false
-        otherwise. In this case, clients should try to emulate alpha
-        compositing themselves
-     */
-    virtual bool drawAlphaBitmap(
-                const SalTwoRect&,
-                const SalBitmap& rSourceBitmap,
-                const SalBitmap& rAlphaBitmap ) override;
-
 public:
     void Init() override;
 };
commit cc4c5299c0b2c1b9d92f9cdf88140735519f32f8
Author:     Caolán McNamara <caol...@redhat.com>
AuthorDate: Tue Jan 10 15:44:00 2023 +0000
Commit:     Caolán McNamara <caol...@redhat.com>
CommitDate: Wed Jan 11 10:33:38 2023 +0000

    consider only CAIRO_CONTENT_ALPHA to be 1bit
    
    Change-Id: I0d09207c8131297e9c95c4e146ae62d5dac77be3
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/145287
    Tested-by: Caolán McNamara <caol...@redhat.com>
    Reviewed-by: Caolán McNamara <caol...@redhat.com>

diff --git a/vcl/headless/CairoCommon.cxx b/vcl/headless/CairoCommon.cxx
index 12f42313081b..6552460cf5e6 100644
--- a/vcl/headless/CairoCommon.cxx
+++ b/vcl/headless/CairoCommon.cxx
@@ -402,7 +402,7 @@ cairo_user_data_key_t* CairoCommon::getDamageKey()
 
 sal_uInt16 CairoCommon::GetBitCount() const
 {
-    if (cairo_surface_get_content(m_pSurface) != CAIRO_CONTENT_COLOR_ALPHA)
+    if (cairo_surface_get_content(m_pSurface) == CAIRO_CONTENT_ALPHA)
         return 1;
     return 32;
 }

Reply via email to