[Libreoffice-commits] core.git: Branch 'libreoffice-7-0' - 2 commits - sw/qa sw/source
Michael Stahl (via logerrit)
logerrit at kemper.freedesktop.org
Thu May 28 10:45:20 UTC 2020
sw/qa/extras/uiwriter/data2/tdf132236.odt |binary
sw/qa/extras/uiwriter/uiwriter2.cxx | 24 +++++++++++++
sw/qa/extras/uiwriter/uiwriter3.cxx | 9 +++++
sw/source/core/layout/frmtool.cxx | 53 ++++++++++++++++++++++++++++--
sw/source/core/layout/layhelp.hxx | 1
sw/source/core/undo/undel.cxx | 1
6 files changed, 85 insertions(+), 3 deletions(-)
New commits:
commit beec1b1f594aa345ea4ee5a64bd70f8dccda64c3
Author: Michael Stahl <Michael.Stahl at cib.de>
AuthorDate: Tue May 26 16:46:57 2020 +0200
Commit: Michael Stahl <michael.stahl at cib.de>
CommitDate: Thu May 28 12:44:56 2020 +0200
tdf#132236 sw_redlinehide: fix SwUndoDelete with sections even more
SwUndoDelete::UndoImpl may want to move something like this into the
nodes-array:
[ 9] 0x6356fe0 TextNode "",
[ 10] 0x31cba00 ~DeletedNode ,
[ 11] 0x64d8840 TextNode "Introduction - xzn Overview Of KmneqxziTY\t3",
[ 12] 0x64e9750 TextNode "shell\t20",
[ 13] 0x7a0f0a0 ~DeletedNode ,
The ~DeletedNode become end nodes of section nodes; in this case
m_nSectDiff != 0.
Don't skip these end nodes because in the above "Untitled 1.odt"
example, they are not necessarily consecutive.
Between the 1st and 2nd one a new SwSectionFrame must be created via the
outer section, so adapt InsertCnt_() to check for extra end nodes in the
range and do this.
(regression from 723728cd358693b8f4bc9d913541aa4479f2bd48)
Change-Id: I7bfba9efca1789392495ebec37eb3e5b6138bd07
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/94883
Tested-by: Jenkins
Reviewed-by: Michael Stahl <michael.stahl at cib.de>
(cherry picked from commit fdd84f2240d3351f408671602563a8909d21f224)
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/94957
diff --git a/sw/qa/extras/uiwriter/data2/tdf132236.odt b/sw/qa/extras/uiwriter/data2/tdf132236.odt
new file mode 100644
index 000000000000..f37c9befc095
Binary files /dev/null and b/sw/qa/extras/uiwriter/data2/tdf132236.odt differ
diff --git a/sw/qa/extras/uiwriter/uiwriter2.cxx b/sw/qa/extras/uiwriter/uiwriter2.cxx
index 13e53234b445..74f6c5e30c22 100644
--- a/sw/qa/extras/uiwriter/uiwriter2.cxx
+++ b/sw/qa/extras/uiwriter/uiwriter2.cxx
@@ -289,6 +289,30 @@ CPPUNIT_TEST_FIXTURE(SwUiWriterTest2, testRedlineInHiddenSection)
CPPUNIT_ASSERT(pNode->GetNodes()[pNode->GetIndex() + 4]->IsEndNode());
}
+CPPUNIT_TEST_FIXTURE(SwUiWriterTest2, testTdf132236)
+{
+ load(DATA_DIRECTORY, "tdf132236.odt");
+
+ SwXTextDocument* const pTextDoc = dynamic_cast<SwXTextDocument*>(mxComponent.get());
+ CPPUNIT_ASSERT(pTextDoc);
+
+ // select everything and delete
+ SwWrtShell* const pWrtShell(pTextDoc->GetDocShell()->GetWrtShell());
+ pWrtShell->Down(true);
+ pWrtShell->Down(true);
+ pWrtShell->Down(true);
+ pWrtShell->Delete();
+ SwDoc* const pDoc(pWrtShell->GetDoc());
+ sw::UndoManager& rUndoManager(pDoc->GetUndoManager());
+ rUndoManager.Undo();
+
+ // check that the text frames exist inside their sections
+ xmlDocUniquePtr pXmlDoc = parseLayoutDump();
+ assertXPath(pXmlDoc, "/root/page[1]/body/section[1]/txt", 1);
+ assertXPath(pXmlDoc, "/root/page[1]/body/section[2]/txt", 2);
+ assertXPath(pXmlDoc, "/root/page[1]/body/txt", 1);
+}
+
CPPUNIT_TEST_FIXTURE(SwUiWriterTest2, testTdf54819)
{
load(DATA_DIRECTORY, "tdf54819.fodt");
diff --git a/sw/source/core/layout/frmtool.cxx b/sw/source/core/layout/frmtool.cxx
index 01af928c3fe9..9253d7018d70 100644
--- a/sw/source/core/layout/frmtool.cxx
+++ b/sw/source/core/layout/frmtool.cxx
@@ -1478,7 +1478,23 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
if( ( !pLay->IsInFootnote() || pSct->IsInFootnote() ) &&
( !pLay->IsInTab() || pSct->IsInTab() ) )
{
- pActualSection.reset(new SwActualSection( nullptr, pSct, nullptr ));
+ pActualSection.reset(new SwActualSection(nullptr, pSct, pSct->GetSection()->GetFormat()->GetSectionNode()));
+ // tdf#132236 for SwUndoDelete: find outer sections whose start
+ // nodes aren't contained in the range but whose end nodes are,
+ // because section frames may need to be created for them
+ SwActualSection * pUpperSection(pActualSection.get());
+ while (pUpperSection->GetSectionNode()->EndOfSectionIndex() < nEndIndex)
+ {
+ SwStartNode *const pStart(pUpperSection->GetSectionNode()->StartOfSectionNode());
+ if (!pStart->IsSectionNode())
+ {
+ break;
+ }
+ // note: these don't have a section frame, check it in EndNode case!
+ auto const pTmp(new SwActualSection(nullptr, nullptr, static_cast<SwSectionNode*>(pStart)));
+ pUpperSection->SetUpper(pTmp);
+ pUpperSection = pTmp;
+ }
OSL_ENSURE( !pLay->Lower() || !pLay->Lower()->IsColumnFrame(),
"InsertCnt_: Wrong Call" );
}
@@ -1800,7 +1816,7 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
SwSectionFrame* pOuterSectionFrame = pActualSection->GetSectionFrame();
// a follow has to be appended to the new section frame
- SwSectionFrame* pFollow = pOuterSectionFrame->GetFollow();
+ SwSectionFrame* pFollow = pOuterSectionFrame ? pOuterSectionFrame->GetFollow() : nullptr;
if ( pFollow )
{
pOuterSectionFrame->SetFollow( nullptr );
@@ -1809,7 +1825,8 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
}
// We don't want to leave empty parts back.
- if( ! pOuterSectionFrame->IsColLocked() &&
+ if (pOuterSectionFrame &&
+ ! pOuterSectionFrame->IsColLocked() &&
! pOuterSectionFrame->ContainsContent() )
{
pOuterSectionFrame->DelEmpty( true );
diff --git a/sw/source/core/layout/layhelp.hxx b/sw/source/core/layout/layhelp.hxx
index d7ebd30b3323..b4d21a3fdc15 100644
--- a/sw/source/core/layout/layhelp.hxx
+++ b/sw/source/core/layout/layhelp.hxx
@@ -94,6 +94,7 @@ public:
SwSectionFrame *GetSectionFrame() { return pSectFrame; }
void SetSectionFrame( SwSectionFrame *p ) { pSectFrame = p; }
SwSectionNode *GetSectionNode() { return pSectNode;}
+ void SetUpper(SwActualSection *p) { pUpper = p; }
SwActualSection *GetUpper() { return pUpper; }
};
diff --git a/sw/source/core/undo/undel.cxx b/sw/source/core/undo/undel.cxx
index 563de152f872..cf063b2a3af1 100644
--- a/sw/source/core/undo/undel.cxx
+++ b/sw/source/core/undo/undel.cxx
@@ -1091,6 +1091,7 @@ void SwUndoDelete::UndoImpl(::sw::UndoRedoContext & rContext)
// tdf#121031 if the start node is a text node, it already has a frame;
// if it's a table, it does not
// tdf#109376 exception: end on non-text-node -> start node was inserted
+ assert(!m_bDelFullPara || (m_nSectDiff == 0));
SwNodeIndex const start(rDoc.GetNodes(), m_nSttNode +
((m_bDelFullPara || !rDoc.GetNodes()[m_nSttNode]->IsTextNode() || pInsNd)
? 0 : 1));
commit bc6faecf24feca423b48ed1ea3d26fa6a64112db
Author: Michael Stahl <Michael.Stahl at cib.de>
AuthorDate: Tue May 26 16:43:27 2020 +0200
Commit: Michael Stahl <michael.stahl at cib.de>
CommitDate: Thu May 28 12:44:47 2020 +0200
tdf#131684 tdf#132236 sw_redlinehide: fix upper of frame moved...
... in SwUndoDelete::UndoImpl; this wasn't fixed properly in commit
6c7245e789f973cf6dad03f7008ab3f9d12d350c - the SwTextFrame was moved
into the SwSectionFrame but its upper was whatever it was previously.
This is rather ugly because with the constraint from the very special
case of tdf#131684 the MakeFrames() requires one node with pre-existing
frames, and it's not possible to move the pre-existing frame after
MakeFrames() because then the tdf#132236 case will have an empty
SwSectionFrame and InsertCnt_() will just delete it.
So try to detect the situation with some hack in InsertCnt_() to move
it into the SwSectionFrame.
(regression from 723728cd358693b8f4bc9d913541aa4479f2bd48)
Change-Id: Ic0199c85d7523a49676ad3df1d2c4d8fe135c2ff
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/94881
Tested-by: Jenkins
Reviewed-by: Michael Stahl <michael.stahl at cib.de>
(cherry picked from commit 55576842ec72a748d0bad123d41fa03c89fc136d)
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/94956
diff --git a/sw/qa/extras/uiwriter/uiwriter3.cxx b/sw/qa/extras/uiwriter/uiwriter3.cxx
index 3b67a6fde7ca..2ba1db6974d2 100644
--- a/sw/qa/extras/uiwriter/uiwriter3.cxx
+++ b/sw/qa/extras/uiwriter/uiwriter3.cxx
@@ -478,6 +478,15 @@ CPPUNIT_TEST_FIXTURE(SwUiWriterTest3, testTdf131684)
// without the fix, it crashes
dispatchCommand(mxComponent, ".uno:Undo", {});
CPPUNIT_ASSERT_EQUAL(sal_Int32(1), xIndexAccess->getCount());
+
+ // check that the text frame has the correct upper
+ xmlDocUniquePtr pXmlDoc = parseLayoutDump();
+ OUString const sectionId = getXPath(pXmlDoc, "/root/page[1]/body/section[7]", "id");
+ OUString const sectionLower = getXPath(pXmlDoc, "/root/page[1]/body/section[7]", "lower");
+ OUString const textId = getXPath(pXmlDoc, "/root/page[1]/body/section[7]/txt[1]", "id");
+ OUString const textUpper = getXPath(pXmlDoc, "/root/page[1]/body/section[7]/txt[1]", "upper");
+ CPPUNIT_ASSERT_EQUAL(textId, sectionLower);
+ CPPUNIT_ASSERT_EQUAL(sectionId, textUpper);
}
CPPUNIT_TEST_FIXTURE(SwUiWriterTest3, testTdf80663)
diff --git a/sw/source/core/layout/frmtool.cxx b/sw/source/core/layout/frmtool.cxx
index b55f56775bb2..01af928c3fe9 100644
--- a/sw/source/core/layout/frmtool.cxx
+++ b/sw/source/core/layout/frmtool.cxx
@@ -1678,6 +1678,36 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
static_cast<SwTextFrame*>(pPrv)->Prepare( PrepareHint::QuoVadis, nullptr, false );
}
}
+ if (nIndex + 1 == nEndIndex)
+ { // tdf#131684 tdf#132236 fix upper of frame moved in
+ // SwUndoDelete; can't be done there unfortunately
+ // because empty section frames are deleted here
+ SwFrame *const pNext(
+ // if there's a parent section, it has been split
+ // into 2 SwSectionFrame already :(
+ ( pFrame->GetNext()->IsSctFrame()
+ && pActualSection->GetUpper()
+ && pActualSection->GetUpper()->GetSectionNode() ==
+ static_cast<SwSectionFrame const*>(pFrame->GetNext())->GetSection()->GetFormat()->GetSectionNode())
+ ? static_cast<SwSectionFrame *>(pFrame->GetNext())->ContainsContent()
+ : pFrame->GetNext());
+ if (pNext
+ && pNext->IsTextFrame()
+ && static_cast<SwTextFrame*>(pNext)->GetTextNodeFirst() == pDoc->GetNodes()[nEndIndex]
+ && (pNext->GetUpper() == pFrame->GetUpper()
+ || pFrame->GetNext()->IsSctFrame())) // checked above
+ {
+ pNext->Cut();
+ pNext->InvalidateInfFlags(); // mbInfSct changed
+ // could have columns
+ SwSectionFrame *const pSection(static_cast<SwSectionFrame*>(pFrame));
+ assert(!pSection->Lower() || pSection->Lower()->IsLayoutFrame());
+ SwLayoutFrame *const pParent(pSection->Lower() ? pSection->GetNextLayoutLeaf() : pSection);
+ assert(!pParent->Lower());
+ // paste invalidates, section could have indent...
+ pNext->Paste(pParent, nullptr);
+ }
+ }
// #i27138#
// notify accessibility paragraphs objects about changed
// CONTENT_FLOWS_FROM/_TO relation.
More information about the Libreoffice-commits
mailing list