diff options
-rw-r--r-- | vcl/headless/CairoCommon.cxx | 244 | ||||
-rw-r--r-- | vcl/headless/SvpGraphicsBackend.cxx | 127 | ||||
-rw-r--r-- | vcl/inc/headless/CairoCommon.hxx | 80 | ||||
-rw-r--r-- | vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx | 123 |
4 files changed, 189 insertions, 385 deletions
diff --git a/vcl/headless/CairoCommon.cxx b/vcl/headless/CairoCommon.cxx index 8ea358cbdc34..f347cf47f930 100644 --- a/vcl/headless/CairoCommon.cxx +++ b/vcl/headless/CairoCommon.cxx @@ -609,18 +609,21 @@ void CairoCommon::clipRegion(cairo_t* cr, const vcl::Region& rClipRegion) void CairoCommon::clipRegion(cairo_t* cr) { CairoCommon::clipRegion(cr, m_aClipRegion); } -void CairoCommon::drawPixel(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, tools::Long nX, tools::Long nY) +void CairoCommon::drawPixel(const std::optional<Color>& rLineColor, tools::Long nX, tools::Long nY, + bool bAntiAlias) { if (!rLineColor) return; + cairo_t* cr = getCairoContext(true, bAntiAlias); + clipRegion(cr); + cairo_rectangle(cr, nX, nY, 1, 1); CairoCommon::applyColor(cr, *rLineColor, 0.0); cairo_fill(cr); - if (pExtents) - *pExtents = getClippedFillDamage(cr); + basegfx::B2DRange extents = getClippedFillDamage(cr); + releaseCairoContext(cr, true, extents); } Color CairoCommon::getPixel(cairo_surface_t* pSurface, tools::Long nX, tools::Long nY) @@ -656,10 +659,12 @@ Color CairoCommon::getPixel(cairo_surface_t* pSurface, tools::Long nX, tools::Lo return aColor; } -void CairoCommon::drawLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, tools::Long nX1, tools::Long nY1, tools::Long nX2, - tools::Long nY2) +void CairoCommon::drawLine(tools::Long nX1, tools::Long nY1, tools::Long nX2, tools::Long nY2, + bool bAntiAlias) { + cairo_t* cr = getCairoContext(false, bAntiAlias); + clipRegion(cr); + basegfx::B2DPolygon aPoly; // PixelOffset used: To not mix with possible PixelSnap, cannot do @@ -676,29 +681,29 @@ void CairoCommon::drawLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color AddPolygonToPath(cr, aPoly, basegfx::B2DHomMatrix(), !bAntiAlias, false); - CairoCommon::applyColor(cr, rLineColor); + CairoCommon::applyColor(cr, *m_oLineColor); - if (pExtents) - { - *pExtents = getClippedStrokeDamage(cr); - pExtents->transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); - } + basegfx::B2DRange extents = getClippedStrokeDamage(cr); + extents.transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); cairo_stroke(cr); + + releaseCairoContext(cr, false, extents); } -void CairoCommon::drawRect(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, double nX, - double nY, double nWidth, double nHeight) +void CairoCommon::drawRect(double nX, double nY, double nWidth, double nHeight, bool bAntiAlias) { // fast path for the common case of simply creating a solid block of color - if (rFillColor && rLineColor && rFillColor == rLineColor) + if (m_oFillColor && m_oLineColor && m_oFillColor == m_oLineColor) { double fTransparency = 0; // don't bother trying to draw stuff which is effectively invisible if (nWidth < 0.1 || nHeight < 0.1) return; + + cairo_t* cr = getCairoContext(true, bAntiAlias); + clipRegion(cr); + bool bPixelSnap = !bAntiAlias; if (bPixelSnap) { @@ -709,52 +714,60 @@ void CairoCommon::drawRect(cairo_t* cr, basegfx::B2DRange* pExtents, nHeight = basegfx::fround(nHeight); } cairo_rectangle(cr, nX, nY, nWidth, nHeight); - CairoCommon::applyColor(cr, *rFillColor, fTransparency); - if (pExtents) - { - // Get FillDamage - *pExtents = getClippedFillDamage(cr); - } + + CairoCommon::applyColor(cr, *m_oFillColor, fTransparency); + // Get FillDamage + basegfx::B2DRange extents = getClippedFillDamage(cr); + cairo_fill(cr); + + releaseCairoContext(cr, true, extents); + return; } // because of the -1 hack we have to do fill and draw separately - if (rFillColor) + std::optional<Color> aOrigFillColor = m_oFillColor; + std::optional<Color> aOrigLineColor = m_oLineColor; + m_oFillColor = std::nullopt; + m_oLineColor = std::nullopt; + + if (aOrigFillColor) { basegfx::B2DPolygon aRect = basegfx::utils::createPolygonFromRect( basegfx::B2DRectangle(nX, nY, nX + nWidth, nY + nHeight)); - drawPolyPolygon(cr, pExtents, std::nullopt, rFillColor, bAntiAlias, basegfx::B2DHomMatrix(), - basegfx::B2DPolyPolygon(aRect), 0.0); + + m_oFillColor = aOrigFillColor; + drawPolyPolygon(basegfx::B2DHomMatrix(), basegfx::B2DPolyPolygon(aRect), 0.0, bAntiAlias); + m_oFillColor = std::nullopt; } - if (rLineColor) + + if (aOrigLineColor) { // need same -1 hack as X11SalGraphicsImpl::drawRect basegfx::B2DPolygon aRect = basegfx::utils::createPolygonFromRect( basegfx::B2DRectangle(nX, nY, nX + nWidth - 1, nY + nHeight - 1)); - drawPolyPolygon(cr, pExtents, rLineColor, std::nullopt, bAntiAlias, basegfx::B2DHomMatrix(), - basegfx::B2DPolyPolygon(aRect), 0.0); + + m_oLineColor = aOrigLineColor; + drawPolyPolygon(basegfx::B2DHomMatrix(), basegfx::B2DPolyPolygon(aRect), 0.0, bAntiAlias); + m_oLineColor = std::nullopt; } + + m_oFillColor = aOrigFillColor; + m_oLineColor = aOrigLineColor; } -void CairoCommon::drawPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - sal_uInt32 nPoints, const Point* pPtAry) +void CairoCommon::drawPolygon(sal_uInt32 nPoints, const Point* pPtAry, bool bAntiAlias) { basegfx::B2DPolygon aPoly; aPoly.append(basegfx::B2DPoint(pPtAry->getX(), pPtAry->getY()), nPoints); for (sal_uInt32 i = 1; i < nPoints; ++i) aPoly.setB2DPoint(i, basegfx::B2DPoint(pPtAry[i].getX(), pPtAry[i].getY())); - drawPolyPolygon(cr, pExtents, rLineColor, rFillColor, bAntiAlias, basegfx::B2DHomMatrix(), - basegfx::B2DPolyPolygon(aPoly), 0.0); + drawPolyPolygon(basegfx::B2DHomMatrix(), basegfx::B2DPolyPolygon(aPoly), 0.0, bAntiAlias); } -void CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - sal_uInt32 nPoly, const sal_uInt32* pPointCounts, - const Point** pPtAry) +void CairoCommon::drawPolyPolygon(sal_uInt32 nPoly, const sal_uInt32* pPointCounts, + const Point** pPtAry, bool bAntiAlias) { basegfx::B2DPolyPolygon aPolyPoly; for (sal_uInt32 nPolygon = 0; nPolygon < nPoly; ++nPolygon) @@ -772,18 +785,15 @@ void CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, } } - drawPolyPolygon(cr, pExtents, rLineColor, rFillColor, bAntiAlias, basegfx::B2DHomMatrix(), - aPolyPoly, 0.0); + drawPolyPolygon(basegfx::B2DHomMatrix(), aPolyPoly, 0.0, bAntiAlias); } -bool CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - const basegfx::B2DHomMatrix& rObjectToDevice, - const basegfx::B2DPolyPolygon& rPolyPolygon, double fTransparency) +bool CairoCommon::drawPolyPolygon(const basegfx::B2DHomMatrix& rObjectToDevice, + const basegfx::B2DPolyPolygon& rPolyPolygon, double fTransparency, + bool bAntiAlias) { - const bool bHasFill(rFillColor.has_value()); - const bool bHasLine(rLineColor.has_value()); + const bool bHasFill(m_oFillColor.has_value()); + const bool bHasLine(m_oLineColor.has_value()); if (0 == rPolyPolygon.count() || !(bHasFill || bHasLine) || fTransparency < 0.0 || fTransparency >= 1.0) @@ -797,6 +807,9 @@ bool CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, if (aPolygonRange.getWidth() < 0.1 || aPolygonRange.getHeight() < 0.1) return true; + cairo_t* cr = getCairoContext(true, bAntiAlias); + clipRegion(cr); + // Set full (Object-to-Device) transformation - if used if (!rObjectToDevice.isIdentity()) { @@ -808,16 +821,16 @@ bool CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, cairo_set_matrix(cr, &aMatrix); } + // To make releaseCairoContext work, use empty extents + basegfx::B2DRange extents; + if (bHasFill) { add_polygon_path(cr, rPolyPolygon, rObjectToDevice, !bAntiAlias); - CairoCommon::applyColor(cr, *rFillColor, fTransparency); - if (pExtents) - { - // Get FillDamage (will be extended for LineDamage below) - *pExtents = getClippedFillDamage(cr); - } + CairoCommon::applyColor(cr, *m_oFillColor, fTransparency); + // Get FillDamage (will be extended for LineDamage below) + extents = getClippedFillDamage(cr); cairo_fill(cr); } @@ -831,31 +844,25 @@ bool CairoCommon::drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, add_polygon_path(cr, rPolyPolygon, rObjectToDevice, !bAntiAlias); - CairoCommon::applyColor(cr, *rLineColor, fTransparency); + CairoCommon::applyColor(cr, *m_oLineColor, fTransparency); - if (pExtents) - { - // expand with possible StrokeDamage - basegfx::B2DRange stroke_extents = getClippedStrokeDamage(cr); - stroke_extents.transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); - pExtents->expand(stroke_extents); - } + // expand with possible StrokeDamage + basegfx::B2DRange stroke_extents = getClippedStrokeDamage(cr); + stroke_extents.transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); + extents.expand(stroke_extents); cairo_stroke(cr); } - if (pExtents) - { - // if transformation has been applied, transform also extents (ranges) - // of damage so they can be correctly redrawn - pExtents->transform(rObjectToDevice); - } + // if transformation has been applied, transform also extents (ranges) + // of damage so they can be correctly redrawn + extents.transform(rObjectToDevice); + releaseCairoContext(cr, true, extents); return true; } -void CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, sal_uInt32 nPoints, const Point* pPtAry) +void CairoCommon::drawPolyLine(sal_uInt32 nPoints, const Point* pPtAry, bool bAntiAlias) { basegfx::B2DPolygon aPoly; aPoly.append(basegfx::B2DPoint(pPtAry->getX(), pPtAry->getY()), nPoints); @@ -863,17 +870,15 @@ void CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const C aPoly.setB2DPoint(i, basegfx::B2DPoint(pPtAry[i].getX(), pPtAry[i].getY())); aPoly.setClosed(false); - drawPolyLine(cr, pExtents, rLineColor, bAntiAlias, basegfx::B2DHomMatrix(), aPoly, 0.0, 1.0, - nullptr, basegfx::B2DLineJoin::Miter, css::drawing::LineCap_BUTT, - basegfx::deg2rad(15.0) /*default*/, false); + drawPolyLine(basegfx::B2DHomMatrix(), aPoly, 0.0, 1.0, nullptr, basegfx::B2DLineJoin::Miter, + css::drawing::LineCap_BUTT, basegfx::deg2rad(15.0) /*default*/, false, bAntiAlias); } -bool CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, const basegfx::B2DHomMatrix& rObjectToDevice, +bool CairoCommon::drawPolyLine(const basegfx::B2DHomMatrix& rObjectToDevice, const basegfx::B2DPolygon& rPolyLine, double fTransparency, double fLineWidth, const std::vector<double>* pStroke, basegfx::B2DLineJoin eLineJoin, css::drawing::LineCap eLineCap, - double fMiterMinimumAngle, bool bPixelSnapHairline) + double fMiterMinimumAngle, bool bPixelSnapHairline, bool bAntiAlias) { // short circuit if there is nothing to do if (0 == rPolyLine.count() || fTransparency < 0.0 || fTransparency >= 1.0) @@ -894,6 +899,9 @@ bool CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const C } } + cairo_t* cr = getCairoContext(false, bAntiAlias); + clipRegion(cr); + // need to check/handle LineWidth when ObjectToDevice transformation is used const bool bObjectToDeviceIsIdentity(rObjectToDevice.isIdentity()); @@ -975,8 +983,8 @@ bool CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const C } } - cairo_set_source_rgba(cr, rLineColor.GetRed() / 255.0, rLineColor.GetGreen() / 255.0, - rLineColor.GetBlue() / 255.0, 1.0 - fTransparency); + cairo_set_source_rgba(cr, m_oLineColor->GetRed() / 255.0, m_oLineColor->GetGreen() / 255.0, + m_oLineColor->GetBlue() / 255.0, 1.0 - fTransparency); cairo_set_line_join(cr, eCairoLineJoin); cairo_set_line_cap(cr, eCairoLineCap); @@ -1134,44 +1142,43 @@ bool CairoCommon::drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const C } // extract extents - if (pExtents) - { - *pExtents = getClippedStrokeDamage(cr); - // transform also extents (ranges) of damage so they can be correctly redrawn - pExtents->transform(aDamageMatrix); - } + basegfx::B2DRange extents = getClippedStrokeDamage(cr); + // transform also extents (ranges) of damage so they can be correctly redrawn + extents.transform(aDamageMatrix); // draw and consume cairo_stroke(cr); + releaseCairoContext(cr, false, extents); + return true; } -bool CairoCommon::drawAlphaRect(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, tools::Long nX, - tools::Long nY, tools::Long nWidth, tools::Long nHeight, - sal_uInt8 nTransparency) +bool CairoCommon::drawAlphaRect(tools::Long nX, tools::Long nY, tools::Long nWidth, + tools::Long nHeight, sal_uInt8 nTransparency, bool bAntiAlias) { - const bool bHasFill(rFillColor.has_value()); - const bool bHasLine(rLineColor.has_value()); + const bool bHasFill(m_oFillColor.has_value()); + const bool bHasLine(m_oLineColor.has_value()); if (!bHasFill && !bHasLine) return true; + cairo_t* cr = getCairoContext(false, bAntiAlias); + clipRegion(cr); + const double fTransparency = nTransparency * (1.0 / 100); + // To make releaseCairoContext work, use empty extents + basegfx::B2DRange extents; + if (bHasFill) { cairo_rectangle(cr, nX, nY, nWidth, nHeight); - applyColor(cr, *rFillColor, fTransparency); + applyColor(cr, *m_oFillColor, fTransparency); - if (pExtents) - { - // set FillDamage - *pExtents = getClippedFillDamage(cr); - } + // set FillDamage + extents = getClippedFillDamage(cr); cairo_fill(cr); } @@ -1186,24 +1193,23 @@ bool CairoCommon::drawAlphaRect(cairo_t* cr, basegfx::B2DRange* pExtents, cairo_rectangle(cr, nX, nY, nWidth, nHeight); - applyColor(cr, *rLineColor, fTransparency); + applyColor(cr, *m_oLineColor, fTransparency); - if (pExtents) - { - // expand with possible StrokeDamage - basegfx::B2DRange stroke_extents = getClippedStrokeDamage(cr); - stroke_extents.transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); - pExtents->expand(stroke_extents); - } + // expand with possible StrokeDamage + basegfx::B2DRange stroke_extents = getClippedStrokeDamage(cr); + stroke_extents.transform(basegfx::utils::createTranslateB2DHomMatrix(0.5, 0.5)); + extents.expand(stroke_extents); cairo_stroke(cr); } + releaseCairoContext(cr, false, extents); + return true; } -bool CairoCommon::drawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias, - const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient) +bool CairoCommon::drawGradient(const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient, + bool bAntiAlias) { if (rGradient.GetStyle() != GradientStyle::Linear && rGradient.GetStyle() != GradientStyle::Radial) @@ -1211,6 +1217,9 @@ bool CairoCommon::drawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bA if (rGradient.GetSteps() != 0) return false; // We can't tell cairo how many colors to use in the gradient. + cairo_t* cr = getCairoContext(true, bAntiAlias); + clipRegion(cr); + tools::Rectangle aInputRect(rPolyPolygon.GetBoundRect()); if (rPolyPolygon.IsRect()) { @@ -1273,17 +1282,19 @@ bool CairoCommon::drawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bA cairo_set_source(cr, pattern); cairo_pattern_destroy(pattern); - if (pExtents) - *pExtents = getClippedFillDamage(cr); + basegfx::B2DRange extents = getClippedFillDamage(cr); cairo_fill_preserve(cr); + releaseCairoContext(cr, true, extents); + return true; } -bool CairoCommon::implDrawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias, - basegfx::B2DPolyPolygon const& rPolyPolygon, - SalGradient const& rGradient) +bool CairoCommon::implDrawGradient(basegfx::B2DPolyPolygon const& rPolyPolygon, + SalGradient const& rGradient, bool bAntiAlias) { + cairo_t* cr = getCairoContext(true, bAntiAlias); + basegfx::B2DHomMatrix rObjectToDevice; for (auto const& rPolygon : rPolyPolygon) @@ -1306,11 +1317,12 @@ bool CairoCommon::implDrawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, boo cairo_set_source(cr, pattern); cairo_pattern_destroy(pattern); - if (pExtents) - *pExtents = getClippedFillDamage(cr); + basegfx::B2DRange extents = getClippedFillDamage(cr); cairo_fill_preserve(cr); + releaseCairoContext(cr, true, extents); + return true; } diff --git a/vcl/headless/SvpGraphicsBackend.cxx b/vcl/headless/SvpGraphicsBackend.cxx index 1d2f17c44747..56fca50c8eef 100644 --- a/vcl/headless/SvpGraphicsBackend.cxx +++ b/vcl/headless/SvpGraphicsBackend.cxx @@ -100,99 +100,48 @@ void SvpGraphicsBackend::SetROPFillColor(SalROPColor nROPColor) void SvpGraphicsBackend::drawPixel(tools::Long nX, tools::Long nY) { - drawPixel(nX, nY, *m_rCairoCommon.m_oLineColor); + m_rCairoCommon.drawPixel(m_rCairoCommon.m_oLineColor, nX, nY, getAntiAlias()); } void SvpGraphicsBackend::drawPixel(tools::Long nX, tools::Long nY, Color aColor) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawPixel(cr, &extents, aColor, nX, nY); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); + m_rCairoCommon.drawPixel(aColor, nX, nY, getAntiAlias()); } void SvpGraphicsBackend::drawLine(tools::Long nX1, tools::Long nY1, tools::Long nX2, tools::Long nY2) { - cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawLine(cr, &extents, *m_rCairoCommon.m_oLineColor, getAntiAlias(), nX1, nY1, nX2, - nY2); - - m_rCairoCommon.releaseCairoContext(cr, false, extents); + m_rCairoCommon.drawLine(nX1, nY1, nX2, nY2, getAntiAlias()); } void SvpGraphicsBackend::drawRect(tools::Long nX, tools::Long nY, tools::Long nWidth, tools::Long nHeight) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawRect(cr, &extents, m_rCairoCommon.m_oLineColor, m_rCairoCommon.m_oFillColor, - getAntiAlias(), nX, nY, nWidth, nHeight); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); + m_rCairoCommon.drawRect(nX, nY, nWidth, nHeight, getAntiAlias()); } void SvpGraphicsBackend::drawPolyLine(sal_uInt32 nPoints, const Point* pPtAry) { - cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange aExtents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawPolyLine(cr, &aExtents, *m_rCairoCommon.m_oLineColor, getAntiAlias(), nPoints, - pPtAry); - - m_rCairoCommon.releaseCairoContext(cr, false, aExtents); + m_rCairoCommon.drawPolyLine(nPoints, pPtAry, getAntiAlias()); } void SvpGraphicsBackend::drawPolygon(sal_uInt32 nPoints, const Point* pPtAry) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawPolygon(cr, &extents, m_rCairoCommon.m_oLineColor, m_rCairoCommon.m_oFillColor, - getAntiAlias(), nPoints, pPtAry); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); + m_rCairoCommon.drawPolygon(nPoints, pPtAry, getAntiAlias()); } void SvpGraphicsBackend::drawPolyPolygon(sal_uInt32 nPoly, const sal_uInt32* pPointCounts, const Point** pPtAry) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - CairoCommon::drawPolyPolygon(cr, &extents, m_rCairoCommon.m_oLineColor, - m_rCairoCommon.m_oFillColor, getAntiAlias(), nPoly, pPointCounts, - pPtAry); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); + m_rCairoCommon.drawPolyPolygon(nPoly, pPointCounts, pPtAry, getAntiAlias()); } bool SvpGraphicsBackend::drawPolyPolygon(const basegfx::B2DHomMatrix& rObjectToDevice, const basegfx::B2DPolyPolygon& rPolyPolygon, double fTransparency) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - bool bRetVal(CairoCommon::drawPolyPolygon(cr, &extents, m_rCairoCommon.m_oLineColor, - m_rCairoCommon.m_oFillColor, getAntiAlias(), - rObjectToDevice, rPolyPolygon, fTransparency)); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetVal; + return m_rCairoCommon.drawPolyPolygon(rObjectToDevice, rPolyPolygon, fTransparency, + getAntiAlias()); } bool SvpGraphicsBackend::drawPolyLine(const basegfx::B2DHomMatrix& rObjectToDevice, @@ -202,28 +151,9 @@ bool SvpGraphicsBackend::drawPolyLine(const basegfx::B2DHomMatrix& rObjectToDevi css::drawing::LineCap eLineCap, double fMiterMinimumAngle, bool bPixelSnapHairline) { - // short circuit if there is nothing to do - if (0 == rPolyLine.count() || fTransparency < 0.0 || fTransparency >= 1.0) - return true; - - // Wrap call to static version of ::drawPolyLine by - // preparing/getting some local data and parameters - // due to usage in vcl/unx/generic/gdi/salgdi.cxx. - // This is mainly about extended handling of extents - // and the way destruction of CairoContext is handled - // due to current XOR stuff - cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange aExtents; - m_rCairoCommon.clipRegion(cr); - - bool bRetval(CairoCommon::drawPolyLine(cr, &aExtents, *m_rCairoCommon.m_oLineColor, - getAntiAlias(), rObjectToDevice, rPolyLine, - fTransparency, fLineWidth, pStroke, eLineJoin, eLineCap, - fMiterMinimumAngle, bPixelSnapHairline)); - - m_rCairoCommon.releaseCairoContext(cr, false, aExtents); - - return bRetval; + return m_rCairoCommon.drawPolyLine(rObjectToDevice, rPolyLine, fTransparency, fLineWidth, + pStroke, eLineJoin, eLineCap, fMiterMinimumAngle, + bPixelSnapHairline, getAntiAlias()); } bool SvpGraphicsBackend::drawPolyLineBezier(sal_uInt32, const Point*, const PolyFlags*) @@ -639,46 +569,19 @@ bool SvpGraphicsBackend::hasFastDrawTransformedBitmap() const bool SvpGraphicsBackend::drawAlphaRect(tools::Long nX, tools::Long nY, tools::Long nWidth, tools::Long nHeight, sal_uInt8 nTransparency) { - cairo_t* cr = m_rCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - const bool bRetval(CairoCommon::drawAlphaRect(cr, &extents, *m_rCairoCommon.m_oLineColor, - *m_rCairoCommon.m_oFillColor, nX, nY, nWidth, - nHeight, nTransparency)); - m_rCairoCommon.releaseCairoContext(cr, false, extents); - - return bRetval; + return m_rCairoCommon.drawAlphaRect(nX, nY, nWidth, nHeight, nTransparency, getAntiAlias()); } bool SvpGraphicsBackend::drawGradient(const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - const bool bRetval( - CairoCommon::drawGradient(cr, &extents, getAntiAlias(), rPolyPolygon, rGradient)); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetval; + return m_rCairoCommon.drawGradient(rPolyPolygon, rGradient, getAntiAlias()); } bool SvpGraphicsBackend::implDrawGradient(basegfx::B2DPolyPolygon const& rPolyPolygon, SalGradient const& rGradient) { - cairo_t* cr = m_rCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - m_rCairoCommon.clipRegion(cr); - - bool bRetVal( - CairoCommon::implDrawGradient(cr, &extents, getAntiAlias(), rPolyPolygon, rGradient)); - - m_rCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetVal; + return m_rCairoCommon.implDrawGradient(rPolyPolygon, rGradient, getAntiAlias()); } bool SvpGraphicsBackend::supportsOperation(OutDevSupportType eType) const diff --git a/vcl/inc/headless/CairoCommon.hxx b/vcl/inc/headless/CairoCommon.hxx index 30e699a49982..b9ba49737e5b 100644 --- a/vcl/inc/headless/CairoCommon.hxx +++ b/vcl/inc/headless/CairoCommon.hxx @@ -153,58 +153,40 @@ struct VCL_DLLPUBLIC CairoCommon void clipRegion(cairo_t* cr); static void clipRegion(cairo_t* cr, const vcl::Region& rClipRegion); - static void drawPixel(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, tools::Long nX, tools::Long nY); + void drawPixel(const std::optional<Color>& rLineColor, tools::Long nX, tools::Long nY, + bool bAntiAlias); static Color getPixel(cairo_surface_t* pSurface, tools::Long nX, tools::Long nY); - static void drawLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, tools::Long nX1, tools::Long nY1, tools::Long nX2, - tools::Long nY2); - - static void drawRect(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, double nX, - double nY, double nWidth, double nHeight); - - static void drawPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - sal_uInt32 nPoints, const Point* pPtAry); - - static void drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - sal_uInt32 nPoly, const sal_uInt32* pPoints, const Point** pPtAry); - - static bool drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, bool bAntiAlias, - const basegfx::B2DHomMatrix& rObjectToDevice, - const basegfx::B2DPolyPolygon&, double fTransparency); - - static void drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, sal_uInt32 nPoints, const Point* pPtAry); - - static bool drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor, - bool bAntiAlias, const basegfx::B2DHomMatrix& rObjectToDevice, - const basegfx::B2DPolygon& rPolyLine, double fTransparency, - double fLineWidth, const std::vector<double>* pStroke, - basegfx::B2DLineJoin eLineJoin, css::drawing::LineCap eLineCap, - double fMiterMinimumAngle, bool bPixelSnapHairline); - - static bool drawAlphaRect(cairo_t* cr, basegfx::B2DRange* pExtents, - const std::optional<Color>& rLineColor, - const std::optional<Color>& rFillColor, tools::Long nX, - tools::Long nY, tools::Long nWidth, tools::Long nHeight, - sal_uInt8 nTransparency); - - static bool drawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias, - const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient); - - static bool implDrawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias, - basegfx::B2DPolyPolygon const& rPolyPolygon, - SalGradient const& rGradient); + void drawLine(tools::Long nX1, tools::Long nY1, tools::Long nX2, tools::Long nY2, + bool bAntiAlias); + + void drawRect(double nX, double nY, double nWidth, double nHeight, bool bAntiAlias); + + void drawPolygon(sal_uInt32 nPoints, const Point* pPtAry, bool bAntiAlias); + + void drawPolyPolygon(sal_uInt32 nPoly, const sal_uInt32* pPoints, const Point** pPtAry, + bool bAntiAlias); + + bool drawPolyPolygon(const basegfx::B2DHomMatrix& rObjectToDevice, + const basegfx::B2DPolyPolygon&, double fTransparency, bool bAntiAlias); + + void drawPolyLine(sal_uInt32 nPoints, const Point* pPtAry, bool bAntiAlias); + + bool drawPolyLine(const basegfx::B2DHomMatrix& rObjectToDevice, + const basegfx::B2DPolygon& rPolyLine, double fTransparency, double fLineWidth, + const std::vector<double>* pStroke, basegfx::B2DLineJoin eLineJoin, + css::drawing::LineCap eLineCap, double fMiterMinimumAngle, + bool bPixelSnapHairline, bool bAntiAlias); + + bool drawAlphaRect(tools::Long nX, tools::Long nY, tools::Long nWidth, tools::Long nHeight, + sal_uInt8 nTransparency, bool bAntiAlias); + + bool drawGradient(const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient, + bool bAntiAlias); + + bool implDrawGradient(basegfx::B2DPolyPolygon const& rPolyPolygon, SalGradient const& rGradient, + bool bAntiAlias); void copyWithOperator(const SalTwoRect& rTR, cairo_surface_t* source, cairo_operator_t eOp, bool bAntiAlias); diff --git a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx index 557ac8960bca..da6845c84eea 100644 --- a/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx +++ b/vcl/unx/generic/gdi/X11CairoSalGraphicsImpl.cxx @@ -31,73 +31,36 @@ X11CairoSalGraphicsImpl::X11CairoSalGraphicsImpl(X11SalGraphics& rParent, CairoC void X11CairoSalGraphicsImpl::drawRect(tools::Long nX, tools::Long nY, tools::Long nWidth, tools::Long nHeight) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawRect(cr, &extents, mrCairoCommon.m_oLineColor, mrCairoCommon.m_oFillColor, - getAntiAlias(), nX, nY, nWidth, nHeight); - - mrCairoCommon.releaseCairoContext(cr, true, extents); + mrCairoCommon.drawRect(nX, nY, nWidth, nHeight, getAntiAlias()); } void X11CairoSalGraphicsImpl::drawPolygon(sal_uInt32 nPoints, const Point* pPtAry) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawPolygon(cr, &extents, mrCairoCommon.m_oLineColor, mrCairoCommon.m_oFillColor, - getAntiAlias(), nPoints, pPtAry); - - mrCairoCommon.releaseCairoContext(cr, true, extents); + mrCairoCommon.drawPolygon(nPoints, pPtAry, getAntiAlias()); } void X11CairoSalGraphicsImpl::drawPolyPolygon(sal_uInt32 nPoly, const sal_uInt32* pPointCounts, const Point** pPtAry) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawPolyPolygon(cr, &extents, mrCairoCommon.m_oLineColor, - mrCairoCommon.m_oFillColor, getAntiAlias(), nPoly, pPointCounts, - pPtAry); - - mrCairoCommon.releaseCairoContext(cr, true, extents); + mrCairoCommon.drawPolyPolygon(nPoly, pPointCounts, pPtAry, getAntiAlias()); } bool X11CairoSalGraphicsImpl::drawPolyPolygon(const basegfx::B2DHomMatrix& rObjectToDevice, const basegfx::B2DPolyPolygon& rPolyPolygon, double fTransparency) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - bool bRetVal(CairoCommon::drawPolyPolygon(cr, &extents, mrCairoCommon.m_oLineColor, - mrCairoCommon.m_oFillColor, getAntiAlias(), - rObjectToDevice, rPolyPolygon, fTransparency)); - - mrCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetVal; + return mrCairoCommon.drawPolyPolygon(rObjectToDevice, rPolyPolygon, fTransparency, + getAntiAlias()); } void X11CairoSalGraphicsImpl::drawPixel(tools::Long nX, tools::Long nY) { - drawPixel(nX, nY, *mrCairoCommon.m_oLineColor); + mrCairoCommon.drawPixel(mrCairoCommon.m_oLineColor, nX, nY, getAntiAlias()); } void X11CairoSalGraphicsImpl::drawPixel(tools::Long nX, tools::Long nY, Color aColor) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawPixel(cr, &extents, aColor, nX, nY); - - mrCairoCommon.releaseCairoContext(cr, true, extents); + mrCairoCommon.drawPixel(aColor, nX, nY, getAntiAlias()); } Color X11CairoSalGraphicsImpl::getPixel(tools::Long nX, tools::Long nY) @@ -108,26 +71,12 @@ Color X11CairoSalGraphicsImpl::getPixel(tools::Long nX, tools::Long nY) void X11CairoSalGraphicsImpl::drawLine(tools::Long nX1, tools::Long nY1, tools::Long nX2, tools::Long nY2) { - cairo_t* cr = mrCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawLine(cr, &extents, *mrCairoCommon.m_oLineColor, getAntiAlias(), nX1, nY1, nX2, - nY2); - - mrCairoCommon.releaseCairoContext(cr, false, extents); + mrCairoCommon.drawLine(nX1, nY1, nX2, nY2, getAntiAlias()); } void X11CairoSalGraphicsImpl::drawPolyLine(sal_uInt32 nPoints, const Point* pPtAry) { - cairo_t* cr = mrCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange aExtents; - mrCairoCommon.clipRegion(cr); - - CairoCommon::drawPolyLine(cr, &aExtents, *mrCairoCommon.m_oLineColor, getAntiAlias(), nPoints, - pPtAry); - - mrCairoCommon.releaseCairoContext(cr, false, aExtents); + mrCairoCommon.drawPolyLine(nPoints, pPtAry, getAntiAlias()); } bool X11CairoSalGraphicsImpl::drawPolyLine(const basegfx::B2DHomMatrix& rObjectToDevice, @@ -138,69 +87,27 @@ bool X11CairoSalGraphicsImpl::drawPolyLine(const basegfx::B2DHomMatrix& rObjectT css::drawing::LineCap eLineCap, double fMiterMinimumAngle, bool bPixelSnapHairline) { - // short circuit if there is nothing to do - if (0 == rPolyLine.count() || fTransparency < 0.0 || fTransparency >= 1.0) - return true; - - cairo_t* cr = mrCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange aExtents; - mrCairoCommon.clipRegion(cr); - - // Use the now available static drawPolyLine from the Cairo-Headless-Fallback - // that will take care of all needed stuff - bool bRetval(CairoCommon::drawPolyLine(cr, &aExtents, *mrCairoCommon.m_oLineColor, - getAntiAlias(), rObjectToDevice, rPolyLine, - fTransparency, fLineWidth, pStroke, eLineJoin, eLineCap, - fMiterMinimumAngle, bPixelSnapHairline)); - - mrCairoCommon.releaseCairoContext(cr, false, aExtents); - - return bRetval; + return mrCairoCommon.drawPolyLine(rObjectToDevice, rPolyLine, fTransparency, fLineWidth, + pStroke, eLineJoin, eLineCap, fMiterMinimumAngle, + bPixelSnapHairline, getAntiAlias()); } bool X11CairoSalGraphicsImpl::drawAlphaRect(tools::Long nX, tools::Long nY, tools::Long nWidth, tools::Long nHeight, sal_uInt8 nTransparency) { - cairo_t* cr = mrCairoCommon.getCairoContext(false, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - const bool bRetval(CairoCommon::drawAlphaRect(cr, &extents, *mrCairoCommon.m_oLineColor, - *mrCairoCommon.m_oFillColor, nX, nY, nWidth, - nHeight, nTransparency)); - mrCairoCommon.releaseCairoContext(cr, false, extents); - - return bRetval; + return mrCairoCommon.drawAlphaRect(nX, nY, nWidth, nHeight, nTransparency, getAntiAlias()); } bool X11CairoSalGraphicsImpl::drawGradient(const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - const bool bRetval( - CairoCommon::drawGradient(cr, &extents, getAntiAlias(), rPolyPolygon, rGradient)); - - mrCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetval; + return mrCairoCommon.drawGradient(rPolyPolygon, rGradient, getAntiAlias()); } bool X11CairoSalGraphicsImpl::implDrawGradient(basegfx::B2DPolyPolygon const& rPolyPolygon, SalGradient const& rGradient) { - cairo_t* cr = mrCairoCommon.getCairoContext(true, getAntiAlias()); - basegfx::B2DRange extents; - mrCairoCommon.clipRegion(cr); - - bool bRetVal( - CairoCommon::implDrawGradient(cr, &extents, getAntiAlias(), rPolyPolygon, rGradient)); - - mrCairoCommon.releaseCairoContext(cr, true, extents); - - return bRetVal; + return mrCairoCommon.implDrawGradient(rPolyPolygon, rGradient, getAntiAlias()); } bool X11CairoSalGraphicsImpl::hasFastDrawTransformedBitmap() const |