sw/qa/core/layout/data/shape-left-padding-wrap-through-off-page.docx |binary sw/qa/core/layout/fly.cxx | 28 ++++++++++ sw/source/core/layout/fly.cxx | 14 +++-- 3 files changed, 37 insertions(+), 5 deletions(-)
New commits: commit a29cea19d594e20bae8ce3c43c8a348bde5e78e6 Author: Miklos Vajna <vmik...@collabora.com> AuthorDate: Wed Mar 26 09:54:35 2025 +0100 Commit: Miklos Vajna <vmik...@collabora.com> CommitDate: Wed Mar 26 14:21:43 2025 +0100 tdf#165020 sw DoNotCaptureDrawObjsOnPage: fix left padding for wrap through Open the bugdoc, the left shapre is partially outside the page frame, but is not captured. This is fine, but the text should be clipped in a way that only the right half is visible, and instead the left half is visible. This went wrong in commit 61692b82ae4ff62662509b5979a7aabc7d380678 (tdf#161635 sw DoNotCaptureDrawObjsOnPage: fix handling of left padding, 2024-06-19), where I assumed that in case the left paddig is increased in Word for these partially off-page shapes, then that happens unconditionally. Fix the new use-case by only doing this for non-wrap-through shapes: this restores the lack of increased left padding for the new use-case and keeps the old one fixed. Special-casing the 'wrap mode == through' case for off-page positioning is not new, SwAnchoredObject::IsDraggingOffPageAllowed() and SwAnchoredObjectPosition::GetInfoAboutObj() also takes it into account. Change-Id: I07dec72e860c810a753c2c356f8f32cc2178b012 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/183339 Reviewed-by: Miklos Vajna <vmik...@collabora.com> Tested-by: Jenkins (cherry picked from commit 44b4ff646ea21df75f9e35b885d76d1aa0d61682) Reviewed-on: https://gerrit.libreoffice.org/c/core/+/183343 diff --git a/sw/qa/core/layout/data/shape-left-padding-wrap-through-off-page.docx b/sw/qa/core/layout/data/shape-left-padding-wrap-through-off-page.docx new file mode 100644 index 000000000000..0b84082d6996 Binary files /dev/null and b/sw/qa/core/layout/data/shape-left-padding-wrap-through-off-page.docx differ diff --git a/sw/qa/core/layout/fly.cxx b/sw/qa/core/layout/fly.cxx index de227280bc55..8276f442a8b3 100644 --- a/sw/qa/core/layout/fly.cxx +++ b/sw/qa/core/layout/fly.cxx @@ -141,6 +141,34 @@ CPPUNIT_TEST_FIXTURE(Test, testShapeLeftPaddingOffPage) // i.e. the shape text had ~4cm left padding (visually) instead of 5cm. CPPUNIT_ASSERT_GREATEREQUAL(nBodyLeft - MINFLY, nFlyLeft); } + +CPPUNIT_TEST_FIXTURE(Test, testShapeLeftPaddingWrapThroughOffPage) +{ + // Given a document with a shape that is off the page (partially clipped on the left): + createSwDoc("shape-left-padding-wrap-through-off-page.docx"); + + // When laying out that document: + SwDoc* pDoc = getSwDoc(); + SwRootFrame* pLayout = pDoc->getIDocumentLayoutAccess().GetCurrentLayout(); + + // Then make sure that the text is also clipped on the left, left margin is only the + // lIns="91440" (in EMUs) from the file: + auto pPage = pLayout->GetLower()->DynCastPageFrame(); + SwSortedObjs& rPageObjs = *pPage->GetSortedObjs(); + CPPUNIT_ASSERT_EQUAL(static_cast<size_t>(2), rPageObjs.size()); + auto it = std::find_if(rPageObjs.begin(), rPageObjs.end(), [](SwAnchoredObject* pObj) -> bool { + return pObj->DynCastFlyFrame() != nullptr; + }); + CPPUNIT_ASSERT(it != rPageObjs.end()); + auto pFly = (*it)->DynCastFlyFrame(); + CPPUNIT_ASSERT(pFly); + SwTwips nFlyLeftMargin = pFly->getFramePrintArea().Left(); + // Without the accompanying fix in place, this test would have failed with: + // - Expected: 144 + // - Actual : 3031 + // i.e. there was a large left margin, the text was clipped on the right. + CPPUNIT_ASSERT_EQUAL(static_cast<SwTwips>(144), nFlyLeftMargin); +} } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/core/layout/fly.cxx b/sw/source/core/layout/fly.cxx index f174143288e7..1a7caee5969d 100644 --- a/sw/source/core/layout/fly.cxx +++ b/sw/source/core/layout/fly.cxx @@ -2071,12 +2071,16 @@ void SwFlyFrame::MakePrtArea( const SwBorderAttrs &rAttrs ) // The fly frame may be partially outside the page, check for this case. SwPageFrame* pPageFrame = FindPageFrame(); - SwFrameFormat* pFormat = GetFormat(); - if (pPageFrame && pFormat) - { - const IDocumentSettingAccess& rIDSA = pFormat->getIDocumentSettingAccess(); + SwFrameFormat* pFlyFormat = GetFormat(); + SwFrameFormat* pDrawFormat = SwTextBoxHelper::getOtherTextBoxFormat(pFlyFormat, RES_FLYFRMFMT); + const SwFrameFormat* pFormat = pDrawFormat ? pDrawFormat : pFlyFormat; + // Don't increase the left padding if the wrap mode is through. + bool bIsWrapThrough = pFormat && pFormat->GetSurround().GetSurround() == text::WrapTextMode::WrapTextMode_THROUGH; + if (pPageFrame && pFlyFormat && !bIsWrapThrough) + { + const IDocumentSettingAccess& rIDSA = pFlyFormat->getIDocumentSettingAccess(); bool bDoNotCaptureDrawObjsOnPage = rIDSA.get(DocumentSettingId::DO_NOT_CAPTURE_DRAW_OBJS_ON_PAGE); - bool bLRTB = pFormat->GetFrameDir().GetValue() == SvxFrameDirection::Horizontal_LR_TB; + bool bLRTB = pFlyFormat->GetFrameDir().GetValue() == SvxFrameDirection::Horizontal_LR_TB; SwTwips nFlyLeft = getFrameArea().Left(); SwTwips nPageLeft = pPageFrame->getFrameArea().Left(); if (bDoNotCaptureDrawObjsOnPage && bLRTB && nFlyLeft < nPageLeft)