[Libreoffice-commits] core.git: Branch 'libreoffice-7-2' - sw/qa writerfilter/source

László Németh (via logerrit) logerrit at kemper.freedesktop.org
Mon Jul 26 10:09:44 UTC 2021


 sw/qa/extras/ooxmlexport/data/TC-table-DnD-move.docx      |binary
 sw/qa/extras/ooxmlexport/data/TC-table-Separate-Move.docx |binary
 sw/qa/extras/ooxmlexport/data/TC-table-rowDND-front.docx  |binary
 sw/qa/extras/ooxmlexport/data/TC-table-rowDND.docx        |binary
 sw/qa/extras/ooxmlexport/ooxmlexport11.cxx                |   50 ++++++++++++++
 writerfilter/source/dmapper/DomainMapper.cxx              |   13 +++
 writerfilter/source/dmapper/DomainMapperTableManager.cxx  |   17 ++++
 writerfilter/source/dmapper/DomainMapperTableManager.hxx  |   37 ++++++++++
 writerfilter/source/ooxml/model.xml                       |    4 +
 9 files changed, 121 insertions(+)

New commits:
commit 5602803d07453bfd7c17ed5b6df7551d1041f97c
Author:     László Németh <nemeth at numbertext.org>
AuthorDate: Thu Jul 22 19:08:47 2021 +0200
Commit:     László Németh <nemeth at numbertext.org>
CommitDate: Mon Jul 26 12:09:10 2021 +0200

    tdf#143510 DOCX import: fix tracked table drag & drop
    
    Accept or reject of tracked drag & drop table (row)
    move weren't handled, resulting an extra empty table
    (rows) instead of removing the deleted or inserted
    table (rows).
    
    Note: tables moved by drag & drop with track changes use
    w:moveFromRangeStart/End and w:moveToRangeStart/End
    bookmark-like elements to sign the boundary of the
    moved text. Now moveFrom/moveTo import is handled by
    tracked table (row) deletion and insertion.
    
    Change-Id: Ie382645fef28f57b30d3504fb28ac08489f705c0
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/119406
    Tested-by: Jenkins
    Reviewed-by: László Németh <nemeth at numbertext.org>
    (cherry picked from commit 7f3c0bbc174b9b0316991c174ca3b407c0e3d141)
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/119436

diff --git a/sw/qa/extras/ooxmlexport/data/TC-table-DnD-move.docx b/sw/qa/extras/ooxmlexport/data/TC-table-DnD-move.docx
new file mode 100644
index 000000000000..f231d6f84240
Binary files /dev/null and b/sw/qa/extras/ooxmlexport/data/TC-table-DnD-move.docx differ
diff --git a/sw/qa/extras/ooxmlexport/data/TC-table-Separate-Move.docx b/sw/qa/extras/ooxmlexport/data/TC-table-Separate-Move.docx
new file mode 100644
index 000000000000..227f2862c68a
Binary files /dev/null and b/sw/qa/extras/ooxmlexport/data/TC-table-Separate-Move.docx differ
diff --git a/sw/qa/extras/ooxmlexport/data/TC-table-rowDND-front.docx b/sw/qa/extras/ooxmlexport/data/TC-table-rowDND-front.docx
new file mode 100644
index 000000000000..17d3feeb3406
Binary files /dev/null and b/sw/qa/extras/ooxmlexport/data/TC-table-rowDND-front.docx differ
diff --git a/sw/qa/extras/ooxmlexport/data/TC-table-rowDND.docx b/sw/qa/extras/ooxmlexport/data/TC-table-rowDND.docx
new file mode 100644
index 000000000000..9608736cf20a
Binary files /dev/null and b/sw/qa/extras/ooxmlexport/data/TC-table-rowDND.docx differ
diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport11.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport11.cxx
index 1864c4bcf83e..431d5d71753d 100644
--- a/sw/qa/extras/ooxmlexport/ooxmlexport11.cxx
+++ b/sw/qa/extras/ooxmlexport/ooxmlexport11.cxx
@@ -881,6 +881,56 @@ DECLARE_OOXMLEXPORT_TEST(testTdf104797, "tdf104797.docx")
     CPPUNIT_ASSERT_EQUAL( OUString( " Will this sentence be duplicated ADDED STUFF?" ), getRun( getParagraph( 2 ), 4 )->getString());
 }
 
+DECLARE_OOXMLEXPORT_TEST(testTdf143510, "TC-table-DnD-move.docx")
+{
+    // check moveFromRangeStart/End and moveToRangeStart/End for tracked table move by drag & drop
+    xmlDocUniquePtr pXmlDoc = parseExport("word/document.xml");
+    if (mbExported)
+    {
+        // This was 0 (missing tracked table row deletion/insertion)
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[1]/w:tr/w:trPr/w:del", 2);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[2]/w:tr/w:trPr/w:ins", 2);
+    }
+}
+
+DECLARE_OOXMLEXPORT_TEST(testTdf143510_table_from_row, "TC-table-Separate-Move.docx")
+{
+    // check moveFromRangeStart/End and moveToRangeStart/End for tracked table move by drag & drop
+    xmlDocUniquePtr pXmlDoc = parseExport("word/document.xml");
+    if (mbExported)
+    {
+        // This was 0 (missing tracked table row deletion/insertion)
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[1]/w:tr/w:trPr/w:del", 1);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[1]/w:tr[3]/w:trPr/w:del", 1);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[2]/w:tr", 1);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl[2]/w:tr/w:trPr/w:ins", 1);
+    }
+}
+
+DECLARE_OOXMLEXPORT_TEST(testTdf143510_within_table, "TC-table-rowDND.docx")
+{
+    // check moveFromRangeStart/End and moveToRangeStart/End for tracked table row move by DnD
+    xmlDocUniquePtr pXmlDoc = parseExport("word/document.xml");
+    if (mbExported)
+    {
+        // This was 0 (missing tracked table row deletion/insertion)
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl/w:tr[1]/w:trPr/w:del", 1);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl/w:tr[4]/w:trPr/w:ins", 1);
+    }
+}
+
+DECLARE_OOXMLEXPORT_TEST(testTdf143510_within_table2, "TC-table-rowDND-front.docx")
+{
+    // check moveFromRangeStart/End and moveToRangeStart/End for tracked table row move by DnD
+    xmlDocUniquePtr pXmlDoc = parseExport("word/document.xml");
+    if (mbExported)
+    {
+        // This was 0 (missing tracked table row deletion/insertion)
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl/w:tr[1]/w:trPr/w:ins", 1);
+        assertXPath(pXmlDoc, "/w:document/w:body/w:tbl/w:tr[4]/w:trPr/w:del", 1);
+    }
+}
+
 DECLARE_OOXMLEXPORT_TEST(testTdf113608_runAwayNumbering, "tdf113608_runAwayNumbering.docx")
 {
     // check that an incorrect numbering style is not applied
diff --git a/writerfilter/source/dmapper/DomainMapper.cxx b/writerfilter/source/dmapper/DomainMapper.cxx
index 182b7c5c3200..232650c7f8ea 100644
--- a/writerfilter/source/dmapper/DomainMapper.cxx
+++ b/writerfilter/source/dmapper/DomainMapper.cxx
@@ -2454,6 +2454,19 @@ void DomainMapper::sprmWithProps( Sprm& rSprm, const PropertyMapPtr& rContext )
         }
     }
     break;
+    case NS_ooxml::LN_EG_RangeMarkupElements_moveFromRangeStart:
+        if (m_pImpl->hasTableManager())
+            m_pImpl->getTableManager().setMoved( getPropertyName(PROP_TABLE_ROW_DELETE) );
+    break;
+    case NS_ooxml::LN_EG_RangeMarkupElements_moveToRangeStart:
+        if (m_pImpl->hasTableManager())
+            m_pImpl->getTableManager().setMoved( getPropertyName(PROP_TABLE_ROW_INSERT) );
+    break;
+    case NS_ooxml::LN_EG_RangeMarkupElements_moveFromRangeEnd:
+    case NS_ooxml::LN_EG_RangeMarkupElements_moveToRangeEnd:
+         if (m_pImpl->hasTableManager())
+            m_pImpl->getTableManager().setMoved( OUString() );
+    break;
     case NS_ooxml::LN_paratrackchange:
         m_pImpl->StartParaMarkerChange( );
         [[fallthrough]];
diff --git a/writerfilter/source/dmapper/DomainMapperTableManager.cxx b/writerfilter/source/dmapper/DomainMapperTableManager.cxx
index a3a76dccbf82..35749d60bd59 100644
--- a/writerfilter/source/dmapper/DomainMapperTableManager.cxx
+++ b/writerfilter/source/dmapper/DomainMapperTableManager.cxx
@@ -30,6 +30,8 @@
 #include <rtl/math.hxx>
 #include <sal/log.hxx>
 #include <numeric>
+#include "TrackChangesHandler.hxx"
+#include <oox/token/tokens.hxx>
 
 namespace writerfilter::dmapper {
 
@@ -449,6 +451,7 @@ void DomainMapperTableManager::startLevel( )
     m_aTablePositions.push_back( pNewPositionHandler );
     // empty name will be replaced by the table style name, if it exists
     m_aTableStyleNames.push_back( OUString() );
+    m_aMoved.push_back( OUString() );
 
     TablePositionHandlerPtr pTmpPosition;
     TablePropertyMapPtr pTmpProperties( new TablePropertyMap( ) );
@@ -507,6 +510,7 @@ void DomainMapperTableManager::endLevel( )
     // in the endTable method called in endLevel.
     m_aTablePositions.pop_back();
     m_aTableStyleNames.pop_back();
+    m_aMoved.pop_back( );
     m_aParagraphsToEndTable.pop();
 }
 
@@ -727,6 +731,19 @@ void DomainMapperTableManager::endOfRowAction()
         pPropMap->dumpXml();
         TagLogger::getInstance().endElement();
 #endif
+
+        // set row insertion/deletion at tracked drag & drop of tables
+        OUString aMoved = getMoved();
+        if ( !aMoved.isEmpty() )
+        {
+            auto pTrackChangesHandler = std::make_shared<TrackChangesHandler>(
+                    aMoved == getPropertyName( PROP_TABLE_ROW_DELETE )
+                        ? oox::XML_tableRowDelete
+                        : oox::XML_tableRowInsert );
+            uno::Sequence<beans::PropertyValue> aTableRedlineProperties = pTrackChangesHandler->getRedlineProperties();
+            pPropMap->Insert( PROP_TABLE_REDLINE_PARAMS , uno::makeAny( aTableRedlineProperties ));
+        }
+
         insertRowProps(pPropMap);
     }
     else if (shouldInsertRow(pCellWidths, pTableGrid, nGrids, bIsIncompleteGrid))
diff --git a/writerfilter/source/dmapper/DomainMapperTableManager.hxx b/writerfilter/source/dmapper/DomainMapperTableManager.hxx
index 8c337e6b48c8..ef90297c5b97 100644
--- a/writerfilter/source/dmapper/DomainMapperTableManager.hxx
+++ b/writerfilter/source/dmapper/DomainMapperTableManager.hxx
@@ -43,6 +43,8 @@ class DomainMapperTableManager : public TableManager
     /// Are we in a shape (text append stack is not empty) or in the body document?
     bool m_bIsInShape;
     std::vector< OUString > m_aTableStyleNames;
+    /// Moved table (in moveRangeFromStart...moveRangeFromEnd or moveRangeToStart...moveRangeToEnd)
+    std::vector< OUString > m_aMoved;
     /// Grab-bag of table look attributes for preserving.
     comphelper::SequenceAsHashMap m_aTableLook;
     std::vector< TablePositionHandlerPtr > m_aTablePositions;
@@ -128,6 +130,41 @@ public:
 
     void setIsInShape(bool bIsInShape);
 
+    // moveFromRangeStart and moveToRangeStart are there
+    // in the first paragraph in the first cell of the
+    // table moved by drag & drop with track changes, but
+    // moveFromRangeEnd and moveToRangeEnd follow the
+    // table element w:tbl in the same level (not in paragraph).
+    // (Special indexing is related to the load of the tables:
+    // first-level tables handled by two levels during the
+    // import, to support table join etc. In the first cell,
+    // setMoved() writes the first level from these two levels
+    // i.e. second startLevel() hasn't been called, yet.)
+    // TODO: check drag & drop of only a part of the tables.
+    void setMoved(OUString sMoved)
+    {
+        if ( m_aMoved.empty() )
+            return;
+
+        if ( !sMoved.isEmpty() )
+            m_aMoved.end()[-1] = sMoved;
+        else if ( m_aMoved.size() >= 2 )
+            // next table rows weren't moved
+            m_aMoved.end()[-2] = "";
+        else
+            m_aMoved.end()[-1] = "";
+    }
+
+    OUString getMoved() const
+    {
+        if ( m_aMoved.size() >= 2 && !m_aMoved.end()[-2].isEmpty() )
+           return m_aMoved.end()[-2];
+        else if ( !m_aMoved.empty() )
+           return m_aMoved.end()[-1];
+
+        return OUString();
+    }
+
 };
 
 }
diff --git a/writerfilter/source/ooxml/model.xml b/writerfilter/source/ooxml/model.xml
index 77dce046fb3d..da6d56473d41 100644
--- a/writerfilter/source/ooxml/model.xml
+++ b/writerfilter/source/ooxml/model.xml
@@ -17472,6 +17472,8 @@
     </resource>
     <resource name="CT_MarkupRangeBookmark" resource="Properties">
       <attribute name="id" tokenid="ooxml:CT_MarkupRangeBookmark_id"/>
+      <action name="end" tokenid="ooxml:EG_RangeMarkupElements_moveFromRangeEnd" action="sendPropertiesWithId" sendtokenid="ooxml:EG_RangeMarkupElements_moveFromRangeEnd"/>
+      <action name="end" tokenid="ooxml:EG_RangeMarkupElements_moveToRangeEnd" action="sendPropertiesWithId" sendtokenid="ooxml:EG_RangeMarkupElements_moveToRangeEnd"/>
     </resource>
     <resource name="CT_PermStart" resource="Properties">
       <attribute name="id" tokenid="ooxml:CT_PermStart_id"/>
@@ -17501,6 +17503,8 @@
     <resource name="CT_MoveBookmark" resource="Properties">
       <attribute name="author" tokenid="ooxml:CT_MoveBookmark_author"/>
       <attribute name="date" tokenid="ooxml:CT_MoveBookmark_date"/>
+      <action name="end" tokenid="ooxml:EG_RangeMarkupElements_moveFromRangeStart" action="sendPropertiesWithId" sendtokenid="ooxml:EG_RangeMarkupElements_moveFromRangeStart"/>
+      <action name="end" tokenid="ooxml:EG_RangeMarkupElements_moveToRangeStart" action="sendPropertiesWithId" sendtokenid="ooxml:EG_RangeMarkupElements_moveToRangeStart"/>
     </resource>
     <resource name="CT_Comment" resource="XNote">
       <attribute name="id" action="checkId"/>


More information about the Libreoffice-commits mailing list