summaryrefslogtreecommitdiff
path: root/sw
diff options
context:
space:
mode:
authorArmin Le Grand <Armin.Le.Grand@cib.de>2017-11-16 18:47:29 +0100
committerArmin Le Grand <Armin.Le.Grand@cib.de>2017-11-18 13:07:47 +0100
commit487ac20ecd73cf3d98071ba30cf5597d957017f7 (patch)
tree8777e0a1e7917ab054723327a59089b264c4a567 /sw
parent059469926e359153b9b291790ef2df84fa63fda9 (diff)
RotateFlyFrame3: add support for AutoContour
For transformed FlyFrames with no Border and no Padding it would be nice to immediately start using AutoContour, added first implementation to do so. Added several conditions for AutoContour, need to work on reaction on changes to these. Corrected needed transform adaptions to Contour(s) Change-Id: Ia3d7845fd5d50c8a413d592ae07ce2041ccc91b9
Diffstat (limited to 'sw')
-rw-r--r--sw/source/core/doc/notxtfrm.cxx36
-rw-r--r--sw/source/core/draw/dflyobj.cxx8
-rw-r--r--sw/source/core/frmedt/fefly1.cxx2
-rw-r--r--sw/source/core/inc/flyfrms.hxx7
-rw-r--r--sw/source/core/layout/fly.cxx221
-rw-r--r--sw/source/core/layout/flylay.cxx71
-rw-r--r--sw/source/core/layout/frmtool.cxx20
-rw-r--r--sw/source/core/text/txtfly.cxx17
8 files changed, 273 insertions, 109 deletions
diff --git a/sw/source/core/doc/notxtfrm.cxx b/sw/source/core/doc/notxtfrm.cxx
index 93103489af70..1ebb9aaf0944 100644
--- a/sw/source/core/doc/notxtfrm.cxx
+++ b/sw/source/core/doc/notxtfrm.cxx
@@ -1308,15 +1308,47 @@ void SwNoTextFrame::PaintPicture( vcl::RenderContext* pOut, const SwRect &rGrfAr
bool SwNoTextFrame::IsTransparent() const
{
const SwViewShell* pSh = getRootFrame()->GetCurrShell();
+
if ( !pSh || !pSh->GetViewOptions()->IsGraphic() )
+ {
return true;
+ }
const SwGrfNode *pNd;
+
if( nullptr != (pNd = GetNode()->GetGrfNode()) )
- return pNd->IsTransparent();
+ {
+ if(pNd->IsTransparent())
+ {
+ return true;
+ }
+ }
+
+ // RotateFlyFrame3: If we are transformed, there are 'free' areas between
+ // the Graphic and the Border/Padding stuff - at least as long as those
+ // (Border and Padding) are not transformed, too
+ if(isTransformableSwFrame())
+ {
+ // we can be more specific - rotations of multiples of
+ // 90 degrees will leave no gaps. Go from [0.0 .. F_2PI]
+ // to [0 .. 360] and check modulo 90
+ const long nRot(static_cast<long>(getLocalFrameRotation() / F_PI180));
+ const bool bMultipleOf90(0 == (nRot % 90));
+
+ if(!bMultipleOf90)
+ {
+ return true;
+ }
+ }
//#29381# OLE are always transparent
- return true;
+ if(nullptr != GetNode()->GetOLENode())
+ {
+ return true;
+ }
+
+ // return false by default to avoid background paint
+ return false;
}
void SwNoTextFrame::StopAnimation( OutputDevice* pOut ) const
diff --git a/sw/source/core/draw/dflyobj.cxx b/sw/source/core/draw/dflyobj.cxx
index a4466f1f9085..2dd8cffbf300 100644
--- a/sw/source/core/draw/dflyobj.cxx
+++ b/sw/source/core/draw/dflyobj.cxx
@@ -632,9 +632,9 @@ void SwVirtFlyDrawObj::NbcSetLogicRect(const tools::Rectangle& )
// SwVirtFlyDrawObj::Move() and Resize()
void SwVirtFlyDrawObj::NbcMove(const Size& rSiz)
{
- if(GetFlyFrame()->IsFlyFreeFrame() && static_cast<SwFlyFreeFrame*>(GetFlyFrame())->isTransformableSwFrame())
+ if(GetFlyFrame()->IsFlyFreeFrame() && static_cast< SwFlyFreeFrame* >(GetFlyFrame())->isTransformableSwFrame())
{
- // When we have a change and are in transformed state (e.g. rotation used),
+ // RotateFlyFrame3: When we have a change and are in transformed state (e.g. rotation used),
// we need to fall back to the un-transformed state to keep the old code below
// working properly. Restore FrameArea and use aOutRect from old FrameArea.
TransformableSwFrame* pTransformableSwFrame(static_cast<SwFlyFreeFrame*>(GetFlyFrame())->getTransformableSwFrame());
@@ -825,7 +825,7 @@ void SwVirtFlyDrawObj::NbcCrop(const basegfx::B2DPoint& rRef, double fxFact, dou
const bool bIsTransformableSwFrame(
GetFlyFrame()->IsFlyFreeFrame() &&
- static_cast<SwFlyFreeFrame*>(GetFlyFrame())->isTransformableSwFrame());
+ static_cast< SwFlyFreeFrame* >(GetFlyFrame())->isTransformableSwFrame());
if(bIsTransformableSwFrame)
{
@@ -977,7 +977,7 @@ void SwVirtFlyDrawObj::NbcResize(const Point& rRef, const Fraction& xFact, const
const bool bUseRightEdge((bVertX && !bVertL2RX ) || bRTL);
const bool bIsTransformableSwFrame(
GetFlyFrame()->IsFlyFreeFrame() &&
- static_cast<SwFlyFreeFrame*>(GetFlyFrame())->isTransformableSwFrame());
+ static_cast< SwFlyFreeFrame* >(GetFlyFrame())->isTransformableSwFrame());
if(bIsTransformableSwFrame)
{
diff --git a/sw/source/core/frmedt/fefly1.cxx b/sw/source/core/frmedt/fefly1.cxx
index 105689dbf848..ece412fde57c 100644
--- a/sw/source/core/frmedt/fefly1.cxx
+++ b/sw/source/core/frmedt/fefly1.cxx
@@ -369,7 +369,7 @@ void SwFEShell::SetFlyPos( const Point& rAbsPos )
// Anchor and new RelPos will be calculated and set by the Fly
if ( pFly->IsFlyAtContentFrame() )
{
- if(pFly->IsFlyFreeFrame() && static_cast<SwFlyFreeFrame*>(pFly)->isTransformableSwFrame())
+ if(pFly->IsFlyFreeFrame() && static_cast< SwFlyFreeFrame* >(pFly)->isTransformableSwFrame())
{
// RotateFlyFrame3: When we have a change and are in transformed state (e.g. rotation used),
// we need to correct the absolute position (rAbsPos) which was created in
diff --git a/sw/source/core/inc/flyfrms.hxx b/sw/source/core/inc/flyfrms.hxx
index eaae5b89059d..1bde38f6784b 100644
--- a/sw/source/core/inc/flyfrms.hxx
+++ b/sw/source/core/inc/flyfrms.hxx
@@ -37,10 +37,10 @@ private:
// #i34753# - flag for at-page anchored Writer fly frames
// to prevent a positioning - call of method <MakeObjPos()> -, if Writer
// fly frame is already clipped during its format by the object formatter.
- bool mbNoMakePos;
+ bool mbNoMakePos : 1;
// #i37068# - flag to prevent move in method <CheckClip(..)>
- bool mbNoMoveOnCheckClip;
+ bool mbNoMoveOnCheckClip : 1;
SwRect maUnclippedFrame;
@@ -134,6 +134,9 @@ public:
TransformableSwFrame* getTransformableSwFrame() { return mpTransformableSwFrame.get(); }
const TransformableSwFrame* getTransformableSwFrame() const { return mpTransformableSwFrame.get(); }
+ // RotateFlyFrame3 - Support for AutoContour
+ bool supportsAutoContour() const;
+
// RotateFlyFrame3 - Support for Transformations
virtual basegfx::B2DHomMatrix getFrameAreaTransformation() const override;
virtual basegfx::B2DHomMatrix getFramePrintAreaTransformation() const override;
diff --git a/sw/source/core/layout/fly.cxx b/sw/source/core/layout/fly.cxx
index 5163fbb3f3c4..569a0ec86282 100644
--- a/sw/source/core/layout/fly.cxx
+++ b/sw/source/core/layout/fly.cxx
@@ -2303,8 +2303,18 @@ void SwFlyFrame::NotifyDrawObj()
pObj->SetRectsDirty();
pObj->SetChanged();
pObj->BroadcastObjectChange();
+
if ( GetFormat()->GetSurround().IsContour() )
+ {
+ ClrContourCache( pObj );
+ }
+ else if(IsFlyFreeFrame() && static_cast< const SwFlyFreeFrame* >(this)->supportsAutoContour())
+ {
+ // RotateFlyFrame3: Also need to clear when changes happen
+ // Caution: isTransformableSwFrame is already reset when resetting rotation, so
+ // *additionally* reset in SwFlyFreeFrame::MakeAll when no more rotation
ClrContourCache( pObj );
+ }
}
Size SwFlyFrame::CalcRel( const SwFormatFrameSize &rSz ) const
@@ -2435,120 +2445,141 @@ bool SwFlyFrame::GetContour( tools::PolyPolygon& rContour,
bool bRet = false;
const bool bIsCandidate(Lower() && Lower()->IsNoTextFrame());
- if(bIsCandidate && GetFormat()->GetSurround().IsContour())
+ if(bIsCandidate)
{
- SwNoTextNode *pNd = const_cast<SwNoTextNode*>(static_cast<const SwNoTextNode*>(static_cast<const SwContentFrame*>(Lower())->GetNode()));
- // OD 16.04.2003 #i13147# - determine <GraphicObject> instead of <Graphic>
- // in order to avoid load of graphic, if <SwNoTextNode> contains a graphic
- // node and method is called for paint.
- const GraphicObject* pGrfObj = nullptr;
- bool bGrfObjCreated = false;
- const SwGrfNode* pGrfNd = pNd->GetGrfNode();
- if ( pGrfNd && _bForPaint )
- {
- pGrfObj = &(pGrfNd->GetGrfObj());
- }
- else
- {
- pGrfObj = new GraphicObject( pNd->GetGraphic() );
- bGrfObjCreated = true;
- }
- OSL_ENSURE( pGrfObj, "SwFlyFrame::GetContour() - No Graphic/GraphicObject found at <SwNoTextNode>." );
- if ( pGrfObj && pGrfObj->GetType() != GraphicType::NONE )
+ const SwFlyFreeFrame* pSwFlyFreeFrame(static_cast< const SwFlyFreeFrame* >(this));
+
+ if(GetFormat()->GetSurround().IsContour())
{
- if( !pNd->HasContour() )
+ SwNoTextNode *pNd = const_cast<SwNoTextNode*>(static_cast<const SwNoTextNode*>(static_cast<const SwContentFrame*>(Lower())->GetNode()));
+ // OD 16.04.2003 #i13147# - determine <GraphicObject> instead of <Graphic>
+ // in order to avoid load of graphic, if <SwNoTextNode> contains a graphic
+ // node and method is called for paint.
+ const GraphicObject* pGrfObj = nullptr;
+ bool bGrfObjCreated = false;
+ const SwGrfNode* pGrfNd = pNd->GetGrfNode();
+ if ( pGrfNd && _bForPaint )
+ {
+ pGrfObj = &(pGrfNd->GetGrfObj());
+ }
+ else
{
- // OD 16.04.2003 #i13147# - no <CreateContour> for a graphic
- // during paint. Thus, return (value of <bRet> should be <false>).
- if ( pGrfNd && _bForPaint )
+ pGrfObj = new GraphicObject( pNd->GetGraphic() );
+ bGrfObjCreated = true;
+ }
+ OSL_ENSURE( pGrfObj, "SwFlyFrame::GetContour() - No Graphic/GraphicObject found at <SwNoTextNode>." );
+ if ( pGrfObj && pGrfObj->GetType() != GraphicType::NONE )
+ {
+ if( !pNd->HasContour() )
{
- OSL_FAIL( "SwFlyFrame::GetContour() - No Contour found at <SwNoTextNode> during paint." );
- return bRet;
+ // OD 16.04.2003 #i13147# - no <CreateContour> for a graphic
+ // during paint. Thus, return (value of <bRet> should be <false>).
+ if ( pGrfNd && _bForPaint )
+ {
+ OSL_FAIL( "SwFlyFrame::GetContour() - No Contour found at <SwNoTextNode> during paint." );
+ return bRet;
+ }
+ pNd->CreateContour();
}
- pNd->CreateContour();
- }
- pNd->GetContour( rContour );
- // The Node holds the Polygon matching the original size of the graphic
- // We need to include the scaling here
- SwRect aClip;
- SwRect aOrig;
- Lower()->Calc(pRenderContext);
- static_cast<const SwNoTextFrame*>(Lower())->GetGrfArea( aClip, &aOrig );
- // OD 16.04.2003 #i13147# - copy method code <SvxContourDlg::ScaleContour(..)>
- // in order to avoid that graphic has to be loaded for contour scale.
- //SvxContourDlg::ScaleContour( rContour, aGrf, MapUnit::MapTwip, aOrig.SSize() );
- {
- OutputDevice* pOutDev = Application::GetDefaultDevice();
- const MapMode aDispMap( MapUnit::MapTwip );
- const MapMode aGrfMap( pGrfObj->GetPrefMapMode() );
- const Size aGrfSize( pGrfObj->GetPrefSize() );
- Size aOrgSize;
- Point aNewPoint;
- bool bPixelMap = aGrfMap.GetMapUnit() == MapUnit::MapPixel;
-
- if ( bPixelMap )
- aOrgSize = pOutDev->PixelToLogic( aGrfSize, aDispMap );
- else
- aOrgSize = OutputDevice::LogicToLogic( aGrfSize, aGrfMap, aDispMap );
-
- if ( aOrgSize.Width() && aOrgSize.Height() )
+ pNd->GetContour( rContour );
+ // The Node holds the Polygon matching the original size of the graphic
+ // We need to include the scaling here
+ SwRect aClip;
+ SwRect aOrig;
+ Lower()->Calc(pRenderContext);
+ static_cast<const SwNoTextFrame*>(Lower())->GetGrfArea( aClip, &aOrig );
+ // OD 16.04.2003 #i13147# - copy method code <SvxContourDlg::ScaleContour(..)>
+ // in order to avoid that graphic has to be loaded for contour scale.
+ //SvxContourDlg::ScaleContour( rContour, aGrf, MapUnit::MapTwip, aOrig.SSize() );
{
- double fScaleX = (double) aOrig.Width() / aOrgSize.Width();
- double fScaleY = (double) aOrig.Height() / aOrgSize.Height();
+ OutputDevice* pOutDev = Application::GetDefaultDevice();
+ const MapMode aDispMap( MapUnit::MapTwip );
+ const MapMode aGrfMap( pGrfObj->GetPrefMapMode() );
+ const Size aGrfSize( pGrfObj->GetPrefSize() );
+ Size aOrgSize;
+ Point aNewPoint;
+ bool bPixelMap = aGrfMap.GetMapUnit() == MapUnit::MapPixel;
+
+ if ( bPixelMap )
+ aOrgSize = pOutDev->PixelToLogic( aGrfSize, aDispMap );
+ else
+ aOrgSize = OutputDevice::LogicToLogic( aGrfSize, aGrfMap, aDispMap );
- for ( sal_uInt16 j = 0, nPolyCount = rContour.Count(); j < nPolyCount; j++ )
+ if ( aOrgSize.Width() && aOrgSize.Height() )
{
- tools::Polygon& rPoly = rContour[ j ];
+ double fScaleX = (double) aOrig.Width() / aOrgSize.Width();
+ double fScaleY = (double) aOrig.Height() / aOrgSize.Height();
- for ( sal_uInt16 i = 0, nCount = rPoly.GetSize(); i < nCount; i++ )
+ for ( sal_uInt16 j = 0, nPolyCount = rContour.Count(); j < nPolyCount; j++ )
{
- if ( bPixelMap )
- aNewPoint = pOutDev->PixelToLogic( rPoly[ i ], aDispMap );
- else
- aNewPoint = OutputDevice::LogicToLogic( rPoly[ i ], aGrfMap, aDispMap );
+ tools::Polygon& rPoly = rContour[ j ];
+
+ for ( sal_uInt16 i = 0, nCount = rPoly.GetSize(); i < nCount; i++ )
+ {
+ if ( bPixelMap )
+ aNewPoint = pOutDev->PixelToLogic( rPoly[ i ], aDispMap );
+ else
+ aNewPoint = OutputDevice::LogicToLogic( rPoly[ i ], aGrfMap, aDispMap );
- rPoly[ i ] = Point( FRound( aNewPoint.getX() * fScaleX ), FRound( aNewPoint.getY() * fScaleY ) );
+ rPoly[ i ] = Point( FRound( aNewPoint.getX() * fScaleX ), FRound( aNewPoint.getY() * fScaleY ) );
+ }
}
}
}
+ // OD 17.04.2003 #i13147# - destroy created <GraphicObject>.
+ if ( bGrfObjCreated )
+ {
+ delete pGrfObj;
+ }
+ rContour.Move( aOrig.Left(), aOrig.Top() );
+ if( !aClip.Width() )
+ aClip.Width( 1 );
+ if( !aClip.Height() )
+ aClip.Height( 1 );
+ rContour.Clip( aClip.SVRect() );
+ rContour.Optimize(PolyOptimizeFlags::CLOSE);
+ bRet = true;
}
- // OD 17.04.2003 #i13147# - destroy created <GraphicObject>.
- if ( bGrfObjCreated )
+ }
+ else
+ {
+ if(nullptr != pSwFlyFreeFrame &&
+ pSwFlyFreeFrame->supportsAutoContour() &&
+ // isTransformableSwFrame already used in supportsAutoContour(), but
+ // better check twice when it may get changed there...
+ pSwFlyFreeFrame->isTransformableSwFrame())
{
- delete pGrfObj;
+ // RotateFlyFrame: use untransformed SwFrame to allow text floating around.
+ // Will be transformed below
+ const TransformableSwFrame* pTransformableSwFrame(pSwFlyFreeFrame->getTransformableSwFrame());
+ const SwRect aFrameArea(pTransformableSwFrame->getUntransformedFrameArea());
+ rContour = tools::PolyPolygon(tools::Polygon(aFrameArea.SVRect()));
+ bRet = (0 != rContour.Count());
}
- rContour.Move( aOrig.Left(), aOrig.Top() );
- if( !aClip.Width() )
- aClip.Width( 1 );
- if( !aClip.Height() )
- aClip.Height( 1 );
- rContour.Clip( aClip.SVRect() );
- rContour.Optimize(PolyOptimizeFlags::CLOSE);
- bRet = true;
}
- }
- if(bRet &&
- rContour.Count() &&
- IsFlyFreeFrame() &&
- static_cast<const SwFlyFreeFrame*>(this)->isTransformableSwFrame())
- {
- // RotateFlyFrame: Need to adapt contour to transformation
- basegfx::B2DVector aScale, aTranslate;
- double fRotate, fShearX;
- getFrameAreaTransformation().decompose(aScale, aTranslate, fRotate, fShearX);
-
- if(!basegfx::fTools::equalZero(fRotate))
- {
- basegfx::B2DPolyPolygon aSource(rContour.getB2DPolyPolygon());
- const basegfx::B2DPoint aCenter(getFrameAreaTransformation() * basegfx::B2DPoint(0.5, 0.5));
- const basegfx::B2DHomMatrix aRotateAroundCenter(
- basegfx::utils::createRotateAroundPoint(
- aCenter.getX(),
- aCenter.getY(),
- fRotate));
- aSource.transform(aRotateAroundCenter);
- rContour = tools::PolyPolygon(aSource);
+ if(bRet &&
+ 0 != rContour.Count() &&
+ nullptr != pSwFlyFreeFrame &&
+ pSwFlyFreeFrame->isTransformableSwFrame())
+ {
+ // Need to adapt contour to transformation
+ basegfx::B2DVector aScale, aTranslate;
+ double fRotate, fShearX;
+ getFrameAreaTransformation().decompose(aScale, aTranslate, fRotate, fShearX);
+
+ if(!basegfx::fTools::equalZero(fRotate))
+ {
+ basegfx::B2DPolyPolygon aSource(rContour.getB2DPolyPolygon());
+ const basegfx::B2DPoint aCenter(getFrameAreaTransformation() * basegfx::B2DPoint(0.5, 0.5));
+ const basegfx::B2DHomMatrix aRotateAroundCenter(
+ basegfx::utils::createRotateAroundPoint(
+ aCenter.getX(),
+ aCenter.getY(),
+ fRotate));
+ aSource.transform(aRotateAroundCenter);
+ rContour = tools::PolyPolygon(aSource);
+ }
}
}
diff --git a/sw/source/core/layout/flylay.cxx b/sw/source/core/layout/flylay.cxx
index 8a8c714ef351..8f6452b9b874 100644
--- a/sw/source/core/layout/flylay.cxx
+++ b/sw/source/core/layout/flylay.cxx
@@ -27,6 +27,7 @@
#include <hints.hxx>
#include <sectfrm.hxx>
#include <notxtfrm.hxx>
+#include <txtfly.hxx>
#include <svx/svdpage.hxx>
#include <editeng/ulspitem.hxx>
@@ -42,6 +43,7 @@
#include <IDocumentSettingAccess.hxx>
#include <IDocumentDrawModelAccess.hxx>
#include <basegfx/matrix/b2dhommatrixtools.hxx>
+#include <svx/sdr/attribute/sdrallfillattributeshelper.hxx>
using namespace ::com::sun::star;
@@ -87,6 +89,8 @@ void SwFlyFreeFrame::DestroyImpl()
SwFlyFreeFrame::~SwFlyFreeFrame()
{
+ // we are possibly in ContourCache, make sure we vanish
+ ::ClrContourCache(GetVirtDrawObj());
}
// #i28701#
@@ -268,6 +272,14 @@ void SwFlyFreeFrame::MakeAll(vcl::RenderContext* /*pRenderContext*/)
}
else
{
+ // RotateFlyFrame3: Also need to clear ContourCache (if used),
+ // usually done in SwFlyFrame::NotifyDrawObj, but there relies on
+ // being in transform mode which is already resetted then
+ if(isTransformableSwFrame())
+ {
+ ::ClrContourCache(GetVirtDrawObj());
+ }
+
// reset transformations to show that they are not used
mpTransformableSwFrame.reset();
}
@@ -283,6 +295,65 @@ void SwFlyFreeFrame::MakeAll(vcl::RenderContext* /*pRenderContext*/)
#endif
}
+bool SwFlyFreeFrame::supportsAutoContour() const
+{
+ if(!isTransformableSwFrame())
+ {
+ // support only when transformed, else there is no free space
+ return false;
+ }
+
+ // Check for Borders. If we have Borders, do (currently) not support,
+ // since borders do not transform with the object.
+ // (Will need to be enhanced to take into account if we have Borders and if these
+ // transform with the object)
+ SwBorderAttrAccess aAccess(SwFrame::GetCache(), this);
+ const SwBorderAttrs &rAttrs(*aAccess.Get());
+
+ if(rAttrs.IsLine())
+ {
+ return false;
+ }
+
+ // Check for Padding. Do not support when padding is used, this will
+ // produce a covered space around the object (filled with fill defines)
+ const SfxPoolItem* pItem(nullptr);
+
+ if(GetFormat() && SfxItemState::SET == GetFormat()->GetItemState(RES_BOX, false, &pItem))
+ {
+ const SvxBoxItem& rBox = *static_cast< const SvxBoxItem* >(pItem);
+
+ if(rBox.HasBorder(/*bTreatPaddingAsBorder*/true))
+ {
+ return false;
+ }
+ }
+
+ // check for Fill - if we have fill, it will fill the gaps and we will not
+ // support AutoContour
+ if(GetFormat() && GetFormat()->supportsFullDrawingLayerFillAttributeSet())
+ {
+ const drawinglayer::attribute::SdrAllFillAttributesHelperPtr aFillAttributes(GetFormat()->getSdrAllFillAttributesHelper());
+
+ if(aFillAttributes.get() && aFillAttributes->isUsed())
+ {
+ return false;
+ }
+ }
+ else
+ {
+ const SvxBrushItem aBack(GetFormat()->makeBackgroundBrushItem());
+
+ if(aBack.isUsed())
+ {
+ return false;
+ }
+ }
+
+ // else, support
+ return true;
+}
+
// RotateFlyFrame3 - Support for Transformations - outer frame
basegfx::B2DHomMatrix SwFlyFreeFrame::getFrameAreaTransformation() const
{
diff --git a/sw/source/core/layout/frmtool.cxx b/sw/source/core/layout/frmtool.cxx
index 7144ee460dcd..2276f7fa2b99 100644
--- a/sw/source/core/layout/frmtool.cxx
+++ b/sw/source/core/layout/frmtool.cxx
@@ -2740,11 +2740,23 @@ void Notify( SwFlyFrame *pFly, SwPageFrame *pOld, const SwRect &rOld,
pFly->NotifyBackground( pOld, aTmp, PREP_FLY_CHGD );
}
}
- else if ( pOldPrt && *pOldPrt != pFly->getFramePrintArea() &&
- pFly->GetFormat()->GetSurround().IsContour() )
+ else if(pOldPrt && *pOldPrt != pFly->getFramePrintArea())
{
- // #i24097#
- pFly->NotifyBackground( pFly->FindPageFrame(), aFrame, PREP_FLY_ARRIVE );
+ bool bNotifyBackground(pFly->GetFormat()->GetSurround().IsContour());
+
+ if(!bNotifyBackground &&
+ pFly->IsFlyFreeFrame() &&
+ static_cast< const SwFlyFreeFrame* >(pFly)->supportsAutoContour())
+ {
+ // RotateFlyFrame3: Also notify for FlyFrames which allow AutoContour
+ bNotifyBackground = true;
+ }
+
+ if(bNotifyBackground)
+ {
+ // #i24097#
+ pFly->NotifyBackground( pFly->FindPageFrame(), aFrame, PREP_FLY_ARRIVE );
+ }
}
}
diff --git a/sw/source/core/text/txtfly.cxx b/sw/source/core/text/txtfly.cxx
index fff55186d725..2fb5c47a38a4 100644
--- a/sw/source/core/text/txtfly.cxx
+++ b/sw/source/core/text/txtfly.cxx
@@ -177,7 +177,22 @@ const SwRect SwContourCache::CalcBoundRect( const SwAnchoredObject* pAnchoredObj
{
SwRect aRet;
const SwFrameFormat* pFormat = &(pAnchoredObj->GetFrameFormat());
- if( pFormat->GetSurround().IsContour() &&
+ bool bHandleContour(pFormat->GetSurround().IsContour());
+
+ if(!bHandleContour)
+ {
+ // RotateFlyFrame3: Object has no set contour, but for rotated
+ // FlyFrames we can create a 'default' contour to make text
+ // flow around the free, non-covered
+ const SwFlyFreeFrame* pSwFlyFreeFrame(dynamic_cast< const SwFlyFreeFrame* >(pAnchoredObj));
+
+ if(nullptr != pSwFlyFreeFrame && pSwFlyFreeFrame->supportsAutoContour())
+ {
+ bHandleContour = true;
+ }
+ }
+
+ if( bHandleContour &&
( dynamic_cast< const SwFlyFrame *>( pAnchoredObj ) == nullptr ||
( static_cast<const SwFlyFrame*>(pAnchoredObj)->Lower() &&
static_cast<const SwFlyFrame*>(pAnchoredObj)->Lower()->IsNoTextFrame() ) ) )