sw/source/filter/ww8/docxattributeoutput.cxx | 145 +++++++++++---- sw/source/filter/ww8/docxattributeoutput.hxx | 4 writerfilter/source/dmapper/DomainMapperTableHandler.cxx | 27 +- 3 files changed, 126 insertions(+), 50 deletions(-)
New commits: commit 47d9a8a3397ed2f4ff7e7ec1bba392da34d8519e Author: Pierre-Eric Pelloux-Prayer <pierre-e...@lanedo.com> Date: Thu Sep 27 10:15:58 2012 +0200 n#780645 docx import: properly import table position This a follow up of commit 53b7f7df0617bcbd7bbef9a34ef53e5097eb16dc Reviewed-on: https://gerrit.libreoffice.org/714 Reviewed-by: Miklos Vajna <vmik...@suse.cz> Tested-by: Miklos Vajna <vmik...@suse.cz> (cherry picked from commit 3cb619bd15a6017f253891f4c377fc790d8aae82) Change-Id: Ia0f79ca24418636af14162e9f339237d847dc221 diff --git a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx index 91d652d..f44e93c 100644 --- a/writerfilter/source/dmapper/DomainMapperTableHandler.cxx +++ b/writerfilter/source/dmapper/DomainMapperTableHandler.cxx @@ -403,7 +403,7 @@ TableStyleSheetEntry * DomainMapperTableHandler::endTableGetTableStyle(TableInfo //table border settings table::TableBorder aTableBorder; - table::BorderLine2 aBorderLine; + table::BorderLine2 aBorderLine, aLeftBorder; if (lcl_extractTableBorderProperty(m_aTableProperties, PROP_TOP_BORDER, rInfo, aBorderLine)) { @@ -415,10 +415,11 @@ TableStyleSheetEntry * DomainMapperTableHandler::endTableGetTableStyle(TableInfo aTableBorder.BottomLine = aBorderLine; aTableBorder.IsBottomLineValid = sal_True; } - if (lcl_extractTableBorderProperty(m_aTableProperties, PROP_LEFT_BORDER, rInfo, aBorderLine)) + if (lcl_extractTableBorderProperty(m_aTableProperties, PROP_LEFT_BORDER, rInfo, aLeftBorder)) { - aTableBorder.LeftLine = aBorderLine; + aTableBorder.LeftLine = aLeftBorder; aTableBorder.IsLeftLineValid = sal_True; + rInfo.nLeftBorderDistance += aLeftBorder.LineWidth * 0.5; } if (lcl_extractTableBorderProperty(m_aTableProperties, PROP_RIGHT_BORDER, rInfo, aBorderLine)) { @@ -445,23 +446,17 @@ TableStyleSheetEntry * DomainMapperTableHandler::endTableGetTableStyle(TableInfo lcl_debug_TableBorder(aTableBorder); #endif - // Mimic Office behavior : if tlbInd is defined, use it place table. - // Otherwise, top-level table's position depends w:tblCellMar attribute (but not nested tables) - if (nLeftMargin) + // Table position in Office is computed in 2 different ways : + // - top level tables: the goal is to have in-cell text starting at table indent pos (tblInd), + // so table's position depends on table's cells margin + // - nested tables: the goal is to have left-most border starting at table_indent pos + if (rInfo.nNestLevel > 1) { - m_aTableProperties->Insert( PROP_LEFT_MARGIN, false, uno::makeAny( nLeftMargin - nGapHalf)); + m_aTableProperties->Insert( PROP_LEFT_MARGIN, false, uno::makeAny( nLeftMargin - nGapHalf )); } else { - // TODO: top-level position depends on w:tblCellMar attribute, not w:cellMar - if (rInfo.nNestLevel > 1) - { - m_aTableProperties->Insert( PROP_LEFT_MARGIN, false, uno::makeAny( - nGapHalf)); - } - else - { - m_aTableProperties->Insert( PROP_LEFT_MARGIN, false, uno::makeAny( - nGapHalf - rInfo.nLeftBorderDistance)); - } + m_aTableProperties->Insert( PROP_LEFT_MARGIN, false, uno::makeAny( nLeftMargin - nGapHalf - rInfo.nLeftBorderDistance )); } m_aTableProperties->getValue( TablePropertyMap::TABLE_WIDTH, nTableWidth ); commit 2cefbc6622e8838e049542376ea76c4c4179fbb3 Author: Pierre-Eric Pelloux-Prayer <pierre-e...@lanedo.com> Date: Thu Sep 27 17:00:08 2012 +0200 n#780645 docx export: export default table cell margins, based on 1st cell Reviewed-on: https://gerrit.libreoffice.org/716 Reviewed-by: Miklos Vajna <vmik...@suse.cz> Tested-by: Miklos Vajna <vmik...@suse.cz> (cherry picked from commit 9751056ba806ba9614392f3c70ada3cbd1251814) Change-Id: I1a697c2a60c7979774242fb6c9b0f66baa3bb72e diff --git a/sw/source/filter/ww8/docxattributeoutput.cxx b/sw/source/filter/ww8/docxattributeoutput.cxx index 179c2f6..b9f2295 100644 --- a/sw/source/filter/ww8/docxattributeoutput.cxx +++ b/sw/source/filter/ww8/docxattributeoutput.cxx @@ -1503,7 +1503,7 @@ static void impl_borderLine( FSHelperPtr pSerializer, sal_Int32 elementToken, co pSerializer->singleElementNS( XML_w, elementToken, xAttrs ); } -static void impl_pageBorders( FSHelperPtr pSerializer, const SvxBoxItem& rBox, bool bUseStartEnd = false ) +static void impl_pageBorders( FSHelperPtr pSerializer, const SvxBoxItem& rBox, sal_Int32 tag, bool bUseStartEnd = false, bool bWriteTag = true, const SvxBoxItem* pDefaultBorders = 0) { static const sal_uInt16 aBorders[] = { @@ -1517,12 +1517,91 @@ static void impl_pageBorders( FSHelperPtr pSerializer, const SvxBoxItem& rBox, b XML_bottom, bUseStartEnd ? XML_end : XML_right }; + bool tagWritten = false; const sal_uInt16* pBrd = aBorders; for( int i = 0; i < 4; ++i, ++pBrd ) { const SvxBorderLine* pLn = rBox.GetLine( *pBrd ); if ( pLn ) + { + if ( pDefaultBorders ) + { + const SvxBorderLine* pRefLn = pDefaultBorders->GetLine( *pBrd ); + + // If border is equal to default border: do not output + if ( pRefLn && *pLn == *pRefLn) { + continue; + } + } + + if (!tagWritten && bWriteTag) { + pSerializer->startElementNS( XML_w, tag, FSEND ); + tagWritten = true; + } + impl_borderLine( pSerializer, aXmlElements[i], pLn, 0 ); + + // When exporting default borders, we need to export these 2 attr + if ( pDefaultBorders == 0 ) { + if ( i == 2 ) + impl_borderLine( pSerializer, XML_insideH, pLn, 0 ); + else if ( i == 3 ) + impl_borderLine( pSerializer, XML_insideV, pLn, 0 ); + } + } + } + if (tagWritten && bWriteTag) { + pSerializer->endElementNS( XML_w, tag ); + } +} + +static void impl_cellMargins( FSHelperPtr pSerializer, const SvxBoxItem& rBox, sal_Int32 tag, bool bUseStartEnd = false, const SvxBoxItem* pDefaultMargins = 0) +{ + static const sal_uInt16 aBorders[] = + { + BOX_LINE_TOP, BOX_LINE_LEFT, BOX_LINE_BOTTOM, BOX_LINE_RIGHT + }; + + const sal_Int32 aXmlElements[] = + { + XML_top, + bUseStartEnd ? XML_start : XML_left, + XML_bottom, + bUseStartEnd ? XML_end : XML_right + }; + bool tagWritten = false; + const sal_uInt16* pBrd = aBorders; + for( int i = 0; i < 4; ++i, ++pBrd ) + { + sal_Int32 nDist = sal_Int32( rBox.GetDistance( *pBrd ) ); + + if ( aBorders[i] == BOX_LINE_LEFT ) { + // Office's cell margin is measured from the right of the border. + // While LO's cell spacing is measured from the center of the border. + // So we add half left-border width to tblIndent value + const SvxBorderLine* pLn = rBox.GetLine( *pBrd ); + if (pLn) + nDist -= pLn->GetWidth() * 0.5; + } + + if (pDefaultMargins) + { + // Skip output if cell margin == table default margin + if (sal_Int32( pDefaultMargins->GetDistance( *pBrd ) ) == nDist) + continue; + } + + if (!tagWritten) { + pSerializer->startElementNS( XML_w, tag, FSEND ); + tagWritten = true; + } + pSerializer->singleElementNS( XML_w, aXmlElements[i], + FSNS( XML_w, XML_w ), OString::valueOf( nDist ).getStr( ), + FSNS( XML_w, XML_type ), "dxa", + FSEND ); + } + if (tagWritten) { + pSerializer->endElementNS( XML_w, tag ); } } @@ -1569,41 +1648,20 @@ void DocxAttributeOutput::TableCellProperties( ww8::WW8TableNodeInfoInner::Point FSEND ); } - // The cell borders - m_pSerializer->startElementNS( XML_w, XML_tcBorders, FSEND ); - SwFrmFmt *pFmt = pTblBox->GetFrmFmt( ); - impl_pageBorders( m_pSerializer, pFmt->GetBox( ), !bEcma ); - m_pSerializer->endElementNS( XML_w, XML_tcBorders ); + const SvxBoxItem& rBox = pTblBox->GetFrmFmt( )->GetBox( ); + const SvxBoxItem& rDefaultBox = (*tableFirstCells.rbegin())->getTableBox( )->GetFrmFmt( )->GetBox( ); + { + // The cell borders + impl_pageBorders( m_pSerializer, rBox, XML_tcBorders, !bEcma, true, &rDefaultBox ); + } TableBackgrounds( pTableTextNodeInfoInner ); - // Cell margins - m_pSerializer->startElementNS( XML_w, XML_tcMar, FSEND ); - const SvxBoxItem& rBox = pFmt->GetBox( ); - static const sal_uInt16 aBorders[] = { - BOX_LINE_TOP, BOX_LINE_LEFT, BOX_LINE_BOTTOM, BOX_LINE_RIGHT - }; - - const sal_Int32 aXmlElements[] = - { - XML_top, - bEcma ? XML_left : XML_start, - XML_bottom, - bEcma ? XML_right : XML_end - }; - const sal_uInt16* pBrd = aBorders; - for( int i = 0; i < 4; ++i, ++pBrd ) - { - sal_Int32 nDist = sal_Int32( rBox.GetDistance( *pBrd ) ); - m_pSerializer->singleElementNS( XML_w, aXmlElements[i], - FSNS( XML_w, XML_w ), OString::valueOf( nDist ).getStr( ), - FSNS( XML_w, XML_type ), "dxa", - FSEND ); + // Cell margins + impl_cellMargins( m_pSerializer, rBox, XML_tcMar, !bEcma, &rDefaultBox ); } - m_pSerializer->endElementNS( XML_w, XML_tcMar ); - TableVerticalCell( pTableTextNodeInfoInner ); m_pSerializer->endElementNS( XML_w, XML_tcPr ); @@ -1633,6 +1691,8 @@ void DocxAttributeOutput::StartTable( ww8::WW8TableNodeInfoInner::Pointer_t pTab { m_pSerializer->startElementNS( XML_w, XML_tbl, FSEND ); + tableFirstCells.push_back(pTableTextNodeInfoInner); + InitTableHelper( pTableTextNodeInfoInner ); TableDefinition( pTableTextNodeInfoInner ); } @@ -1644,6 +1704,8 @@ void DocxAttributeOutput::EndTable() if ( m_nTableDepth > 0 ) --m_nTableDepth; + tableFirstCells.pop_back(); + // We closed the table; if it is a nested table, the cell that contains it // still continues m_bTableCellOpen = true; @@ -1788,6 +1850,10 @@ void DocxAttributeOutput::TableDefinition( ww8::WW8TableNodeInfoInner::Pointer_t // Output the table borders TableDefaultBorders( pTableTextNodeInfoInner ); + + // Output the default cell margins + TableDefaultCellMargins( pTableTextNodeInfoInner, nIndent ); + TableBidi( pTableTextNodeInfoInner ); // Table indent @@ -1826,9 +1892,20 @@ void DocxAttributeOutput::TableDefaultBorders( ww8::WW8TableNodeInfoInner::Point bool bEcma = GetExport().GetFilter().getVersion( ) == oox::core::ECMA_DIALECT; // the defaults of the table are taken from the top-left cell - m_pSerializer->startElementNS( XML_w, XML_tblBorders, FSEND ); - impl_pageBorders( m_pSerializer, pFrmFmt->GetBox( ), !bEcma ); - m_pSerializer->endElementNS( XML_w, XML_tblBorders ); + impl_pageBorders( m_pSerializer, pFrmFmt->GetBox( ), XML_tblBorders, !bEcma, true ); +} + +void DocxAttributeOutput::TableDefaultCellMargins( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner, sal_Int32& tblIndent ) +{ + const SwTableBox * pTabBox = pTableTextNodeInfoInner->getTableBox(); + const SwFrmFmt * pFrmFmt = pTabBox->GetFrmFmt(); + const SvxBoxItem& rBox = pFrmFmt->GetBox( ); + const bool bEcma = GetExport().GetFilter().getVersion( ) == oox::core::ECMA_DIALECT; + + impl_cellMargins(m_pSerializer, rBox, XML_tblCellMar, !bEcma); + + // add table cell left margin to tblIndent + tblIndent += sal_Int32( rBox.GetDistance( BOX_LINE_LEFT ) ); } void DocxAttributeOutput::TableBackgrounds( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ) @@ -4255,7 +4332,7 @@ void DocxAttributeOutput::FormatBox( const SvxBoxItem& rBox ) m_pSerializer->startElementNS( XML_w, XML_pBdr, FSEND ); } - impl_pageBorders( m_pSerializer, rBox ); + impl_pageBorders( m_pSerializer, rBox, false, false ); if ( m_bOpenedSectPr ) { diff --git a/sw/source/filter/ww8/docxattributeoutput.hxx b/sw/source/filter/ww8/docxattributeoutput.hxx index 4caf047..c425ee8 100644 --- a/sw/source/filter/ww8/docxattributeoutput.hxx +++ b/sw/source/filter/ww8/docxattributeoutput.hxx @@ -153,6 +153,7 @@ public: virtual void TableInfoRow( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); virtual void TableDefinition( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); virtual void TableDefaultBorders( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); + virtual void TableDefaultCellMargins( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner, sal_Int32& tblIndent ); virtual void TableBackgrounds( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); virtual void TableHeight( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); virtual void TableCanSplit( ww8::WW8TableNodeInfoInner::Pointer_t pTableTextNodeInfoInner ); @@ -605,6 +606,9 @@ private: unsigned int m_postitFieldsMaxId; int m_anchorId; + // Remember first cell (used for for default borders/margins) of each table + std::vector<ww8::WW8TableNodeInfoInner::Pointer_t> tableFirstCells; + public: DocxAttributeOutput( DocxExport &rExport, ::sax_fastparser::FSHelperPtr pSerializer, oox::drawingml::DrawingML* pDrawingML ); _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits