summaryrefslogtreecommitdiff
path: root/sw
diff options
context:
space:
mode:
authorMiklos Vajna <vmiklos@collabora.co.uk>2017-05-26 13:54:27 +0200
committerMiklos Vajna <vmiklos@collabora.co.uk>2017-05-31 13:43:24 +0200
commit657a01ef00064f8f7cf7e81582f44064417321a8 (patch)
tree45d34020ee6dec09eece0cea481e15bcb1027564 /sw
parent1f8beedc2579457876e35dac91260c3c6e97f7ac (diff)
tdf#108056 sw SubtractFlys: work with a polypolygon directly
In case the intention is that the clip rectangle should include the page, except a fly frame, we built a list of rectangles that covered this area. This introduces the problem if adjacent rectangles don't join perfectly. Instead allow lcl_SubtractFlys() to work on a clip state directly, this way the clip polypolygon will only contain two paths (the page rectangle and the rectangle of the fly), so rounding errors can't happen. Change-Id: I5b2e9a382aa7d16f3b16509670de754b5e00bd6d Reviewed-on: https://gerrit.libreoffice.org/38066 Reviewed-by: Miklos Vajna <vmiklos@collabora.co.uk> Tested-by: Jenkins <ci@libreoffice.org> (cherry picked from commit 87d62a6222932d36c91d7b69240c7bccbf4e46be) Reviewed-on: https://gerrit.libreoffice.org/38261
Diffstat (limited to 'sw')
-rw-r--r--sw/source/core/doc/notxtfrm.cxx3
-rw-r--r--sw/source/core/inc/frmtool.hxx2
-rw-r--r--sw/source/core/layout/paintfrm.cxx28
3 files changed, 16 insertions, 17 deletions
diff --git a/sw/source/core/doc/notxtfrm.cxx b/sw/source/core/doc/notxtfrm.cxx
index 87a7b43c9055..4156753cf966 100644
--- a/sw/source/core/doc/notxtfrm.cxx
+++ b/sw/source/core/doc/notxtfrm.cxx
@@ -186,7 +186,8 @@ static void lcl_ClearArea( const SwFrame &rFrame,
if ( rFrame.GetBackgroundBrush( aFillAttributes, pItem, pCol, aOrigRect, false ) )
{
SwRegionRects const region(rPtArea);
- const bool bDone(::DrawFillAttributes(aFillAttributes, aOrigRect, region, rOut));
+ basegfx::tools::B2DClipState aClipState;
+ const bool bDone(::DrawFillAttributes(aFillAttributes, aOrigRect, region, aClipState, rOut));
if(!bDone)
{
diff --git a/sw/source/core/inc/frmtool.hxx b/sw/source/core/inc/frmtool.hxx
index 81453b10487c..b9093eb523c5 100644
--- a/sw/source/core/inc/frmtool.hxx
+++ b/sw/source/core/inc/frmtool.hxx
@@ -27,6 +27,7 @@
#include <editeng/lrspitem.hxx>
#include <swfont.hxx>
#include <flyfrm.hxx>
+#include <basegfx/tools/b2dclipstate.hxx>
class SwPageFrame;
class SwFlyFrame;
@@ -68,6 +69,7 @@ bool DrawFillAttributes(
const drawinglayer::attribute::SdrAllFillAttributesHelperPtr& rFillAttributes,
const SwRect& rOriginalLayoutRect,
const SwRegionRects& rPaintRegion,
+ const basegfx::tools::B2DClipState& rClipState,
OutputDevice& rOut);
void paintGraphicUsingPrimitivesHelper(
diff --git a/sw/source/core/layout/paintfrm.cxx b/sw/source/core/layout/paintfrm.cxx
index 1cd629dacba3..bb6ca5a7e2eb 100644
--- a/sw/source/core/layout/paintfrm.cxx
+++ b/sw/source/core/layout/paintfrm.cxx
@@ -1533,7 +1533,7 @@ static void lcl_ExtendLeftAndRight( SwRect& _rRect,
}
static void lcl_SubtractFlys( const SwFrame *pFrame, const SwPageFrame *pPage,
- const SwRect &rRect, SwRegionRects &rRegion, SwPaintProperties & rProperties)
+ const SwRect &rRect, SwRegionRects &rRegion, basegfx::tools::B2DClipState& rClipState, SwPaintProperties & rProperties)
{
const SwSortedObjs& rObjs = *pPage->GetSortedObjs();
const SwFlyFrame* pSelfFly = pFrame->IsInFly() ? pFrame->FindFlyFrame() : gProp.pSRetoucheFly2;
@@ -1666,6 +1666,7 @@ static void lcl_SubtractFlys( const SwFrame *pFrame, const SwPageFrame *pPage,
const SwBorderAttrs &rAttrs = *aAccess.Get();
::lcl_CalcBorderRect( aRect, pFly, rAttrs, true, rProperties );
rRegion -= aRect;
+ rClipState.subtractRange(basegfx::B2DRange(aRect.Left(), aRect.Top(), aRect.Right(), aRect.Bottom()));
continue;
}
else
@@ -1683,12 +1684,14 @@ static void lcl_SubtractFlys( const SwFrame *pFrame, const SwPageFrame *pPage,
const SwBorderAttrs &rAttrs = *aAccess.Get();
::lcl_CalcBorderRect( aRect, pFly, rAttrs, true, rProperties );
rRegion -= aRect;
+ rClipState.subtractRange(basegfx::B2DRange(aRect.Left(), aRect.Top(), aRect.Right(), aRect.Bottom()));
}
else
{
SwRect aRect( pFly->Prt() );
aRect += pFly->Frame().Pos();
rRegion -= aRect;
+ rClipState.subtractRange(basegfx::B2DRange(aRect.Left(), aRect.Top(), aRect.Right(), aRect.Bottom()));
}
}
if (gProp.pSRetoucheFly == gProp.pSRetoucheFly2)
@@ -1854,6 +1857,7 @@ bool DrawFillAttributes(
const drawinglayer::attribute::SdrAllFillAttributesHelperPtr& rFillAttributes,
const SwRect& rOriginalLayoutRect,
const SwRegionRects& rPaintRegion,
+ const basegfx::tools::B2DClipState& rClipState,
vcl::RenderContext& rOut)
{
if(rFillAttributes.get() && rFillAttributes->isUsed())
@@ -1916,18 +1920,7 @@ bool DrawFillAttributes(
// tdf#86578 the awful lcl_SubtractFlys hack
if (rPaintRegion.size() > 1 || rPaintRegion[0] != rPaintRegion.GetOrigin())
{
- tools::PolyPolygon tempRegion;
- for (size_t i = 0; i < rPaintRegion.size(); ++i)
- {
- // Don't use SwRect::SvRect() here, as the clip
- // rectangle is supposed to cover everything outside
- // the flys, so the Width() - 1 isn't correct.
- const SwRect& rRect = rPaintRegion[i];
- tools::Rectangle aRectangle(rRect.Pos().getX(), rRect.Pos().getY(), rRect.Pos().getX() + rRect.SSize().getWidth(), rRect.Pos().getY() + rRect.SSize().getHeight());
- tempRegion.Insert(tools::Polygon(aRectangle));
- }
- basegfx::B2DPolyPolygon const maskRegion( tempRegion.getB2DPolyPolygon());
-
+ basegfx::B2DPolyPolygon const maskRegion(rClipState.getClipPoly());
primitives.resize(1);
primitives[0] = new drawinglayer::primitive2d::MaskPrimitive2D(
maskRegion, rSequence);
@@ -4681,7 +4674,8 @@ void SwFrame::PaintBorderLine( const SwRect& rRect,
pPage->GetFormat()->GetDoc()->getIDocumentSettingAccess().get(DocumentSettingId::SUBTRACT_FLYS))
{
SwRegionRects aRegion( aOut, 4 );
- ::lcl_SubtractFlys( this, pPage, aOut, aRegion, gProp );
+ basegfx::tools::B2DClipState aClipState;
+ ::lcl_SubtractFlys( this, pPage, aOut, aRegion, aClipState, gProp );
for ( size_t i = 0; i < aRegion.size(); ++i )
gProp.pSLines->AddLineRect( aRegion[i], pColor, nStyle, pTab, nSubCol, gProp );
}
@@ -6588,10 +6582,12 @@ void SwFrame::PaintBackground( const SwRect &rRect, const SwPageFrame *pPage,
}
SwRegionRects aRegion( aRect );
+ basegfx::B2DPolygon aB2DPolygon{tools::Polygon(aRect.SVRect()).getB2DPolygon()};
+ basegfx::tools::B2DClipState aClipState{basegfx::B2DPolyPolygon(aB2DPolygon)};
if (pPage->GetSortedObjs() &&
pSh->GetDoc()->getIDocumentSettingAccess().get(DocumentSettingId::SUBTRACT_FLYS))
{
- ::lcl_SubtractFlys( this, pPage, aRect, aRegion, gProp );
+ ::lcl_SubtractFlys( this, pPage, aRect, aRegion, aClipState, gProp );
}
// OD 06.08.2002 #99657# - determine, if background transparency
@@ -6608,7 +6604,7 @@ void SwFrame::PaintBackground( const SwRect &rRect, const SwPageFrame *pPage,
if(aFillAttributes->isUsed())
{
// check if really something is painted
- bDone = DrawFillAttributes(aFillAttributes, aOrigBackRect, aRegion, *pOut);
+ bDone = DrawFillAttributes(aFillAttributes, aOrigBackRect, aRegion, aClipState, *pOut);
}
if(!bDone)