From 6ab19d364c8238bd84d8b1474d0af7ed001e3217 Mon Sep 17 00:00:00 2001 From: Miklos Vajna Date: Thu, 9 Feb 2017 13:47:33 +0100 Subject: xmlsecurity: use pdfium to generate a preview in pdfverify This is just test code to check if the bundled pdfium is usable. Change-Id: I1f1d808796fe77924518cd004d99affe70279e88 Reviewed-on: https://gerrit.libreoffice.org/34081 Reviewed-by: Miklos Vajna Tested-by: Jenkins (cherry picked from commit ea92b7cc2e4a948e101f4915d50c2469968e95b1) --- xmlsecurity/workben/pdfverify.cxx | 89 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 89 insertions(+) (limited to 'xmlsecurity/workben') diff --git a/xmlsecurity/workben/pdfverify.cxx b/xmlsecurity/workben/pdfverify.cxx index 92504fcba42d..dceb863ca77b 100644 --- a/xmlsecurity/workben/pdfverify.cxx +++ b/xmlsecurity/workben/pdfverify.cxx @@ -9,6 +9,15 @@ #include +#ifdef WNT +#include +#endif +#include +#include +#ifdef WNT +#include +#endif + #include #include #include @@ -17,6 +26,10 @@ #include #include #include +#include +#include +#include +#include #include @@ -24,6 +37,73 @@ using namespace com::sun::star; namespace { +/// Convert to inch, then assume 96 DPI. +double pointToPixel(double fPoint) +{ + return fPoint / 72 * 96; +} + +/// Does PDF to PNG conversion using pdfium. +void generatePreview(const OString& rPdfPath, const OString& rPngPath) +{ + FPDF_LIBRARY_CONFIG aConfig; + aConfig.version = 2; + aConfig.m_pUserFontPaths = nullptr; + aConfig.m_pIsolate = nullptr; + aConfig.m_v8EmbedderSlot = 0; + FPDF_InitLibraryWithConfig(&aConfig); + + // Read input into a buffer. + OUString aInURL; + osl::FileBase::getFileURLFromSystemPath(OUString::fromUtf8(rPdfPath), aInURL); + SvFileStream aInStream(aInURL, StreamMode::READ); + SvMemoryStream aInBuffer; + aInBuffer.WriteStream(aInStream); + + // Load the buffer using pdfium. + FPDF_DOCUMENT pPdfDocument = FPDF_LoadMemDocument(aInBuffer.GetData(), aInBuffer.GetSize(), /*password=*/nullptr); + if (!pPdfDocument) + return; + + // Render the first page. + FPDF_PAGE pPdfPage = FPDF_LoadPage(pPdfDocument, /*page_index=*/0); + if (!pPdfPage) + return; + + // Returned unit is points, convert that to pixel. + int nPageWidth = pointToPixel(FPDF_GetPageWidth(pPdfPage)); + int nPageHeight = pointToPixel(FPDF_GetPageHeight(pPdfPage)); + FPDF_BITMAP pPdfBitmap = FPDFBitmap_Create(nPageWidth, nPageHeight, /*alpha=*/1); + if (!pPdfBitmap) + return; + + FPDF_DWORD nColor = FPDFPage_HasTransparency(pPdfPage) ? 0x00000000 : 0xFFFFFFFF; + FPDFBitmap_FillRect(pPdfBitmap, 0, 0, nPageWidth, nPageHeight, nColor); + FPDF_RenderPageBitmap(pPdfBitmap, pPdfPage, /*start_x=*/0, /*start_y=*/0, nPageWidth, nPageHeight, /*rotate=*/0, /*flags=*/0); + + // Save the buffer as a PNG file. + Bitmap aBitmap(Size(nPageWidth, nPageHeight), 32); + { + Bitmap::ScopedWriteAccess pWriteAccess(aBitmap); + const void* pPdfBuffer = FPDFBitmap_GetBuffer(pPdfBitmap); + std::memcpy(pWriteAccess->GetBuffer(), pPdfBuffer, nPageWidth * nPageHeight * 4); + } + BitmapEx aBitmapEx(aBitmap); +#ifdef WNT + aBitmapEx.Mirror(BmpMirrorFlags::Vertical); +#endif + vcl::PNGWriter aWriter(aBitmapEx); + OUString aOutURL; + osl::FileBase::getFileURLFromSystemPath(OUString::fromUtf8(rPngPath), aOutURL); + SvFileStream aOutStream(aOutURL, StreamMode::WRITE); + aWriter.Write(aOutStream); + + FPDFBitmap_Destroy(pPdfBitmap); + FPDF_ClosePage(pPdfPage); + FPDF_CloseDocument(pPdfDocument); + FPDF_DestroyLibrary(); +} + int pdfVerify(int nArgc, char** pArgv) { if (nArgc < 2) @@ -46,6 +126,15 @@ int pdfVerify(int nArgc, char** pArgv) uno::Reference xMultiComponentFactory = xComponentContext->getServiceManager(); uno::Reference xMultiServiceFactory(xMultiComponentFactory, uno::UNO_QUERY); comphelper::setProcessServiceFactory(xMultiServiceFactory); + + if (nArgc > 3 && OString(pArgv[3]) == "-p") + { + InitVCL(); + generatePreview(pArgv[1], pArgv[2]); + DeInitVCL(); + return 0; + } + uno::Reference xSEInitializer; try { -- cgit