summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLei Zhang <thestig@chromium.org>2017-05-05 17:21:36 -0700
committerChromium commit bot <commit-bot@chromium.org>2017-05-08 14:37:55 +0000
commitd1c9b45aa2dc3a3d6824059e1e8f1f046c59a4f3 (patch)
treed2a693de2ce594caeee7843fcecb98ec5944a594
parent2df760fea931b546d290e797b8c216530c4e13c1 (diff)
downloadpdfium-d1c9b45aa2dc3a3d6824059e1e8f1f046c59a4f3.tar.xz
Add raw PostScript output to pdfium_test on Windows.
Activated by --ps2 and --ps3 for PostScript level 2 and 3, respectively. The raw output is not formatted in a way for most PostScript processing tools to recognize as actually PostScript. Also fix the type of the parameter to FPDF_SetPrintPostscriptLevel() even though it ends up being a no-op. Change-Id: Iaa34fd3dfaedad2b016fefe1227cbed9c974ae2a Reviewed-on: https://pdfium-review.googlesource.com/4996 Commit-Queue: dsinclair <dsinclair@chromium.org> Reviewed-by: dsinclair <dsinclair@chromium.org>
-rw-r--r--public/fpdfview.h3
-rw-r--r--samples/pdfium_test.cc76
2 files changed, 73 insertions, 6 deletions
diff --git a/public/fpdfview.h b/public/fpdfview.h
index 0ed9187f35..13e4f1f5f1 100644
--- a/public/fpdfview.h
+++ b/public/fpdfview.h
@@ -248,8 +248,7 @@ DLLEXPORT void STDCALL FPDF_SetPrintTextWithGDI(FPDF_BOOL use_gdi);
// All other values are invalid.
// Return value:
// True if successful, false if unsucessful (typically invalid input).
-DLLEXPORT FPDF_BOOL STDCALL
-FPDF_SetPrintPostscriptLevel(FPDF_BOOL postscript_level);
+DLLEXPORT FPDF_BOOL STDCALL FPDF_SetPrintPostscriptLevel(int postscript_level);
#endif // defined(_WIN32)
// Function: FPDF_LoadDocument
diff --git a/samples/pdfium_test.cc b/samples/pdfium_test.cc
index d2b3c01196..fa57d65b9e 100644
--- a/samples/pdfium_test.cc
+++ b/samples/pdfium_test.cc
@@ -60,6 +60,8 @@ enum OutputFormat {
#ifdef _WIN32
OUTPUT_BMP,
OUTPUT_EMF,
+ OUTPUT_PS2,
+ OUTPUT_PS3,
#endif
#ifdef PDF_ENABLE_SKIA
OUTPUT_SKP,
@@ -274,14 +276,13 @@ static std::string WriteBmp(const char* pdf_name,
}
void WriteEmf(FPDF_PAGE page, const char* pdf_name, int num) {
- int width = static_cast<int>(FPDF_GetPageWidth(page));
- int height = static_cast<int>(FPDF_GetPageHeight(page));
-
char filename[256];
snprintf(filename, sizeof(filename), "%s.%d.emf", pdf_name, num);
HDC dc = CreateEnhMetaFileA(nullptr, filename, nullptr, nullptr);
+ int width = static_cast<int>(FPDF_GetPageWidth(page));
+ int height = static_cast<int>(FPDF_GetPageHeight(page));
HRGN rgn = CreateRectRgn(0, 0, width, height);
SelectClipRgn(dc, rgn);
DeleteObject(rgn);
@@ -296,7 +297,48 @@ void WriteEmf(FPDF_PAGE page, const char* pdf_name, int num) {
DeleteEnhMetaFile(CloseEnhMetaFile(dc));
}
-#endif
+
+int CALLBACK EnhMetaFileProc(HDC hdc,
+ HANDLETABLE* handle_table,
+ const ENHMETARECORD* record,
+ int objects_count,
+ LPARAM param) {
+ std::vector<const ENHMETARECORD*>& items =
+ *reinterpret_cast<std::vector<const ENHMETARECORD*>*>(param);
+ items.push_back(record);
+ return 1;
+}
+
+void WritePS(FPDF_PAGE page, const char* pdf_name, int num) {
+ char filename[256];
+ snprintf(filename, sizeof(filename), "%s.%d.ps", pdf_name, num);
+ FILE* fp = fopen(filename, "wb");
+ if (!fp)
+ return;
+
+ HDC dc = CreateEnhMetaFileA(nullptr, nullptr, nullptr, nullptr);
+
+ int width = static_cast<int>(FPDF_GetPageWidth(page));
+ int height = static_cast<int>(FPDF_GetPageHeight(page));
+ FPDF_RenderPage(dc, page, 0, 0, width, height, 0,
+ FPDF_ANNOT | FPDF_PRINTING | FPDF_NO_CATCH);
+
+ HENHMETAFILE emf = CloseEnhMetaFile(dc);
+ std::vector<const ENHMETARECORD*> items;
+ EnumEnhMetaFile(nullptr, emf, &EnhMetaFileProc, &items, nullptr);
+ for (const ENHMETARECORD* record : items) {
+ if (record->iType != EMR_GDICOMMENT)
+ continue;
+
+ const auto* comment = reinterpret_cast<const EMRGDICOMMENT*>(record);
+ const char* data = reinterpret_cast<const char*>(comment->Data);
+ uint16_t size = *reinterpret_cast<const uint16_t*>(data);
+ fwrite(data + sizeof(uint16_t), size, 1, fp);
+ }
+ fclose(fp);
+ DeleteEnhMetaFile(emf);
+}
+#endif // _WIN32
#ifdef PDF_ENABLE_SKIA
static std::string WriteSkp(const char* pdf_name,
@@ -474,6 +516,18 @@ bool ParseCommandLine(const std::vector<std::string>& args,
return false;
}
options->output_format = OUTPUT_EMF;
+ } else if (cur_arg == "--ps2") {
+ if (options->output_format != OUTPUT_NONE) {
+ fprintf(stderr, "Duplicate or conflicting --ps2 argument\n");
+ return false;
+ }
+ options->output_format = OUTPUT_PS2;
+ } else if (cur_arg == "--ps3") {
+ if (options->output_format != OUTPUT_NONE) {
+ fprintf(stderr, "Duplicate or conflicting --ps3 argument\n");
+ return false;
+ }
+ options->output_format = OUTPUT_PS3;
} else if (cur_arg == "--bmp") {
if (options->output_format != OUTPUT_NONE) {
fprintf(stderr, "Duplicate or conflicting --bmp argument\n");
@@ -736,6 +790,11 @@ bool RenderPage(const std::string& name,
case OUTPUT_EMF:
WriteEmf(page.get(), name.c_str(), page_index);
break;
+
+ case OUTPUT_PS2:
+ case OUTPUT_PS3:
+ WritePS(page.get(), name.c_str(), page_index);
+ break;
#endif
case OUTPUT_TEXT:
WriteText(page.get(), name.c_str(), page_index);
@@ -898,6 +957,13 @@ void RenderPdf(const std::string& name,
FORM_DoDocumentJSAction(form.get());
FORM_DoDocumentOpenAction(form.get());
+#if _WIN32
+ if (options.output_format == OUTPUT_PS2)
+ FPDF_SetPrintPostscriptLevel(2);
+ else if (options.output_format == OUTPUT_PS3)
+ FPDF_SetPrintPostscriptLevel(3);
+#endif
+
int page_count = FPDF_GetPageCount(doc.get());
int rendered_pages = 0;
int bad_pages = 0;
@@ -966,6 +1032,8 @@ static const char kUsageString[] =
#ifdef _WIN32
" --bmp - write page images <pdf-name>.<page-number>.bmp\n"
" --emf - write page meta files <pdf-name>.<page-number>.emf\n"
+ " --ps2 - write page raw PostScript (Lvl 2) <pdf-name>.<page-number>.ps\n"
+ " --ps3 - write page raw PostScript (Lvl 3) <pdf-name>.<page-number>.ps\n"
#endif // _WIN32
" --txt - write page text in UTF32-LE <pdf-name>.<page-number>.txt\n"
" --png - write page images <pdf-name>.<page-number>.png\n"