sw/qa/extras/ooxmlimport/data/fdo65090.docx              |binary
 sw/qa/extras/ooxmlimport/ooxmlimport.cxx                 |   10 +++
 writerfilter/source/dmapper/DomainMapperTableHandler.cxx |   43 ++++++++++++++-
 writerfilter/source/dmapper/DomainMapperTableHandler.hxx |   17 +++++
 writerfilter/source/dmapper/DomainMapperTableManager.cxx |    8 ++
 writerfilter/source/dmapper/PropertyIds.cxx              |    1 
 writerfilter/source/dmapper/PropertyIds.hxx              |    1 
 7 files changed, 77 insertions(+), 3 deletions(-)

New commits:
commit 97dcf77841d19d344d58d5bdacdab141cdea4817
Author: Miklos Vajna <vmik...@collabora.co.uk>
Date:   Fri Dec 27 21:07:43 2013 +0100

    Related: fdo#65090 DOCX import: handle w:hMerge cell property
    
    Change-Id: I82f334426715fd1a1f0105b86f763d41e66f32da

diff --git a/sw/qa/extras/ooxmlimport/data/fdo65090.docx 
b/sw/qa/extras/ooxmlimport/data/fdo65090.docx
new file mode 100644
index 0000000..4d45737
Binary files /dev/null and b/sw/qa/extras/ooxmlimport/data/fdo65090.docx differ
diff --git a/sw/qa/extras/ooxmlimport/ooxmlimport.cxx 
b/sw/qa/extras/ooxmlimport/ooxmlimport.cxx
index e91de29..7804340 100644
--- a/sw/qa/extras/ooxmlimport/ooxmlimport.cxx
+++ b/sw/qa/extras/ooxmlimport/ooxmlimport.cxx
@@ -1660,6 +1660,16 @@ DECLARE_OOXMLIMPORT_TEST(testRPrChangeClosed, 
"rprchange_closed.docx")
     CPPUNIT_ASSERT_EQUAL(false, hasProperty(getRun(getParagraph(2), 1), 
"RedlineType"));
 }
 
+DECLARE_OOXMLIMPORT_TEST(testFdo65090, "fdo65090.docx")
+{
+    uno::Reference<text::XTextTablesSupplier> xTablesSupplier(mxComponent, 
uno::UNO_QUERY);
+    uno::Reference<container::XIndexAccess> 
xTables(xTablesSupplier->getTextTables( ), uno::UNO_QUERY);
+    uno::Reference<text::XTextTable> xTextTable(xTables->getByIndex(0), 
uno::UNO_QUERY);
+    uno::Reference<table::XTableRows> xTableRows(xTextTable->getRows(), 
uno::UNO_QUERY);
+    // The first row had two cells, instead of a single horizontally merged 
one.
+    CPPUNIT_ASSERT_EQUAL(sal_Int32(0), getProperty< 
uno::Sequence<text::TableColumnSeparator> >(xTableRows->getByIndex(0), 
"TableColumnSeparators").getLength());
+}
+
 #endif
 
 CPPUNIT_PLUGIN_IMPLEMENT();
diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx 
b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
index a098472..7e248de 100644
--- a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
+++ b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx
@@ -539,7 +539,7 @@ TableStyleSheetEntry * 
DomainMapperTableHandler::endTableGetTableStyle(TableInfo
 #define CNF_LAST_ROW_LAST_COLUMN    0x002
 #define CNF_LAST_ROW_FIRST_COLUMN   0x001
 
-CellPropertyValuesSeq_t 
DomainMapperTableHandler::endTableGetCellProperties(TableInfo & rInfo)
+CellPropertyValuesSeq_t 
DomainMapperTableHandler::endTableGetCellProperties(TableInfo & rInfo, 
std::vector<HorizontallyMergedCell>& rMerges)
 {
 #ifdef DEBUG_DMAPPER_TABLE_HANDLER
     dmapper_logger->startElement("getCellProperties");
@@ -699,6 +699,25 @@ CellPropertyValuesSeq_t 
DomainMapperTableHandler::endTableGetCellProperties(Tabl
                     aCellIterator->get()->Insert( PROP_BOTTOM_BORDER_DISTANCE,
                                                  uno::makeAny((sal_Int32) 
rInfo.nBottomBorderDistance ) );
 
+                // Horizontal merge is not an UNO property, extract that info 
here to rMerges, and then remove it from the map.
+                const PropertyMap::const_iterator aHorizontalMergeIter = 
aCellIterator->get()->find(PROP_HORIZONTAL_MERGE);
+                if (aHorizontalMergeIter != aCellIterator->get()->end())
+                {
+                    if 
(aHorizontalMergeIter->second.getValue().get<sal_Bool>())
+                    {
+                        // first cell in a merge
+                        HorizontallyMergedCell aMerge(nRow, nCell);
+                        rMerges.push_back(aMerge);
+                    }
+                    else if (!rMerges.empty())
+                    {
+                        // resuming an earlier merge
+                        HorizontallyMergedCell& rMerge = rMerges.back();
+                        rMerge.m_nLastRow = nRow;
+                        rMerge.m_nLastCol = nCell;
+                    }
+                    aCellIterator->get()->erase(PROP_HORIZONTAL_MERGE);
+                }
                 pSingleCellProperties[nCell] = 
aCellIterator->get()->GetPropertyValues();
 #ifdef DEBUG_DMAPPER_TABLE_HANDLER
                 dmapper_logger->endElement();
@@ -816,7 +835,8 @@ void DomainMapperTableHandler::endTable(unsigned int 
nestedTableLevel)
     aTableInfo.pTableStyle = endTableGetTableStyle(aTableInfo, 
aFrameProperties);
     //  expands to uno::Sequence< Sequence< beans::PropertyValues > >
 
-    CellPropertyValuesSeq_t aCellProperties = 
endTableGetCellProperties(aTableInfo);
+    std::vector<HorizontallyMergedCell> aMerges;
+    CellPropertyValuesSeq_t aCellProperties = 
endTableGetCellProperties(aTableInfo, aMerges);
 
     RowPropertyValuesSeq_t aRowProperties = endTableGetRowProperties();
 
@@ -849,8 +869,27 @@ void DomainMapperTableHandler::endTable(unsigned int 
nestedTableLevel)
                         aTableInfo.aTableProperties);
 
                 if (xTable.is())
+                {
                     m_xTableRange = xTable->getAnchor( );
 
+                    if (!aMerges.empty())
+                    {
+                        // Perform horizontal merges in reverse order, so the 
fact that merging changes the position of cells won't cause a problem for us.
+                        for 
(std::vector<HorizontallyMergedCell>::reverse_iterator it = aMerges.rbegin(); 
it != aMerges.rend(); ++it)
+                        {
+                            uno::Reference<table::XCellRange> 
xCellRange(xTable, uno::UNO_QUERY_THROW);
+                            uno::Reference<beans::XPropertySet> 
xCell(xCellRange->getCellByPosition(it->m_nFirstCol, it->m_nFirstRow), 
uno::UNO_QUERY_THROW);
+                            OUString aFirst = 
xCell->getPropertyValue("CellName").get<OUString>();
+                            
xCell.set(xCellRange->getCellByPosition(it->m_nLastCol, it->m_nLastRow), 
uno::UNO_QUERY_THROW);
+                            OUString aLast = 
xCell->getPropertyValue("CellName").get<OUString>();
+
+                            uno::Reference<text::XTextTableCursor> xCursor = 
xTable->createCursorByCellName(aFirst);
+                            xCursor->gotoCellByName(aLast, true);
+                            xCursor->mergeRange();
+                        }
+                    }
+                }
+
                 // OOXML table style may container paragraph properties, apply 
these now.
                 for (int i = 0; i < aTableInfo.aTableProperties.getLength(); 
++i)
                 {
diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx 
b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
index 3dc75af..342eb74 100644
--- a/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
+++ b/writerfilter/source/dmapper/DomainMapperTableHandler.hxx
@@ -48,6 +48,21 @@ typedef std::vector<PropertyMapVector1> PropertyMapVector2;
 class DomainMapper_Impl;
 class TableStyleSheetEntry;
 struct TableInfo;
+
+/// A horizontally merged cell is in fact a range of cells till its merge is 
performed.
+struct HorizontallyMergedCell
+{
+    sal_Int32 m_nFirstRow;
+    sal_Int32 m_nFirstCol;
+    sal_Int32 m_nLastRow;
+    sal_Int32 m_nLastCol;
+    HorizontallyMergedCell(sal_Int32 nFirstRow, sal_Int32 nFirstCol)
+        : m_nFirstRow(nFirstRow),
+        m_nFirstCol(nFirstCol)
+    {
+    }
+};
+
 class WRITERFILTER_DLLPRIVATE DomainMapperTableHandler : public 
TableDataHandler<Handle_t , TablePropertyMapPtr >
 {
     TextReference_t         m_xText;
@@ -67,7 +82,7 @@ class WRITERFILTER_DLLPRIVATE DomainMapperTableHandler : 
public TableDataHandler
     sal_Int32 m_nRowIndex;
 
     TableStyleSheetEntry * endTableGetTableStyle(TableInfo & rInfo, 
uno::Sequence<beans::PropertyValue>& rFrameProperties);
-    CellPropertyValuesSeq_t endTableGetCellProperties(TableInfo & rInfo);
+    CellPropertyValuesSeq_t endTableGetCellProperties(TableInfo & rInfo, 
std::vector<HorizontallyMergedCell>& rMerges);
     RowPropertyValuesSeq_t endTableGetRowProperties();
 
 public:
diff --git a/writerfilter/source/dmapper/DomainMapperTableManager.cxx 
b/writerfilter/source/dmapper/DomainMapperTableManager.cxx
index 7db941d..9625a1f 100644
--- a/writerfilter/source/dmapper/DomainMapperTableManager.cxx
+++ b/writerfilter/source/dmapper/DomainMapperTableManager.cxx
@@ -309,6 +309,14 @@ bool DomainMapperTableManager::sprm(Sprm & rSprm)
                 cellProps( pMergeProps);
             }
             break;
+            case NS_ooxml::LN_CT_TcPrBase_hMerge:
+            {
+                // values can be: LN_Value_ST_Merge_restart, 
LN_Value_ST_Merge_continue, in reality the second one is a 0
+                TablePropertyMapPtr pMergeProps(new TablePropertyMap());
+                pMergeProps->Insert(PROP_HORIZONTAL_MERGE, 
uno::makeAny(bool(sal::static_int_cast<Id>(nIntValue) == 
NS_ooxml::LN_Value_ST_Merge_restart)));
+                cellProps(pMergeProps);
+            }
+            break;
             case NS_ooxml::LN_CT_TcPrBase_gridSpan: //number of grid positions 
spanned by this cell
             {
 #ifdef DEBUG_DOMAINMAPPER
diff --git a/writerfilter/source/dmapper/PropertyIds.cxx 
b/writerfilter/source/dmapper/PropertyIds.cxx
index a05249a..1cce816 100644
--- a/writerfilter/source/dmapper/PropertyIds.cxx
+++ b/writerfilter/source/dmapper/PropertyIds.cxx
@@ -359,6 +359,7 @@ OUString PropertyNameSupplier::GetName( PropertyIds eId ) 
const
             case PROP_CHAR_THEME_ORIGINAL_COLOR     :   sName = 
"CharThemeOriginalColor"; break;
             case PROP_CHAR_THEME_COLOR_SHADE        :   sName = 
"CharThemeColorShade"; break;
             case PROP_CHAR_THEME_FILL               :   sName = 
"CharThemeFill"; break;
+            case PROP_HORIZONTAL_MERGE: sName = "HorizontalMerge"; break;
         }
         ::std::pair<PropertyNameMap_t::iterator,bool> aInsertIt =
                 m_pImpl->aNameMap.insert( PropertyNameMap_t::value_type( eId, 
sName ));
diff --git a/writerfilter/source/dmapper/PropertyIds.hxx 
b/writerfilter/source/dmapper/PropertyIds.hxx
index ae3e02a..2a9c1ee 100644
--- a/writerfilter/source/dmapper/PropertyIds.hxx
+++ b/writerfilter/source/dmapper/PropertyIds.hxx
@@ -330,6 +330,7 @@ enum PropertyIds
         ,PROP_CHAR_THEME_ORIGINAL_COLOR
         ,PROP_CHAR_THEME_COLOR_SHADE
         ,PROP_CHAR_THEME_FILL
+        ,PROP_HORIZONTAL_MERGE
     };
 struct PropertyNameSupplier_Impl;
 class PropertyNameSupplier
_______________________________________________
Libreoffice-commits mailing list
libreoffice-comm...@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits

Reply via email to