From c6d3d0642e0f5d24cab402a8a7c6f81406d044cf Mon Sep 17 00:00:00 2001 From: Mark Hung Date: Tue, 20 Feb 2018 18:40:38 +0800 Subject: tdf#115623: invoke openPageSpan / closePageSpan * For paragraphs or tables whose styles specify style:master-page-name, it indicate starting a new page style and should invoke openPageSpan / closePageSapn properly. * closePageSpan at the end of text body is invoked. Change-Id: Ic85157c9b1a43c94a027b464ad9105e9072afcf7 Reviewed-on: https://gerrit.libreoffice.org/52082 Tested-by: Jenkins Reviewed-by: Miklos Vajna --- writerperfect/qa/unit/EPUBExportTest.cxx | 55 +++++++++++++++++++++ .../writer/epubexport/tdf115623-many-pagespans.odt | Bin 0 -> 8591 bytes .../epubexport/tdf115623-single-writing-mode.odt | Bin 0 -> 8562 bytes .../epubexport/tdf115623-split-by-chapter.odt | Bin 0 -> 9346 bytes writerperfect/source/writer/exp/txtparai.cxx | 1 + writerperfect/source/writer/exp/txtstyli.cxx | 1 + writerperfect/source/writer/exp/xmlimp.cxx | 32 ++++++++++++ writerperfect/source/writer/exp/xmlimp.hxx | 5 ++ writerperfect/source/writer/exp/xmltbli.cxx | 3 ++ writerperfect/source/writer/exp/xmltext.cxx | 7 +++ writerperfect/source/writer/exp/xmltext.hxx | 1 + 11 files changed, 105 insertions(+) create mode 100644 writerperfect/qa/unit/data/writer/epubexport/tdf115623-many-pagespans.odt create mode 100644 writerperfect/qa/unit/data/writer/epubexport/tdf115623-single-writing-mode.odt create mode 100644 writerperfect/qa/unit/data/writer/epubexport/tdf115623-split-by-chapter.odt diff --git a/writerperfect/qa/unit/EPUBExportTest.cxx b/writerperfect/qa/unit/EPUBExportTest.cxx index 81d70591a0da..231c63252efd 100644 --- a/writerperfect/qa/unit/EPUBExportTest.cxx +++ b/writerperfect/qa/unit/EPUBExportTest.cxx @@ -98,6 +98,9 @@ public: void testPopupAPI(); void testPageSize(); void testSVG(); + void testTdf115623SingleWritingMode(); + void testTdf115623SplitByChapter(); + void testTdf115623ManyPageSpans(); CPPUNIT_TEST_SUITE(EPUBExportTest); CPPUNIT_TEST(testOutlineLevel); @@ -144,6 +147,9 @@ public: CPPUNIT_TEST(testPopupAPI); CPPUNIT_TEST(testPageSize); CPPUNIT_TEST(testSVG); + CPPUNIT_TEST(testTdf115623SingleWritingMode); + CPPUNIT_TEST(testTdf115623SplitByChapter); + CPPUNIT_TEST(testTdf115623ManyPageSpans); CPPUNIT_TEST_SUITE_END(); }; @@ -881,6 +887,55 @@ void EPUBExportTest::testSVG() assertXPathNSDef(mpXmlDoc, "/svg:svg", "xlink", "http://www.w3.org/1999/xlink"); } + +void EPUBExportTest::testTdf115623SingleWritingMode() +{ + // Simple page that has single writing mode should work. + createDoc("tdf115623-single-writing-mode.odt", {}); + std::map< OUString, std::vector > aCssDoc = parseCss("OEBPS/styles/stylesheet.css"); + mpXmlDoc = parseExport("OEBPS/sections/section0001.xhtml"); + OUString aClass = getXPath(mpXmlDoc, "//xhtml:body", "class"); + CPPUNIT_ASSERT_EQUAL(OUString("vertical-rl"), EPUBExportTest::getCss(aCssDoc, aClass, "writing-mode")); +} + +void EPUBExportTest::testTdf115623SplitByChapter() +{ + createDoc("tdf115623-split-by-chapter.odt", {}); + std::map< OUString, std::vector > aCssDoc = parseCss("OEBPS/styles/stylesheet.css"); + { + mpXmlDoc = parseExport("OEBPS/sections/section0001.xhtml"); + OUString aClass = getXPath(mpXmlDoc, "//xhtml:body", "class"); + CPPUNIT_ASSERT_EQUAL(OUString("vertical-rl"), EPUBExportTest::getCss(aCssDoc, aClass, "writing-mode")); + xmlFreeDoc(mpXmlDoc); + mpXmlDoc = nullptr; + } + // Splitted HTML should keep the same writing-mode. + { + mpXmlDoc = parseExport("OEBPS/sections/section0002.xhtml"); + OUString aClass = getXPath(mpXmlDoc, "//xhtml:body", "class"); + CPPUNIT_ASSERT_EQUAL(OUString("vertical-rl"), EPUBExportTest::getCss(aCssDoc, aClass, "writing-mode")); + } +} + +void EPUBExportTest::testTdf115623ManyPageSpans() +{ + createDoc("tdf115623-many-pagespans.odt", {}); + std::map< OUString, std::vector > aCssDoc = parseCss("OEBPS/styles/stylesheet.css"); + // Two pages should have different writing modes. + { + mpXmlDoc = parseExport("OEBPS/sections/section0001.xhtml"); + OUString aClass = getXPath(mpXmlDoc, "//xhtml:body", "class"); + CPPUNIT_ASSERT_EQUAL(OUString("vertical-rl"), EPUBExportTest::getCss(aCssDoc, aClass, "writing-mode")); + xmlFreeDoc(mpXmlDoc); + mpXmlDoc = nullptr; + } + { + mpXmlDoc = parseExport("OEBPS/sections/section0002.xhtml"); + OUString aClass = getXPath(mpXmlDoc, "//xhtml:body", "class"); + CPPUNIT_ASSERT_EQUAL(OUString("horizontal-tb"), EPUBExportTest::getCss(aCssDoc, aClass, "writing-mode")); + } +} + CPPUNIT_TEST_SUITE_REGISTRATION(EPUBExportTest); } diff --git a/writerperfect/qa/unit/data/writer/epubexport/tdf115623-many-pagespans.odt b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-many-pagespans.odt new file mode 100644 index 000000000000..3e7c291aa197 Binary files /dev/null and b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-many-pagespans.odt differ diff --git a/writerperfect/qa/unit/data/writer/epubexport/tdf115623-single-writing-mode.odt b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-single-writing-mode.odt new file mode 100644 index 000000000000..4c374a1bd478 Binary files /dev/null and b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-single-writing-mode.odt differ diff --git a/writerperfect/qa/unit/data/writer/epubexport/tdf115623-split-by-chapter.odt b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-split-by-chapter.odt new file mode 100644 index 000000000000..ee6d48296ff4 Binary files /dev/null and b/writerperfect/qa/unit/data/writer/epubexport/tdf115623-split-by-chapter.odt differ diff --git a/writerperfect/source/writer/exp/txtparai.cxx b/writerperfect/source/writer/exp/txtparai.cxx index 904c865bf90d..e02e83d5fdbf 100644 --- a/writerperfect/source/writer/exp/txtparai.cxx +++ b/writerperfect/source/writer/exp/txtparai.cxx @@ -402,6 +402,7 @@ void XMLParaContext::startElement(const OUString &/*rName*/, const css::uno::Ref m_aStyleName = rAttributeValue; FillStyles(m_aStyleName, mrImport.GetAutomaticParagraphStyles(), mrImport.GetParagraphStyles(), aPropertyList); FillStyles(m_aStyleName, mrImport.GetAutomaticTextStyles(), mrImport.GetTextStyles(), m_aTextPropertyList); + mrImport.HandlePageSpan(aPropertyList); } else { diff --git a/writerperfect/source/writer/exp/txtstyli.cxx b/writerperfect/source/writer/exp/txtstyli.cxx index 548aa654dcdf..90cc66b9c80b 100644 --- a/writerperfect/source/writer/exp/txtstyli.cxx +++ b/writerperfect/source/writer/exp/txtstyli.cxx @@ -296,6 +296,7 @@ void XMLStyleContext::startElement(const OUString &/*rName*/, const css::uno::Re m_aGraphicPropertyList.insert(sName.getStr(), sValue.getStr()); m_aPageLayoutPropertyList.insert(sName.getStr(), sValue.getStr()); m_aMasterPagePropertyList.insert(sName.getStr(), sValue.getStr()); + m_aTablePropertyList.insert(sName.getStr(), sValue.getStr()); } } diff --git a/writerperfect/source/writer/exp/xmlimp.cxx b/writerperfect/source/writer/exp/xmlimp.cxx index 9ef9afa837c1..5c22a5f911d7 100644 --- a/writerperfect/source/writer/exp/xmlimp.cxx +++ b/writerperfect/source/writer/exp/xmlimp.cxx @@ -339,6 +339,7 @@ void XMLOfficeDocContext::HandleFixedLayoutPage(const FixedLayoutPage &rPage, bo XMLImport::XMLImport(const uno::Reference &xContext, librevenge::RVNGTextInterface &rGenerator, const OUString &rURL, const uno::Sequence &rDescriptor, const std::vector &rPageMetafiles) : mrGenerator(rGenerator), mxContext(xContext), + mbIsInPageSpan(false), mrPageMetafiles(rPageMetafiles) { uno::Sequence aFilterData; @@ -595,6 +596,37 @@ void XMLImport::setDocumentLocator(const uno::Reference &/*x { } +void XMLImport::HandlePageSpan(const librevenge::RVNGPropertyList &rPropertyList) +{ + OUString sMasterPageName; + OUString sLayoutName; + + if (rPropertyList["style:master-page-name"]) + sMasterPageName = OStringToOUString(rPropertyList["style:master-page-name"]->getStr().cstr(), RTL_TEXTENCODING_UTF8); + else if (!GetIsInPageSpan()) + sMasterPageName = "Standard"; + + if (sMasterPageName.getLength()) + { + librevenge::RVNGPropertyList &rMasterPage = GetMasterStyles()[sMasterPageName]; + if (rMasterPage["style:page-layout-name"]) + { + sLayoutName = OStringToOUString(rMasterPage["style:page-layout-name"]->getStr().cstr(), RTL_TEXTENCODING_UTF8); + } + } + + if (sLayoutName.getLength()) + { + librevenge::RVNGPropertyList &rPageLayout = GetPageLayouts()[sLayoutName]; + + if (GetIsInPageSpan()) + GetGenerator().closePageSpan(); + + GetGenerator().openPageSpan(rPageLayout); + SetIsInPageSpan(true); + } +} + } // namespace exp } // namespace writerperfect diff --git a/writerperfect/source/writer/exp/xmlimp.hxx b/writerperfect/source/writer/exp/xmlimp.hxx index 392eef4956cd..097a96cdcce9 100644 --- a/writerperfect/source/writer/exp/xmlimp.hxx +++ b/writerperfect/source/writer/exp/xmlimp.hxx @@ -83,6 +83,7 @@ class XMLImport : public cppu::WeakImplHelper const css::uno::Reference &mxContext; css::uno::Reference mxUriReferenceFactory; OUString maMediaDir; + bool mbIsInPageSpan; const std::vector &mrPageMetafiles; public: @@ -113,6 +114,10 @@ public: const std::vector &GetPageMetafiles() const; const css::uno::Reference &GetComponentContext() const; + bool GetIsInPageSpan() const { return mbIsInPageSpan; } + void SetIsInPageSpan(bool bSet) { mbIsInPageSpan = bSet; } + void HandlePageSpan(const librevenge::RVNGPropertyList &rPropertyList); + // XDocumentHandler void SAL_CALL startDocument() override; void SAL_CALL endDocument() override; diff --git a/writerperfect/source/writer/exp/xmltbli.cxx b/writerperfect/source/writer/exp/xmltbli.cxx index bec52dab0f22..82468e12a91a 100644 --- a/writerperfect/source/writer/exp/xmltbli.cxx +++ b/writerperfect/source/writer/exp/xmltbli.cxx @@ -205,7 +205,10 @@ void XMLTableContext::startElement(const OUString &/*rName*/, const css::uno::Re const OUString &rAttributeValue = xAttribs->getValueByIndex(i); if (rAttributeName == "table:style-name") + { FillStyles(rAttributeValue, mrImport.GetAutomaticTableStyles(), mrImport.GetTableStyles(), m_aPropertyList); + mrImport.HandlePageSpan(m_aPropertyList); + } else { OString sName = OUStringToOString(rAttributeName, RTL_TEXTENCODING_UTF8); diff --git a/writerperfect/source/writer/exp/xmltext.cxx b/writerperfect/source/writer/exp/xmltext.cxx index 3902e15ae839..a6624b1f2115 100644 --- a/writerperfect/source/writer/exp/xmltext.cxx +++ b/writerperfect/source/writer/exp/xmltext.cxx @@ -13,6 +13,7 @@ #include "xmltbli.hxx" #include "XMLSectionContext.hxx" #include "XMLTextListContext.hxx" +#include "xmlimp.hxx" using namespace com::sun::star; @@ -26,6 +27,12 @@ XMLBodyContentContext::XMLBodyContentContext(XMLImport &rImport) { } +void XMLBodyContentContext::endElement(const OUString &/*rName*/) +{ + if (mrImport.GetIsInPageSpan()) + mrImport.GetGenerator().closePageSpan(); +} + rtl::Reference XMLBodyContentContext::CreateChildContext(const OUString &rName, const css::uno::Reference &/*xAttribs*/) { return CreateTextChildContext(mrImport, rName); diff --git a/writerperfect/source/writer/exp/xmltext.hxx b/writerperfect/source/writer/exp/xmltext.hxx index bce957c4f7e8..1c9a1e131542 100644 --- a/writerperfect/source/writer/exp/xmltext.hxx +++ b/writerperfect/source/writer/exp/xmltext.hxx @@ -24,6 +24,7 @@ public: XMLBodyContentContext(XMLImport &rImport); rtl::Reference CreateChildContext(const OUString &rName, const css::uno::Reference &/*xAttribs*/) override; + void SAL_CALL endElement(const OUString &rName) override; }; /// Context factory for body text, section, table cell, etc. -- cgit v1.2.3