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

Miklos Vajna vmiklos at collabora.co.uk
Fri Nov 11 15:25:07 UTC 2016


 sw/qa/extras/ooxmlexport/data/tdf79329.docx              |binary
 sw/qa/extras/ooxmlexport/ooxmlexport7.cxx                |    8 +++++++
 writerfilter/source/dmapper/DomainMapper.cxx             |   12 +++++++++++
 writerfilter/source/dmapper/DomainMapperTableHandler.cxx |    7 ++++--
 writerfilter/source/dmapper/DomainMapperTableHandler.hxx |    2 -
 writerfilter/source/dmapper/DomainMapper_Impl.cxx        |    3 ++
 writerfilter/source/dmapper/DomainMapper_Impl.hxx        |    4 +++
 writerfilter/source/dmapper/TableManager.cxx             |   10 +++++++--
 writerfilter/source/dmapper/TableManager.hxx             |    3 ++
 writerfilter/source/ooxml/OOXMLFastContextHandler.cxx    |   16 +++++++++++++++
 writerfilter/source/ooxml/OOXMLFastContextHandler.hxx    |    2 -
 writerfilter/source/ooxml/model.xml                      |    2 +
 12 files changed, 63 insertions(+), 6 deletions(-)

New commits:
commit d6e89673155c9cb536747c734b2de23f3d8484ef
Author: Miklos Vajna <vmiklos at collabora.co.uk>
Date:   Tue Nov 8 09:11:33 2016 +0100

    tdf#79329 DOCX import: fix missing outer table with floattable at cell start
    
    The bug document has a normal table, then its C1 cell starts with a
    nested table, which is floating. The problem is that converting the
    nested table to a textframe invalidates the start text range of the C1
    cell in the outer table we store, so the conversion of the outer table
    from text to table fails.
    
    This never worked, so to avoid the regression just don't convert inner
    floating tables to textframes when they're anchored at the cell start.
    A more general fix in the future can be addressing the actual
    invalidation of the cell start/end text ranges, and then this specific
    fix will not be necessary anymore.
    
    (cherry picked from commit c1eebcdac9f2b289fd363399130c485ca5ff444c)
    
    Conflicts:
    	sw/qa/extras/ooxmlexport/ooxmlexport9.cxx
    	writerfilter/source/dmapper/DomainMapper.cxx
    
    Change-Id: I12cefa41977cf719b07b0fb3ef9ec423c17ef3b1
    Reviewed-on: https://gerrit.libreoffice.org/30770
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Caolán McNamara <caolanm at redhat.com>
    Tested-by: Caolán McNamara <caolanm at redhat.com>

diff --git a/sw/qa/extras/ooxmlexport/data/tdf79329.docx b/sw/qa/extras/ooxmlexport/data/tdf79329.docx
new file mode 100644
index 0000000..142f295
Binary files /dev/null and b/sw/qa/extras/ooxmlexport/data/tdf79329.docx differ
diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport7.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport7.cxx
index 6babd92..c3b94a7 100644
--- a/sw/qa/extras/ooxmlexport/ooxmlexport7.cxx
+++ b/sw/qa/extras/ooxmlexport/ooxmlexport7.cxx
@@ -59,6 +59,14 @@ DECLARE_OOXMLEXPORT_TEST( testChildNodesOfCubicBezierTo, "FDO74774.docx")
         "/w:document/w:body/w:p[2]/w:r[1]/mc:AlternateContent[1]/mc:Choice/w:drawing[1]/wp:inline[1]/a:graphic[1]/a:graphicData[1]/wpg:wgp[1]/wps:wsp[3]/wps:spPr[1]/a:custGeom[1]/a:pathLst[1]/a:path[1]/a:cubicBezTo[2]/a:pt[3]");
 }
 
+DECLARE_OOXMLEXPORT_TEST(testTdf79329, "tdf79329.docx")
+{
+    uno::Reference<text::XTextTablesSupplier> xTablesSupplier(mxComponent, uno::UNO_QUERY);
+    uno::Reference<container::XIndexAccess> xTables(xTablesSupplier->getTextTables(), uno::UNO_QUERY);
+    // This was 1: only the inner, not the outer table was created.
+    CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(2), xTables->getCount());
+}
+
 DECLARE_OOXMLEXPORT_TEST(testMSwordHang,"test_msword_hang.docx")
 {
     // fdo#74771:
diff --git a/writerfilter/source/dmapper/DomainMapper.cxx b/writerfilter/source/dmapper/DomainMapper.cxx
index e309870..a46c6f6 100644
--- a/writerfilter/source/dmapper/DomainMapper.cxx
+++ b/writerfilter/source/dmapper/DomainMapper.cxx
@@ -2542,6 +2542,11 @@ void DomainMapper::sprmWithProps( Sprm& rSprm, const PropertyMapPtr& rContext )
     break;
     case NS_ooxml::LN_tblStart:
 
+        if (m_pImpl->hasTableManager())
+        {
+            bool bTableStartsAtCellStart = m_pImpl->m_nTableDepth > 0 && m_pImpl->m_nTableCellDepth > m_pImpl->m_nLastTableCellParagraphDepth + 1;
+            m_pImpl->getTableManager().setTableStartsAtCellStart(bTableStartsAtCellStart);
+        }
         /*
          * Hack for Importing Section Properties
          * LO is not able to import section properties if first element in the
@@ -2559,6 +2564,13 @@ void DomainMapper::sprmWithProps( Sprm& rSprm, const PropertyMapPtr& rContext )
     case NS_ooxml::LN_tblEnd:
         m_pImpl->m_nTableDepth--;
     break;
+    case NS_ooxml::LN_tcStart:
+        m_pImpl->m_nTableCellDepth++;
+    break;
+    case NS_ooxml::LN_tcEnd:
+        m_pImpl->m_nTableCellDepth--;
+        m_pImpl->m_nLastTableCellParagraphDepth = 0;
+    break;
     case NS_ooxml::LN_glow_glow:
     case NS_ooxml::LN_shadow_shadow:
     case NS_ooxml::LN_reflection_reflection:
diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
index 1769982..43ef3be 100644
--- a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
+++ b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
@@ -969,7 +969,7 @@ static void lcl_ApplyCellParaProps(uno::Reference<table::XCell> const& xCell,
     }
 }
 
-void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel)
+void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel, bool bTableStartsAtCellStart)
 {
 #ifdef DEBUG_WRITERFILTER
     TagLogger::getInstance().startElement("tablehandler.endTable");
@@ -1114,7 +1114,10 @@ void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel)
             {
                 // m_xText points to the body text, get the current xText from m_rDMapper_Impl, in case e.g. we would be in a header.
                 uno::Reference<text::XTextAppendAndConvert> xTextAppendAndConvert(m_rDMapper_Impl.GetTopTextAppend(), uno::UNO_QUERY);
-                if (xTextAppendAndConvert.is())
+                // Only execute the conversion if the table is not anchored at
+                // the start of an outer table cell, that's not yet
+                // implemented.
+                if (xTextAppendAndConvert.is() && !bTableStartsAtCellStart)
                     xTextAppendAndConvert->convertToTextFrame(xStart, xEnd, comphelper::containerToSequence(aFrameProperties));
             }
         }
diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
index b1ac2f1..ed9cb04 100644
--- a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
+++ b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
@@ -94,7 +94,7 @@ public:
      */
     void startTable(unsigned int nDepth, const TablePropertyMapPtr& pProps);
     /// Handle end of table.
-    void endTable(unsigned int nestedTableLevel);
+    void endTable(unsigned int nestedTableLevel, bool bTableStartsAtCellStart);
     /**
        Handle start of row.
 
diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.cxx b/writerfilter/source/dmapper/DomainMapper_Impl.cxx
index dc054bc..08de96e 100644
--- a/writerfilter/source/dmapper/DomainMapper_Impl.cxx
+++ b/writerfilter/source/dmapper/DomainMapper_Impl.cxx
@@ -232,6 +232,8 @@ DomainMapper_Impl::DomainMapper_Impl(
         m_bIsNewDoc(!rMediaDesc.getUnpackedValueOrDefault("InsertMode", false)),
         m_bInTableStyleRunProps(false),
         m_nTableDepth(0),
+        m_nTableCellDepth(0),
+        m_nLastTableCellParagraphDepth(0),
         m_bHasFtnSep(false),
         m_bIgnoreNextPara(false),
         m_bIgnoreNextTab(false),
@@ -1023,6 +1025,7 @@ void DomainMapper_Impl::finishParagraph( const PropertyMapPtr& pPropertyMap )
     TagLogger::getInstance().startElement("finishParagraph");
 #endif
 
+    m_nLastTableCellParagraphDepth = m_nTableCellDepth;
     ParagraphPropertyMap* pParaContext = dynamic_cast< ParagraphPropertyMap* >( pPropertyMap.get() );
     if (m_aTextAppendStack.empty())
         return;
diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.hxx b/writerfilter/source/dmapper/DomainMapper_Impl.hxx
index 5b33c39..5f2ce81 100644
--- a/writerfilter/source/dmapper/DomainMapper_Impl.hxx
+++ b/writerfilter/source/dmapper/DomainMapper_Impl.hxx
@@ -818,6 +818,10 @@ public:
      * inTbl SPRM or not).
      */
     sal_Int32 m_nTableDepth;
+    /// Raw table cell depth.
+    sal_Int32 m_nTableCellDepth;
+    /// Table cell depth of the last finished paragraph.
+    sal_Int32 m_nLastTableCellParagraphDepth;
 
     /// If the document has a footnote separator.
     bool m_bHasFtnSep;
diff --git a/writerfilter/source/dmapper/TableManager.cxx b/writerfilter/source/dmapper/TableManager.cxx
index b574d83..432abc9 100644
--- a/writerfilter/source/dmapper/TableManager.cxx
+++ b/writerfilter/source/dmapper/TableManager.cxx
@@ -314,7 +314,7 @@ void TableManager::resolveCurrentTable()
                 mpTableDataHandler->endRow();
             }
 
-            mpTableDataHandler->endTable(mTableDataStack.size() - 1);
+            mpTableDataHandler->endTable(mTableDataStack.size() - 1, m_bTableStartsAtCellStart);
         }
         catch (css::uno::Exception const& e)
         {
@@ -454,8 +454,14 @@ void TableManager::cellDepth(sal_uInt32 nDepth)
     mnTableDepthNew = nDepth;
 }
 
+void TableManager::setTableStartsAtCellStart(bool bTableStartsAtCellStart)
+{
+    m_bTableStartsAtCellStart = bTableStartsAtCellStart;
+}
+
 TableManager::TableManager()
-    : mnTableDepthNew(0), mnTableDepth(0), mbKeepUnfinishedRow(false)
+    : mnTableDepthNew(0), mnTableDepth(0), mbKeepUnfinishedRow(false),
+      m_bTableStartsAtCellStart(false)
 {
     setRowEnd(false);
     setInCell(false);
diff --git a/writerfilter/source/dmapper/TableManager.hxx b/writerfilter/source/dmapper/TableManager.hxx
index 334634d..f3d5f66 100644
--- a/writerfilter/source/dmapper/TableManager.hxx
+++ b/writerfilter/source/dmapper/TableManager.hxx
@@ -314,6 +314,8 @@ private:
     std::stack<TableData::Pointer_t> mTableDataStack;
     RowData::Pointer_t mpUnfinishedRow;
     bool mbKeepUnfinishedRow;
+    /// If this is a nested table, does it start at cell start?
+    bool m_bTableStartsAtCellStart;
 
     /**
        handler for resolveCurrentTable
@@ -515,6 +517,7 @@ public:
     bool isIgnore() const;
 
 
+    void setTableStartsAtCellStart(bool bTableStartsAtCellStart);
 };
 
 }
diff --git a/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx b/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx
index 645ade6..d804e1d 100644
--- a/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx
+++ b/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx
@@ -1284,6 +1284,17 @@ OOXMLFastContextHandlerTextTableCell::~OOXMLFastContextHandlerTextTableCell()
 
 void OOXMLFastContextHandlerTextTableCell::startCell()
 {
+    if (isForwardEvents())
+    {
+        OOXMLPropertySet * pProps = new OOXMLPropertySet;
+        {
+            OOXMLValue::Pointer_t pVal = OOXMLBooleanValue::Create(mnTableDepth > 0);
+            OOXMLProperty::Pointer_t pProp(new OOXMLProperty(NS_ooxml::LN_tcStart, pVal, OOXMLProperty::SPRM));
+            pProps->add(pProp);
+        }
+
+        mpStream->props(writerfilter::Reference<Properties>::Pointer_t(pProps));
+    }
 }
 
 void OOXMLFastContextHandlerTextTableCell::endCell()
@@ -1306,6 +1317,11 @@ void OOXMLFastContextHandlerTextTableCell::endCell()
             OOXMLProperty::Pointer_t pProp(new OOXMLProperty(NS_ooxml::LN_tblCell, pVal, OOXMLProperty::SPRM));
             pProps->add(pProp);
         }
+        {
+            OOXMLValue::Pointer_t pVal = OOXMLBooleanValue::Create(mnTableDepth > 0);
+            OOXMLProperty::Pointer_t pProp(new OOXMLProperty(NS_ooxml::LN_tcEnd, pVal, OOXMLProperty::SPRM));
+            pProps->add(pProp);
+        }
 
         mpStream->props(writerfilter::Reference<Properties>::Pointer_t(pProps));
     }
diff --git a/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx b/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx
index f713fcf..60d423c 100644
--- a/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx
+++ b/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx
@@ -391,7 +391,7 @@ public:
 
     virtual std::string getType() const override { return "TextTableCell"; }
 
-    static void startCell();
+    void startCell();
     void endCell();
 };
 
diff --git a/writerfilter/source/ooxml/model.xml b/writerfilter/source/ooxml/model.xml
index 61438c3..3b6a03e 100644
--- a/writerfilter/source/ooxml/model.xml
+++ b/writerfilter/source/ooxml/model.xml
@@ -40,6 +40,8 @@
   <token tokenid="ooxml:object"/>
   <token tokenid="ooxml:tblStart"/>
   <token tokenid="ooxml:tblEnd"/>
+  <token tokenid="ooxml:tcStart"/>
+  <token tokenid="ooxml:tcEnd"/>
 
   <!-- These are not directly generated from OOXML XML elements / attributes, need to clean them up in the future. -->
   <token tokenid="ooxml:tblDepth"/>


More information about the Libreoffice-commits mailing list