sw/qa/extras/ooxmlimport/data/fdo68787.docx |binary sw/qa/extras/ooxmlimport/ooxmlimport.cxx | 9 +++++++++ writerfilter/source/dmapper/DomainMapper.cxx | 16 ++++++++++++++++ writerfilter/source/dmapper/DomainMapper_Impl.cxx | 4 +++- writerfilter/source/dmapper/DomainMapper_Impl.hxx | 6 ++++++ writerfilter/source/dmapper/PropertyIds.cxx | 1 + writerfilter/source/dmapper/PropertyIds.hxx | 1 + writerfilter/source/dmapper/PropertyMap.cxx | 3 +++ writerfilter/source/ooxml/OOXMLFastContextHandler.cxx | 15 +++++++++++++-- writerfilter/source/ooxml/OOXMLFastContextHandler.hxx | 3 +++ writerfilter/source/ooxml/model.xml | 2 +- 11 files changed, 56 insertions(+), 4 deletions(-)
New commits: commit 330b860205c7ba69dd6603f65324d0f89ad9cd5f Author: Miklos Vajna <vmik...@collabora.co.uk> Date: Wed Sep 4 16:08:49 2013 +0200 fdo#68787 DOCX import: handle when w:separator is missing for footnotes There were two problems here: 1) OOXML has no way to explicitly disable the footnote separator, what is does is that it omits the <w:separator/> element in that case. We didn't parse that previously -- now we do, and if it's missing, the separator is disabled. 2) The footnote stream isn't read by the importer, only when the main stream references the footnote one, the relevant part of it is parsed. At the moment we always parse the first (special, "separator") entry in the footnote stream, that may be optimized later if it becomes a bottleneck. Change-Id: Ie588270a212fc90fc41095029a362cfd832b24f8 diff --git a/sw/qa/extras/ooxmlimport/data/fdo68787.docx b/sw/qa/extras/ooxmlimport/data/fdo68787.docx new file mode 100644 index 0000000..c47b809 Binary files /dev/null and b/sw/qa/extras/ooxmlimport/data/fdo68787.docx differ diff --git a/sw/qa/extras/ooxmlimport/ooxmlimport.cxx b/sw/qa/extras/ooxmlimport/ooxmlimport.cxx index 973f3b1..bfae9a3 100644 --- a/sw/qa/extras/ooxmlimport/ooxmlimport.cxx +++ b/sw/qa/extras/ooxmlimport/ooxmlimport.cxx @@ -131,6 +131,7 @@ public: void testTableStyleParprop(); void testTablePagebreak(); void testFdo68607(); + void testFdo68787(); CPPUNIT_TEST_SUITE(Test); #if !defined(MACOSX) && !defined(WNT) @@ -228,6 +229,7 @@ void Test::run() {"table-style-parprop.docx", &Test::testTableStyleParprop}, {"table-pagebreak.docx", &Test::testTablePagebreak}, {"fdo68607.docx", &Test::testFdo68607}, + {"fdo68787.docx", &Test::testFdo68787}, }; header(); for (unsigned int i = 0; i < SAL_N_ELEMENTS(aMethods); ++i) @@ -1540,6 +1542,13 @@ void Test::testFdo68607() CPPUNIT_ASSERT(getPages() > 1); } +void Test::testFdo68787() +{ + uno::Reference<beans::XPropertySet> xPageStyle(getStyles("PageStyles")->getByName(DEFAULT_STYLE), uno::UNO_QUERY); + // This was 25, the 'lack of w:separator' <-> '0 line width' mapping was missing. + CPPUNIT_ASSERT_EQUAL(sal_Int32(0), getProperty<sal_Int32>(xPageStyle, "FootnoteLineRelativeWidth")); +} + CPPUNIT_TEST_SUITE_REGISTRATION(Test); CPPUNIT_PLUGIN_IMPLEMENT(); diff --git a/writerfilter/source/dmapper/DomainMapper.cxx b/writerfilter/source/dmapper/DomainMapper.cxx index 261d99c..0dc4667 100644 --- a/writerfilter/source/dmapper/DomainMapper.cxx +++ b/writerfilter/source/dmapper/DomainMapper.cxx @@ -1465,6 +1465,11 @@ void DomainMapper::lcl_attribute(Id nName, Value & val) if (pSectionContext != NULL) pSectionContext->SetPageNumber(nIntValue); break; + case NS_ooxml::LN_CT_FtnEdn_type: + // This is the "separator" footnote, ignore its linebreak. + if (static_cast<sal_uInt32>(nIntValue) == NS_ooxml::LN_Value_wordprocessingml_ST_FtnEdn_separator) + m_pImpl->m_bIgnoreNextPara = true; + break; default: { #if OSL_DEBUG_LEVEL > 0 @@ -3728,6 +3733,12 @@ void DomainMapper::lcl_utext(const sal_uInt8 * data_, size_t len) m_pImpl->m_pSdtHelper->createDateControl(sText); return; } + else if (len == 1 && sText[0] == 0x03) + { + // This is the uFtnEdnSep, remember that the document has a separator. + m_pImpl->m_bHasFtnSep = true; + return; + } try { @@ -3735,6 +3746,11 @@ void DomainMapper::lcl_utext(const sal_uInt8 * data_, size_t len) if(len == 1 && (sText[0] == 0x0d || sText[0] == 0x07)) { + if (m_pImpl->m_bIgnoreNextPara) + { + m_pImpl->m_bIgnoreNextPara = false; + return; + } PropertyMapPtr pContext = m_pImpl->GetTopContextOfType(CONTEXT_PARAGRAPH); if (pContext && m_pImpl->GetSettingsTable()->GetSplitPgBreakAndParaMark()) { diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.cxx b/writerfilter/source/dmapper/DomainMapper_Impl.cxx index 8a4b252..c89fdf2 100644 --- a/writerfilter/source/dmapper/DomainMapper_Impl.cxx +++ b/writerfilter/source/dmapper/DomainMapper_Impl.cxx @@ -175,7 +175,9 @@ DomainMapper_Impl::DomainMapper_Impl( m_bIsNewDoc(bIsNewDoc), m_bInTableStyleRunProps(false), m_pSdtHelper(0), - m_nTableDepth(0) + m_nTableDepth(0), + m_bHasFtnSep(false), + m_bIgnoreNextPara(false) { appendTableManager( ); diff --git a/writerfilter/source/dmapper/DomainMapper_Impl.hxx b/writerfilter/source/dmapper/DomainMapper_Impl.hxx index 9b1ebe1..0da21a0 100644 --- a/writerfilter/source/dmapper/DomainMapper_Impl.hxx +++ b/writerfilter/source/dmapper/DomainMapper_Impl.hxx @@ -701,6 +701,12 @@ public: * PFInTable SPRM or not). */ sal_Int32 m_nTableDepth; + + /// If the document has a footnote separator. + bool m_bHasFtnSep; + + /// If the next newline should be ignored, used by the special footnote separator paragraph. + bool m_bIgnoreNextPara; }; } //namespace dmapper } //namespace writerfilter diff --git a/writerfilter/source/dmapper/PropertyIds.cxx b/writerfilter/source/dmapper/PropertyIds.cxx index 34a0017..27ebabc 100644 --- a/writerfilter/source/dmapper/PropertyIds.cxx +++ b/writerfilter/source/dmapper/PropertyIds.cxx @@ -331,6 +331,7 @@ const OUString& PropertyNameSupplier::GetName( PropertyIds eId ) const case PROP_MIRROR_INDENTS : sName = "MirrorIndents"; break; case PROP_SURROUND_TEXT_WRAP_SMALL: sName = "SurroundTextWrapSmall"; break; case PROP_PARA_SHADOW_FORMAT: sName = "ParaShadowFormat"; break; + case PROP_FOOTNOTE_LINE_RELATIVE_WIDTH: sName = "FootnoteLineRelativeWidth"; 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 de53e7d..f35cdfd 100644 --- a/writerfilter/source/dmapper/PropertyIds.hxx +++ b/writerfilter/source/dmapper/PropertyIds.hxx @@ -302,6 +302,7 @@ enum PropertyIds ,PROP_MIRROR_INDENTS ,PROP_SURROUND_TEXT_WRAP_SMALL ,PROP_PARA_SHADOW_FORMAT + ,PROP_FOOTNOTE_LINE_RELATIVE_WIDTH }; struct PropertyNameSupplier_Impl; class PropertyNameSupplier diff --git a/writerfilter/source/dmapper/PropertyMap.cxx b/writerfilter/source/dmapper/PropertyMap.cxx index d4cbbf2..91ab014 100644 --- a/writerfilter/source/dmapper/PropertyMap.cxx +++ b/writerfilter/source/dmapper/PropertyMap.cxx @@ -864,6 +864,9 @@ void SectionPropertyMap::HandleMarginsHeaderFooter(DomainMapper_Impl& rDM_Impl) if (rDM_Impl.m_oBackgroundColor) operator[](PropertyDefinition(PROP_BACK_COLOR )) = uno::makeAny(*rDM_Impl.m_oBackgroundColor); + if (!rDM_Impl.m_bHasFtnSep) + // Set footnote line width to zero, document has no footnote separator. + operator[](PropertyDefinition(PROP_FOOTNOTE_LINE_RELATIVE_WIDTH)) = uno::makeAny(sal_Int32(0)); /*** if headers/footers are available then the top/bottom margins of the header/footer are copied to the top/bottom margin of the page diff --git a/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx b/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx index 8845623..e3962f5 100644 --- a/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx +++ b/writerfilter/source/ooxml/OOXMLFastContextHandler.cxx @@ -1748,7 +1748,7 @@ void OOXMLFastContextHandlerTable::newPropertySet OOXMLFastContextHandlerXNote::OOXMLFastContextHandlerXNote (OOXMLFastContextHandler * pContext) -: OOXMLFastContextHandlerProperties(pContext), mbForwardEventsSaved(false) +: OOXMLFastContextHandlerProperties(pContext), mbForwardEventsSaved(false), mnMyXNoteType(0) { } @@ -1763,7 +1763,8 @@ void OOXMLFastContextHandlerXNote::lcl_startFastElement { mbForwardEventsSaved = isForwardEvents(); - if (mnMyXNoteId == getXNoteId()) + // If this is the note we're looking for or this is the footnote separator one. + if (mnMyXNoteId == getXNoteId() || static_cast<sal_uInt32>(mnMyXNoteType) == NS_ooxml::LN_Value_wordprocessingml_ST_FtnEdn_separator) setForwardEvents(true); else setForwardEvents(false); @@ -1794,6 +1795,16 @@ void OOXMLFastContextHandlerXNote::checkId(OOXMLValue::Pointer_t pValue) mnMyXNoteId = sal_Int32(pValue->getInt()); } +void OOXMLFastContextHandlerXNote::checkType(OOXMLValue::Pointer_t pValue) +{ +#ifdef DEBUG_ELEMENT + debug_logger->startElement("checkType"); + debug_logger->attribute("myType", sal_Int32(pValue->getInt())); + debug_logger->endElement(); +#endif + mnMyXNoteType = pValue->getInt(); +} + /* class OOXMLFastContextHandlerTextTableCell */ diff --git a/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx b/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx index 5a72be2..d26dcda7 100644 --- a/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx +++ b/writerfilter/source/ooxml/OOXMLFastContextHandler.hxx @@ -432,11 +432,14 @@ public: void checkId(OOXMLValue::Pointer_t pValue); + void checkType(OOXMLValue::Pointer_t pValue); + virtual string getType() const { return "XNote"; } private: bool mbForwardEventsSaved; sal_Int32 mnMyXNoteId; + sal_Int32 mnMyXNoteType; virtual void lcl_startFastElement (Token_t Element, diff --git a/writerfilter/source/ooxml/model.xml b/writerfilter/source/ooxml/model.xml index 63c182c..3f0ed5a 100644 --- a/writerfilter/source/ooxml/model.xml +++ b/writerfilter/source/ooxml/model.xml @@ -23120,7 +23120,7 @@ <attribute name="id" tokenid="ooxml:CT_FtnEdnSepRef_id"/> </resource> <resource name="CT_FtnEdn" resource="XNote" tag="reference"> - <attribute name="type" tokenid="ooxml:CT_FtnEdn_type"/> + <attribute name="type" tokenid="ooxml:CT_FtnEdn_type" action="checkType"/> <attribute name="id" tokenid="ooxml:CT_FtnEdn_id" action="checkId"/> <action name="start" action="propagateCharacterProperties"/> <action name="end" action="endSectionGroup"/> _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits