sw/qa/extras/ooxmlexport/ooxmlexport17.cxx | 7 +++ sw/source/core/doc/doclay.cxx | 46 ++++------------------- sw/source/core/unocore/unodraw.cxx | 11 +++++ sw/source/writerfilter/dmapper/GraphicImport.cxx | 13 ++++-- 4 files changed, 35 insertions(+), 42 deletions(-)
New commits: commit d97775f3eec51021d4db60ef6d3cc542f5207827 Author: Michael Stahl <[email protected]> AuthorDate: Tue Nov 4 14:38:32 2025 +0100 Commit: Michael Stahl <[email protected]> CommitDate: Thu Nov 6 09:38:59 2025 +0100 sw: fix SwDoc::IsInHeaderFooter() with flys If the node is in a fly, this can only print: sw/source/core/doc/doclay.cxx:1619: Found a FlySection but not a Format! This is a regression from commit e07feb9457f2ffb373ae69b73dda290140e4005f which used the wrong node's anchored objects: of course the fly is never anchored to itself, so this will never find anything. It turns out that there is already a function SwNode::GetFlyFormat() that can do most of the work, even using the layout to speed it up, so just use that to get the anchor. Change-Id: I7a22231f929175ed7c5c11724882b03890781cfc Reviewed-on: https://gerrit.libreoffice.org/c/core/+/193476 Reviewed-by: Michael Stahl <[email protected]> Tested-by: Jenkins diff --git a/sw/source/core/doc/doclay.cxx b/sw/source/core/doc/doclay.cxx index fdef5c76f427..8624bb4da50e 100644 --- a/sw/source/core/doc/doclay.cxx +++ b/sw/source/core/doc/doclay.cxx @@ -1577,48 +1577,20 @@ bool SwDoc::IsInHeaderFooter( const SwNode& rIdx ) const const SwNode* pFlyNd = pNd->FindFlyStartNode(); while( pFlyNd ) { - // get up by using the Anchor -#if OSL_DEBUG_LEVEL > 0 - std::vector<const SwFrameFormat*> checkFormats; - for(sw::SpzFrameFormat* pFormat: *GetSpzFrameFormats()) - { - const SwNodeIndex* pIdx = pFormat->GetContent().GetContentIdx(); - if( pIdx && pFlyNd == &pIdx->GetNode() ) - checkFormats.push_back( pFormat ); - } -#endif - std::vector<SwFrameFormat*> const & rFlys(pFlyNd->GetAnchoredFlys()); - bool bFound(false); - for (size_t i = 0; i < rFlys.size(); ++i) + // go up by using the Anchor + SwFormatAnchor const& rAnchor{pNd->GetFlyFormat()->GetAnchor()}; + if (rAnchor.GetAnchorId() == RndStdIds::FLY_AT_PAGE) { - const SwFrameFormat *const pFormat = rFlys[i]; - const SwNodeIndex* pIdx = pFormat->GetContent().GetContentIdx(); - if( pIdx && pFlyNd == &pIdx->GetNode() ) - { -#if OSL_DEBUG_LEVEL > 0 - auto checkPos = std::find( - checkFormats.begin(), checkFormats.end(), pFormat ); - assert( checkPos != checkFormats.end()); - checkFormats.erase( checkPos ); -#endif - const SwFormatAnchor& rAnchor = pFormat->GetAnchor(); - if ((RndStdIds::FLY_AT_PAGE == rAnchor.GetAnchorId()) || - !rAnchor.GetAnchorNode() ) - { - return false; - } - - pNd = rAnchor.GetAnchorNode(); - pFlyNd = pNd->FindFlyStartNode(); - bFound = true; - break; - } + return false; } - if (!bFound) + if (rAnchor.GetAnchorNode() == nullptr) { - OSL_ENSURE(mbInReading, "Found a FlySection but not a Format!"); + assert(mbInReading); return false; } + assert(pNd != rAnchor.GetAnchorNode()); + pNd = rAnchor.GetAnchorNode(); + pFlyNd = pNd->FindFlyStartNode(); } return nullptr != pNd->FindHeaderStartNode() || commit 9e330d0562ac57b902ff7d7ec7e7d8798ecd5e30 Author: Michael Stahl <[email protected]> AuthorDate: Tue Nov 4 16:11:56 2025 +0100 Commit: Michael Stahl <[email protected]> CommitDate: Thu Nov 6 09:38:56 2025 +0100 sw: prevent anchoring SwXShape to its own textbox SwXShape::setPropertyValue() allows anchoring a shape to its own textbox; this actually happens in testTdf146955. Detect this and throw IllegalArgumentException. Also catch the exception in GraphicImport::lcl_attribute() so the test doesn't fail. Change-Id: I236e12384e07793e0cf3474fc92657967d9249f0 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/193475 Reviewed-by: Michael Stahl <[email protected]> Tested-by: Jenkins diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport17.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport17.cxx index 1e7e8ce727dc..192d8c6c80c0 100644 --- a/sw/qa/extras/ooxmlexport/ooxmlexport17.cxx +++ b/sw/qa/extras/ooxmlexport/ooxmlexport17.cxx @@ -976,7 +976,12 @@ DECLARE_OOXMLEXPORT_TEST(testTdf144563, "tdf144563.docx") #if !defined(_WIN32) CPPUNIT_TEST_FIXTURE(Test, testTdf146955) { - loadAndReload("tdf146955.odt"); + auto const url{createFileURL(u"tdf146955.odt")}; + std::cout << url << ": "; + loadFromURL(url, nullptr); + save(mpFilter, nullptr); + std::cout << maTempFile.GetURL() << ": "; + loadFromURL(maTempFile.GetURL(), nullptr); // import of a (broken?) DOCX export with dozens of frames raised a SAX exception, // when the code tried to access to a non-existent footnote uno::Reference<text::XFootnotesSupplier> xNotes(mxComponent, uno::UNO_QUERY); diff --git a/sw/source/core/unocore/unodraw.cxx b/sw/source/core/unocore/unodraw.cxx index cc59b24dba70..fecc1edc2281 100644 --- a/sw/source/core/unocore/unodraw.cxx +++ b/sw/source/core/unocore/unodraw.cxx @@ -1142,6 +1142,17 @@ void SwXShape::setPropertyValue(const OUString& rPropertyName, const uno::Any& a throw uno::RuntimeException(); } + if (SwStartNode const*const pFly{pInternalPam->GetPoint()->GetNode().FindFlyStartNode()}) + { + if (SwFrameFormat const*const pTextBox{SwTextBoxHelper::getOtherTextBoxFormat(pFormat, RES_DRAWFRMFMT)}) + { + if (pFly == &pTextBox->GetContent().GetContentIdx()->GetNode()) + { + throw lang::IllegalArgumentException(u"cannot anchor object to itself"_ustr, nullptr, 1); + } + } + } + if (aAnchor.GetAnchorId() == RndStdIds::FLY_AS_CHAR) { //delete old SwFormatFlyCnt diff --git a/sw/source/writerfilter/dmapper/GraphicImport.cxx b/sw/source/writerfilter/dmapper/GraphicImport.cxx index 93f8c6f99f4e..891f287741d0 100644 --- a/sw/source/writerfilter/dmapper/GraphicImport.cxx +++ b/sw/source/writerfilter/dmapper/GraphicImport.cxx @@ -903,10 +903,15 @@ void GraphicImport::lcl_attribute(Id nName, const Value& rValue) if (!xServiceInfo->supportsService(u"com.sun.star.text.TextFrame"_ustr)) { bKeepRotation = true; - xShapeProps->setPropertyValue - (getPropertyName(PROP_TEXT_RANGE), - uno::Any - (m_rDomainMapper.GetCurrentTextRange())); + try + { + xShapeProps->setPropertyValue(getPropertyName(PROP_TEXT_RANGE), + uno::Any(m_rDomainMapper.GetCurrentTextRange())); + } + catch (lang::IllegalArgumentException const&) + { + SAL_WARN("writerfilter", "GraphicImport::lcl_attribute: cannot set anchor"); + } } awt::Size aSize(m_xShape->getSize());
