summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMiklos Vajna <vmiklos@collabora.co.uk>2018-05-24 17:29:13 +0200
committerMiklos Vajna <vmiklos@collabora.co.uk>2018-05-25 08:45:24 +0200
commit89dc667cebfec5315f0c0361e49d759e88458689 (patch)
treeaffbfc03e045e00bc983b7d4074d9051078876c7
parent6b1b8ef51b752f9711d6581283d6c515d3c50d9b (diff)
tdf#113143 PDF export: fix mis-scaled JPGs on Impress note pages
This is really similar to commit 4c2172a3e973bc6351107a3a1b554c77b40b75dd (tdf#106702 PDF export: fix missing images from Writer headers/footers, 2018-05-22) just this one is about the size of the output rectangle for JPG content, while the previous problem was about the position of them. Also extract PdfExportTest::exportAndParse() from the last two tests to avoid duplication. Change-Id: I9812924d505e9fdaca2a95b4990e7aaa5e44fd7f Reviewed-on: https://gerrit.libreoffice.org/54773 Tested-by: Jenkins <ci@libreoffice.org> Reviewed-by: Miklos Vajna <vmiklos@collabora.co.uk>
-rw-r--r--vcl/qa/cppunit/pdfexport/data/tdf113143.odpbin0 -> 100637 bytes
-rw-r--r--vcl/qa/cppunit/pdfexport/pdfexport.cxx173
-rw-r--r--vcl/source/gdi/pdfextoutdevdata.cxx6
3 files changed, 114 insertions, 65 deletions
diff --git a/vcl/qa/cppunit/pdfexport/data/tdf113143.odp b/vcl/qa/cppunit/pdfexport/data/tdf113143.odp
new file mode 100644
index 000000000000..5f8a1b10e2e5
--- /dev/null
+++ b/vcl/qa/cppunit/pdfexport/data/tdf113143.odp
Binary files differ
diff --git a/vcl/qa/cppunit/pdfexport/pdfexport.cxx b/vcl/qa/cppunit/pdfexport/pdfexport.cxx
index 28803f0fd1b2..849e87b90f4a 100644
--- a/vcl/qa/cppunit/pdfexport/pdfexport.cxx
+++ b/vcl/qa/cppunit/pdfexport/pdfexport.cxx
@@ -39,8 +39,13 @@ class PdfExportTest : public test::BootstrapFixture, public unotest::MacrosTest
uno::Reference<lang::XComponent> mxComponent;
FPDF_PAGE mpPdfPage = nullptr;
FPDF_DOCUMENT mpPdfDocument = nullptr;
+ utl::TempFile maTempFile;
+ SvMemoryStream maMemory;
+ // Export the document as PDF, then parse it with PDFium.
+ void exportAndParse(const OUString& rURL, const utl::MediaDescriptor& rDescriptor);
public:
+ PdfExportTest();
virtual void setUp() override;
virtual void tearDown() override;
void load(const OUString& rFile, vcl::filter::PDFDocument& rDocument);
@@ -82,6 +87,7 @@ public:
void testTdf109143();
void testTdf105954();
void testTdf106702();
+ void testTdf113143();
CPPUNIT_TEST_SUITE(PdfExportTest);
CPPUNIT_TEST(testTdf106059);
@@ -110,9 +116,32 @@ public:
CPPUNIT_TEST(testTdf109143);
CPPUNIT_TEST(testTdf105954);
CPPUNIT_TEST(testTdf106702);
+ CPPUNIT_TEST(testTdf113143);
CPPUNIT_TEST_SUITE_END();
};
+PdfExportTest::PdfExportTest()
+{
+ maTempFile.EnableKillingFile();
+}
+
+void PdfExportTest::exportAndParse(const OUString& rURL, const utl::MediaDescriptor& rDescriptor)
+{
+ // Import the bugdoc and export as PDF.
+ mxComponent = loadFromDesktop(rURL);
+ CPPUNIT_ASSERT(mxComponent.is());
+
+ uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
+ xStorable->storeToURL(maTempFile.GetURL(), rDescriptor.getAsConstPropertyValueList());
+
+ // Parse the export result with pdfium.
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
+ maMemory.WriteStream(aFile);
+ mpPdfDocument
+ = FPDF_LoadMemDocument(maMemory.GetData(), maMemory.GetSize(), /*password=*/nullptr);
+ CPPUNIT_ASSERT(mpPdfDocument);
+}
+
void PdfExportTest::setUp()
{
test::BootstrapFixture::setUp();
@@ -150,14 +179,12 @@ void PdfExportTest::load(const OUString& rFile, vcl::filter::PDFDocument& rDocum
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(rDocument.Read(aStream));
}
@@ -169,8 +196,6 @@ void PdfExportTest::testTdf106059()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
// Explicitly enable the usage of the reference XObject markup.
@@ -178,11 +203,11 @@ void PdfExportTest::testTdf106059()
{"UseReferenceXObject", uno::Any(true) }
}));
aMediaDescriptor["FilterData"] <<= aFilterData;
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
vcl::filter::PDFDocument aDocument;
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(aDocument.Read(aStream));
// Assert that the XObject in the page resources dictionary is a reference XObject.
@@ -249,14 +274,12 @@ void PdfExportTest::testTdf105461()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
@@ -298,19 +321,17 @@ void PdfExportTest::testTdf107868()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
uno::Reference<view::XPrintable> xPrintable(mxComponent, uno::UNO_QUERY);
CPPUNIT_ASSERT(xPrintable.is());
uno::Sequence<beans::PropertyValue> aOptions(comphelper::InitPropertySequence(
{
- {"FileName", uno::makeAny(aTempFile.GetURL())},
+ {"FileName", uno::makeAny(maTempFile.GetURL())},
{"Wait", uno::makeAny(true)}
}));
xPrintable->print(aOptions);
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
@@ -385,15 +406,13 @@ void PdfExportTest::testTdf106206()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
vcl::filter::PDFDocument aDocument;
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(aDocument.Read(aStream));
// The document has one page.
@@ -436,15 +455,13 @@ void PdfExportTest::testTdf109143()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
vcl::filter::PDFDocument aDocument;
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(aDocument.Read(aStream));
// The document has one page.
@@ -476,15 +493,13 @@ void PdfExportTest::testTdf106972()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
vcl::filter::PDFDocument aDocument;
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(aDocument.Read(aStream));
// Get access to the only form object on the only page.
@@ -522,15 +537,13 @@ void PdfExportTest::testTdf106972Pdf17()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result.
vcl::filter::PDFDocument aDocument;
- SvFileStream aStream(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aStream(maTempFile.GetURL(), StreamMode::READ);
CPPUNIT_ASSERT(aDocument.Read(aStream));
// Get access to the only image on the only page.
@@ -743,14 +756,12 @@ void PdfExportTest::testTdf108963()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
@@ -941,14 +952,12 @@ void PdfExportTest::testTdf115117_1a()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
@@ -986,14 +995,12 @@ void PdfExportTest::testTdf115117_2a()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
@@ -1295,18 +1302,16 @@ void PdfExportTest::testTdf105954()
CPPUNIT_ASSERT(mxComponent.is());
uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
uno::Sequence<beans::PropertyValue> aFilterData(comphelper::InitPropertySequence(
{ { "ReduceImageResolution", uno::Any(true) },
{ "MaxImageResolution", uno::Any(static_cast<sal_Int32>(300)) } }));
aMediaDescriptor["FilterData"] <<= aFilterData;
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
+ xStorable->storeToURL(maTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
// Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
+ SvFileStream aFile(maTempFile.GetURL(), StreamMode::READ);
SvMemoryStream aMemory;
aMemory.WriteStream(aFile);
mpPdfDocument
@@ -1335,23 +1340,9 @@ void PdfExportTest::testTdf106702()
{
// Import the bugdoc and export as PDF.
OUString aURL = m_directories.getURLFromSrc(DATA_DIRECTORY) + "tdf106702.odt";
- mxComponent = loadFromDesktop(aURL);
- CPPUNIT_ASSERT(mxComponent.is());
-
- uno::Reference<frame::XStorable> xStorable(mxComponent, uno::UNO_QUERY);
- utl::TempFile aTempFile;
- aTempFile.EnableKillingFile();
utl::MediaDescriptor aMediaDescriptor;
aMediaDescriptor["FilterName"] <<= OUString("writer_pdf_Export");
- xStorable->storeToURL(aTempFile.GetURL(), aMediaDescriptor.getAsConstPropertyValueList());
-
- // Parse the export result with pdfium.
- SvFileStream aFile(aTempFile.GetURL(), StreamMode::READ);
- SvMemoryStream aMemory;
- aMemory.WriteStream(aFile);
- mpPdfDocument
- = FPDF_LoadMemDocument(aMemory.GetData(), aMemory.GetSize(), /*password=*/nullptr);
- CPPUNIT_ASSERT(mpPdfDocument);
+ exportAndParse(aURL, aMediaDescriptor);
// The document has two pages.
CPPUNIT_ASSERT_EQUAL(2, FPDF_GetPageCount(mpPdfDocument));
@@ -1396,6 +1387,62 @@ void PdfExportTest::testTdf106702()
CPPUNIT_ASSERT_EQUAL(nExpected, nActual);
}
+void PdfExportTest::testTdf113143()
+{
+ OUString aURL = m_directories.getURLFromSrc(DATA_DIRECTORY) + "tdf113143.odp";
+ utl::MediaDescriptor aMediaDescriptor;
+ aMediaDescriptor["FilterName"] <<= OUString("impress_pdf_Export");
+ uno::Sequence<beans::PropertyValue> aFilterData(comphelper::InitPropertySequence({
+ { "ExportNotesPages", uno::Any(true) },
+ // ReduceImageResolution is on by default and that hides the bug we
+ // want to test.
+ { "ReduceImageResolution", uno::Any(false) },
+ }));
+ aMediaDescriptor["FilterData"] <<= aFilterData;
+ exportAndParse(aURL, aMediaDescriptor);
+
+ // The document has two pages.
+ CPPUNIT_ASSERT_EQUAL(2, FPDF_GetPageCount(mpPdfDocument));
+
+ // First has the original (larger) image.
+ mpPdfPage = FPDF_LoadPage(mpPdfDocument, /*page_index=*/0);
+ CPPUNIT_ASSERT(mpPdfPage);
+ int nLarger = 0;
+ int nPageObjectCount = FPDFPage_CountObjects(mpPdfPage);
+ for (int i = 0; i < nPageObjectCount; ++i)
+ {
+ FPDF_PAGEOBJECT pPageObject = FPDFPage_GetObject(mpPdfPage, i);
+ if (FPDFPageObj_GetType(pPageObject) != FPDF_PAGEOBJ_IMAGE)
+ continue;
+
+ float fLeft = 0, fBottom = 0, fRight = 0, fTop = 0;
+ FPDFPageObj_GetBounds(pPageObject, &fLeft, &fBottom, &fRight, &fTop);
+ nLarger = fRight - fLeft;
+ break;
+ }
+
+ // Second page has the scaled (smaller) image.
+ FPDF_ClosePage(mpPdfPage);
+ mpPdfPage = FPDF_LoadPage(mpPdfDocument, /*page_index=*/1);
+ CPPUNIT_ASSERT(mpPdfPage);
+ int nSmaller = 0;
+ nPageObjectCount = FPDFPage_CountObjects(mpPdfPage);
+ for (int i = 0; i < nPageObjectCount; ++i)
+ {
+ FPDF_PAGEOBJECT pPageObject = FPDFPage_GetObject(mpPdfPage, i);
+ if (FPDFPageObj_GetType(pPageObject) != FPDF_PAGEOBJ_IMAGE)
+ continue;
+
+ float fLeft = 0, fBottom = 0, fRight = 0, fTop = 0;
+ FPDFPageObj_GetBounds(pPageObject, &fLeft, &fBottom, &fRight, &fTop);
+ nSmaller = fRight - fLeft;
+ break;
+ }
+
+ // This failed, both were 319, now nSmaller is 169.
+ CPPUNIT_ASSERT_LESS(nLarger, nSmaller);
+}
+
CPPUNIT_TEST_SUITE_REGISTRATION(PdfExportTest);
}
diff --git a/vcl/source/gdi/pdfextoutdevdata.cxx b/vcl/source/gdi/pdfextoutdevdata.cxx
index 05bb37a0c6c3..d36ab2844f17 100644
--- a/vcl/source/gdi/pdfextoutdevdata.cxx
+++ b/vcl/source/gdi/pdfextoutdevdata.cxx
@@ -466,8 +466,9 @@ bool PageSyncData::PlaySyncPageAct( PDFWriter& rWriter, sal_uInt32& rCurGDIMtfAc
// Look up the output rectangle from the previous
// bitmap scale action if possible. This has the
- // correct position for images repeated in
- // Writer headers/footers for non-first pages.
+ // correct position and size for images with a
+ // custom translation (Writer header) or scaling
+ // (Impress notes page).
if (rCurGDIMtfAction > 0)
{
const MetaAction* pAction = rMtf.GetAction(rCurGDIMtfAction - 1);
@@ -476,6 +477,7 @@ bool PageSyncData::PlaySyncPageAct( PDFWriter& rWriter, sal_uInt32& rCurGDIMtfAc
const MetaBmpScaleAction* pA
= static_cast<const MetaBmpScaleAction*>(pAction);
aOutputRect.SetPos(pA->GetPoint());
+ aOutputRect.SetSize(pA->GetSize());
}
}