1//========================================================================
2//
3// image-embedding.cc
4// A test util to check ImageEmbeddingUtils::embed().
5//
6// This file is licensed under the GPLv2 or later
7//
8// Copyright (C) 2021 Georgiy Sgibnev <georgiy@sgibnev.com>. Work sponsored by lab50.net.
9// Copyright (C) 2022 by Albert Astals Cid <aacid@kde.org>
10//
11//========================================================================
12
13#include <config.h>
14#include <cstdio>
15#include <string>
16
17#include "utils/parseargs.h"
18#include "goo/GooString.h"
19#include "Object.h"
20#include "Dict.h"
21#include "PDFDoc.h"
22#include "PDFDocFactory.h"
23#include "ImageEmbeddingUtils.h"
24
25static int depth = 0;
26static GooString colorSpace;
27static GooString filter;
28static bool smask = false;
29static bool fail = false;
30static bool printHelp = false;
31
32static const ArgDesc argDesc[] = { { .arg: "-depth", .kind: argInt, .val: &depth, .size: 0, .usage: "XObject's property 'BitsPerComponent'" },
33 { .arg: "-colorspace", .kind: argGooString, .val: &colorSpace, .size: 0, .usage: "XObject's property 'ColorSpace'" },
34 { .arg: "-filter", .kind: argGooString, .val: &filter, .size: 0, .usage: "XObject's property 'Filter'" },
35 { .arg: "-smask", .kind: argFlag, .val: &smask, .size: 0, .usage: "SMask should exist" },
36 { .arg: "-fail", .kind: argFlag, .val: &fail, .size: 0, .usage: "the image embedding API is expected to fail" },
37 { .arg: "-h", .kind: argFlag, .val: &printHelp, .size: 0, .usage: "print usage information" },
38 { .arg: "-help", .kind: argFlag, .val: &printHelp, .size: 0, .usage: "print usage information" },
39 { .arg: "--help", .kind: argFlag, .val: &printHelp, .size: 0, .usage: "print usage information" },
40 { .arg: "-?", .kind: argFlag, .val: &printHelp, .size: 0, .usage: "print usage information" },
41 {} };
42
43int main(int argc, char *argv[])
44{
45 // Parse args.
46 const bool ok = parseArgs(args: argDesc, argc: &argc, argv);
47 if (!ok || (argc != 3) || printHelp) {
48 printUsage(program: argv[0], otherArgs: "PDF-FILE IMAGE-FILE", args: argDesc);
49 return (printHelp) ? 0 : 1;
50 }
51 const GooString docPath(argv[1]);
52 const GooString imagePath(argv[2]);
53
54 auto doc = std::unique_ptr<PDFDoc>(PDFDocFactory().createPDFDoc(uri: docPath));
55 if (!doc->isOk()) {
56 fprintf(stderr, format: "Error opening input PDF file.\n");
57 return 1;
58 }
59
60 // Embed an image.
61 Ref baseImageRef = ImageEmbeddingUtils::embed(xref: doc->getXRef(), imagePath: imagePath.toStr());
62 if (baseImageRef == Ref::INVALID()) {
63 if (fail) {
64 return 0;
65 } else {
66 fprintf(stderr, format: "ImageEmbeddingUtils::embed() failed.\n");
67 return 1;
68 }
69 }
70
71 // Save the updated PDF document.
72 // const GooString outputPathSuffix(".pdf");
73 // const GooString outputPath = GooString(&imagePath, &outputPathSuffix);
74 // doc->saveAs(&outputPath, writeForceRewrite);
75
76 // Check the base image.
77 Object baseImageObj = Object(baseImageRef).fetch(xref: doc->getXRef());
78 Dict *baseImageDict = baseImageObj.streamGetDict();
79 if (std::string("XObject") != baseImageDict->lookup(key: "Type").getName()) {
80 fprintf(stderr, format: "A problem with Type.\n");
81 return 1;
82 }
83 if (std::string("Image") != baseImageDict->lookup(key: "Subtype").getName()) {
84 fprintf(stderr, format: "A problem with Subtype.\n");
85 return 1;
86 }
87 if (depth > 0) {
88 if (baseImageDict->lookup(key: "BitsPerComponent").getInt() != depth) {
89 fprintf(stderr, format: "A problem with BitsPerComponent.\n");
90 return 1;
91 }
92 }
93 if (!colorSpace.toStr().empty()) {
94 if (colorSpace.cmp(sA: baseImageDict->lookup(key: "ColorSpace").getName()) != 0) {
95 fprintf(stderr, format: "A problem with ColorSpace.\n");
96 return 1;
97 }
98 }
99 if (!filter.toStr().empty()) {
100 if (filter.cmp(sA: baseImageDict->lookup(key: "Filter").getName()) != 0) {
101 fprintf(stderr, format: "A problem with Filter.\n");
102 return 1;
103 }
104 }
105 if (smask) {
106 Object maskObj = baseImageDict->lookup(key: "SMask");
107 if (!maskObj.isStream()) {
108 fprintf(stderr, format: "A problem with SMask.\n");
109 return 1;
110 }
111 }
112 return 0;
113}
114

source code of poppler/test/image-embedding.cc