diff options
author | Michael Stahl <michael.stahl@allotropia.de> | 2021-09-07 13:51:20 +0200 |
---|---|---|
committer | Michael Stahl <michael.stahl@allotropia.de> | 2021-09-07 19:02:32 +0200 |
commit | 992f878e8c3424f7ce96a78ccf3a316b29ffd9ec (patch) | |
tree | 94c4d0bddf6ea26e7c37f2078b74a2feac717f5d /vcl | |
parent | 7228a2dbfa11cd846678aaacd248c68adcda5f34 (diff) |
tdf#142129 vcl: add unit test
Reportedly bug was fixed by commit
5fc6a601d7a1978db291fd0f7dcec638a7c25651
Change-Id: Iee32cacff0c939bdf498e9dc8102eb2d22a5a1c9
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/121776
Tested-by: Michael Stahl <michael.stahl@allotropia.de>
Reviewed-by: Michael Stahl <michael.stahl@allotropia.de>
Diffstat (limited to 'vcl')
-rw-r--r-- | vcl/qa/cppunit/pdfexport/data/WG7100-Preface.odt | bin | 0 -> 25317 bytes | |||
-rw-r--r-- | vcl/qa/cppunit/pdfexport/data/master.odm | bin | 0 -> 22304 bytes | |||
-rw-r--r-- | vcl/qa/cppunit/pdfexport/pdfexport.cxx | 87 | ||||
-rw-r--r-- | vcl/source/filter/ipdf/pdfdocument.cxx | 17 |
4 files changed, 104 insertions, 0 deletions
diff --git a/vcl/qa/cppunit/pdfexport/data/WG7100-Preface.odt b/vcl/qa/cppunit/pdfexport/data/WG7100-Preface.odt Binary files differnew file mode 100644 index 000000000000..05e2bb18408a --- /dev/null +++ b/vcl/qa/cppunit/pdfexport/data/WG7100-Preface.odt diff --git a/vcl/qa/cppunit/pdfexport/data/master.odm b/vcl/qa/cppunit/pdfexport/data/master.odm Binary files differnew file mode 100644 index 000000000000..74016352b762 --- /dev/null +++ b/vcl/qa/cppunit/pdfexport/data/master.odm diff --git a/vcl/qa/cppunit/pdfexport/pdfexport.cxx b/vcl/qa/cppunit/pdfexport/pdfexport.cxx index bb203602714d..0da9bedd33ef 100644 --- a/vcl/qa/cppunit/pdfexport/pdfexport.cxx +++ b/vcl/qa/cppunit/pdfexport/pdfexport.cxx @@ -2791,6 +2791,93 @@ CPPUNIT_TEST_FIXTURE(PdfExportTest, testPdfUaMetadata) CPPUNIT_ASSERT_EQUAL(OString("1"), aPdfUaPart); } +CPPUNIT_TEST_FIXTURE(PdfExportTest, testTdf142129) +{ + OUString aURL = m_directories.getURLFromSrc(DATA_DIRECTORY) + "master.odm"; + mxComponent = loadFromDesktop(aURL); + + // update linked section + dispatchCommand(mxComponent, ".uno:UpdateAllLinks", {}); + + uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY); + utl::MediaDescriptor aMediaDescriptor; + aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export"); + + // Enable Outlines export + uno::Sequence<beans::PropertyValue> aFilterData( + comphelper::InitPropertySequence({ { "ExportBookmarks", uno::Any(true) } })); + aMediaDescriptor["FilterData"] <<= aFilterData; + xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList()); + + // Parse the export result. + vcl::filter::PDFDocument aDocument; + SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ); + CPPUNIT_ASSERT(aDocument.Read(aStream)); + + auto* pCatalog = aDocument.GetCatalog(); + CPPUNIT_ASSERT(pCatalog); + auto* pCatalogDictionary = pCatalog->GetDictionary(); + CPPUNIT_ASSERT(pCatalogDictionary); + auto* pOutlinesObject = pCatalogDictionary->LookupObject("Outlines"); + CPPUNIT_ASSERT(pOutlinesObject); + auto* pOutlinesDictionary = pOutlinesObject->GetDictionary(); +#if 0 + // Type isn't actually written currently + auto* pType + = dynamic_cast<vcl::filter::PDFNameElement*>(pOutlinesDictionary->LookupElement("Type")); + CPPUNIT_ASSERT(pType); + CPPUNIT_ASSERT_EQUAL(OString("Outlines"), pType->GetValue()); +#endif + + auto* pFirst = dynamic_cast<vcl::filter::PDFReferenceElement*>( + pOutlinesDictionary->LookupElement("First")); + CPPUNIT_ASSERT(pFirst); + auto* pFirstD = pFirst->LookupObject()->GetDictionary(); + CPPUNIT_ASSERT(pFirstD); + //CPPUNIT_ASSERT_EQUAL(OString("Outlines"), dynamic_cast<vcl::filter::PDFNameElement*>(pFirstD->LookupElement("Type"))->GetValue()); + CPPUNIT_ASSERT_EQUAL(OUString(u"Preface"), ::vcl::filter::PDFDocument::DecodeHexStringUTF16BE( + *dynamic_cast<vcl::filter::PDFHexStringElement*>( + pFirstD->LookupElement("Title")))); + + auto* pFirst1 + = dynamic_cast<vcl::filter::PDFReferenceElement*>(pFirstD->LookupElement("First")); + CPPUNIT_ASSERT(pFirst1); + auto* pFirst1D = pFirst1->LookupObject()->GetDictionary(); + CPPUNIT_ASSERT(pFirst1D); + // here is a hidden section with headings "Copyright" etc.; check that + // there are no outline entries for it + //CPPUNIT_ASSERT_EQUAL(OString("Outlines"), dynamic_cast<vcl::filter::PDFNameElement*>(pFirst1D->LookupElement("Type"))->GetValue()); + CPPUNIT_ASSERT_EQUAL( + OUString(u"Who is this book for?"), + ::vcl::filter::PDFDocument::DecodeHexStringUTF16BE( + *dynamic_cast<vcl::filter::PDFHexStringElement*>(pFirst1D->LookupElement("Title")))); + + auto* pFirst2 + = dynamic_cast<vcl::filter::PDFReferenceElement*>(pFirst1D->LookupElement("Next")); + auto* pFirst2D = pFirst2->LookupObject()->GetDictionary(); + CPPUNIT_ASSERT(pFirst2D); + //CPPUNIT_ASSERT_EQUAL(OString("Outlines"), dynamic_cast<vcl::filter::PDFNameElement*>(pFirst2D->LookupElement("Type"))->GetValue()); + CPPUNIT_ASSERT_EQUAL( + OUString(u"What\u2019s in this book?"), + ::vcl::filter::PDFDocument::DecodeHexStringUTF16BE( + *dynamic_cast<vcl::filter::PDFHexStringElement*>(pFirst2D->LookupElement("Title")))); + + auto* pFirst3 + = dynamic_cast<vcl::filter::PDFReferenceElement*>(pFirst2D->LookupElement("Next")); + auto* pFirst3D = pFirst3->LookupObject()->GetDictionary(); + CPPUNIT_ASSERT(pFirst3D); + //CPPUNIT_ASSERT_EQUAL(OString("Outlines"), dynamic_cast<vcl::filter::PDFNameElement*>(pFirst3D->LookupElement("Type"))->GetValue()); + CPPUNIT_ASSERT_EQUAL( + OUString(u"Minimum requirements for using LibreOffice"), + ::vcl::filter::PDFDocument::DecodeHexStringUTF16BE( + *dynamic_cast<vcl::filter::PDFHexStringElement*>(pFirst3D->LookupElement("Title")))); + + CPPUNIT_ASSERT_EQUAL(static_cast<vcl::filter::PDFElement*>(nullptr), + pFirst3D->LookupElement("Next")); + CPPUNIT_ASSERT_EQUAL(static_cast<vcl::filter::PDFElement*>(nullptr), + pFirstD->LookupElement("Next")); +} + CPPUNIT_TEST_FIXTURE(PdfExportTest, testPdfImageRotate180) { // Create an empty document. diff --git a/vcl/source/filter/ipdf/pdfdocument.cxx b/vcl/source/filter/ipdf/pdfdocument.cxx index b8224b159329..7e1a25e54e7b 100644 --- a/vcl/source/filter/ipdf/pdfdocument.cxx +++ b/vcl/source/filter/ipdf/pdfdocument.cxx @@ -2052,6 +2052,23 @@ std::vector<unsigned char> PDFDocument::DecodeHexString(PDFHexStringElement cons return svl::crypto::DecodeHexString(pElement->GetValue()); } +OUString PDFDocument::DecodeHexStringUTF16BE(PDFHexStringElement const& rElement) +{ + std::vector<unsigned char> const encoded(DecodeHexString(&rElement)); + // Text strings can be PDF-DocEncoding or UTF-16BE with mandatory BOM; + // only the latter supported is here + if (encoded.size() < 2 || encoded[0] != 0xFE || encoded[1] != 0xFF || (encoded.size() & 1) != 0) + { + return OUString(); + } + OUStringBuffer buf(static_cast<unsigned int>(encoded.size() - 2)); + for (size_t i = 2; i < encoded.size(); i += 2) + { + buf.append(sal_Unicode((static_cast<sal_uInt16>(encoded[i]) << 8) | encoded[i + 1])); + } + return buf.makeStringAndClear(); +} + PDFCommentElement::PDFCommentElement(PDFDocument& rDoc) : m_rDoc(rDoc) { |