bool load(const char* fileName) { delete _pdfDoc; delete _outputDev; delete _nullOutputDev; for (int i=0; i<_bmpCache.size(); i++) delete _bmpCache[i]; _bmpCache.resize(0); for (int i=0; i<_textCache.size(); i++) delete _textCache[i]; _textCache.resize(0); _pdfDoc= new PDFDoc(new GooString(fileName), NULL, NULL, NULL); if (!_pdfDoc->isOk()) { printf("error loading pdf"); return false; } GBool bitmapTopDown = gTrue; SplashColor white; white[0]=0xff; white[1]=0xff; white[2]=0xff; // _outputDev = new SplashOutputDev_mod(splashModeRGB8, 4, gFalse, white, bitmapTopDown); _outputDev = new SplashOutputDev(splashModeRGB8, 4, gFalse, white, bitmapTopDown); if(!_outputDev) { printf("error loading pdf"); return false; } #ifdef USE_NULLOUTPUTDEV _nullOutputDev=new NullOutputDev(); #endif #ifdef POPPLER_VERSION _outputDev->startDoc(_pdfDoc); #else _outputDev->startDoc(_pdfDoc->getXRef()); #endif _bmpCache.resize(_pdfDoc->getNumPages()); for (int i=0; i<_bmpCache.size(); i++) _bmpCache[i]=NULL; _textCache.resize(_pdfDoc->getNumPages()); for (int i=0; i<_textCache.size(); i++) _textCache[i]=NULL; return true; }
bool PdfPlug::convert(QString fn) { bool firstPg = true; int currentLayer = m_Doc->activeLayer(); int baseLayer = m_Doc->activeLayer(); importedColors.clear(); if(progressDialog) { progressDialog->setOverallProgress(2); progressDialog->setLabel("GI", tr("Generating Items")); qApp->processEvents(); } QFile f(fn); oldDocItemCount = m_Doc->Items->count(); if (progressDialog) { progressDialog->setBusyIndicator("GI"); qApp->processEvents(); } globalParams = new GlobalParams(); if (globalParams) { GooString *fname = new GooString(QFile::encodeName(fn).data()); globalParams->setErrQuiet(gTrue); GBool hasOcg = gFalse; QList<OptionalContentGroup*> ocgGroups; // globalParams->setPrintCommands(gTrue); PDFDoc *pdfDoc = new PDFDoc(fname, 0, 0, 0); if (pdfDoc) { if (pdfDoc->isOk()) { double hDPI = 72.0; double vDPI = 72.0; int firstPage = 1; int lastPage = pdfDoc->getNumPages(); SlaOutputDev *dev = new SlaOutputDev(m_Doc, &Elements, &importedColors, importerFlags); if (dev->isOk()) { OCGs* ocg = pdfDoc->getOptContentConfig(); if (ocg) { hasOcg = ocg->hasOCGs(); if (hasOcg) { QStringList ocgNames; Array *order = ocg->getOrderArray(); if (order) { for (int i = 0; i < order->getLength (); ++i) { Object orderItem; order->get(i, &orderItem); if (orderItem.isDict()) { Object ref; order->getNF(i, &ref); if (ref.isRef()) { OptionalContentGroup *oc = ocg->findOcgByRef(ref.getRef()); QString ocgName = UnicodeParsedString(oc->getName()); if (!ocgNames.contains(ocgName)) { ocgGroups.prepend(oc); ocgNames.append(ocgName); } } ref.free(); } else { GooList *ocgs; int i; ocgs = ocg->getOCGs (); for (i = 0; i < ocgs->getLength (); ++i) { OptionalContentGroup *oc = (OptionalContentGroup *)ocgs->get(i); QString ocgName = UnicodeParsedString(oc->getName()); if (!ocgNames.contains(ocgName)) { ocgGroups.prepend(oc); ocgNames.append(ocgName); } } } } } else { GooList *ocgs; int i; ocgs = ocg->getOCGs (); for (i = 0; i < ocgs->getLength (); ++i) { OptionalContentGroup *oc = (OptionalContentGroup *)ocgs->get(i); QString ocgName = UnicodeParsedString(oc->getName()); if (!ocgNames.contains(ocgName)) { ocgGroups.prepend(oc); ocgNames.append(ocgName); } } } } } GBool useMediaBox = gTrue; GBool crop = gFalse; GBool printing = gFalse; dev->startDoc(pdfDoc, pdfDoc->getXRef(), pdfDoc->getCatalog()); int rotate = pdfDoc->getPageRotate(firstPage); if (importerFlags & LoadSavePlugin::lfCreateDoc) { // POPPLER_VERSION appeared in 0.19.0 first #ifdef POPPLER_VERSION if (hasOcg) { QString actL = m_Doc->activeLayerName(); for (int a = 0; a < ocgGroups.count(); a++) { OptionalContentGroup *oc = ocgGroups[a]; if (actL != UnicodeParsedString(oc->getName())) currentLayer = m_Doc->addLayer(UnicodeParsedString(oc->getName()), false); else currentLayer = m_Doc->layerIDFromName(UnicodeParsedString(oc->getName())); // POPPLER_VERSION appeared in 0.19.0 first #ifdef POPPLER_VERSION if ((oc->getViewState() == OptionalContentGroup::ocUsageOn) || (oc->getViewState() == OptionalContentGroup::ocUsageUnset)) m_Doc->setLayerVisible(currentLayer, true); else m_Doc->setLayerVisible(currentLayer, false); if ((oc->getPrintState() == OptionalContentGroup::ocUsageOn) || (oc->getPrintState() == OptionalContentGroup::ocUsageUnset)) m_Doc->setLayerPrintable(currentLayer, true); else m_Doc->setLayerPrintable(currentLayer, false); #else if (oc->getState() == OptionalContentGroup::On) { m_Doc->setLayerVisible(currentLayer, true); m_Doc->setLayerPrintable(currentLayer, true); } else { m_Doc->setLayerVisible(currentLayer, false); m_Doc->setLayerPrintable(currentLayer, false); } #endif oc->setState(OptionalContentGroup::Off); } dev->layersSetByOCG = true; } #endif Object info; pdfDoc->getDocInfo(&info); if (info.isDict()) { Object obj; GooString *s1; Dict *infoDict = info.getDict(); if (infoDict->lookup((char*)"Title", &obj )->isString()) { s1 = obj.getString(); m_Doc->documentInfo().setTitle(UnicodeParsedString(obj.getString())); obj.free(); } if (infoDict->lookup((char*)"Author", &obj )->isString()) { s1 = obj.getString(); m_Doc->documentInfo().setAuthor(UnicodeParsedString(obj.getString())); obj.free(); } if (infoDict->lookup((char*)"Subject", &obj )->isString()) { s1 = obj.getString(); m_Doc->documentInfo().setSubject(UnicodeParsedString(obj.getString())); obj.free(); } if (infoDict->lookup((char*)"Keywords", &obj )->isString()) { s1 = obj.getString(); m_Doc->documentInfo().setKeywords(UnicodeParsedString(obj.getString())); obj.free(); } } info.free(); for (int pp = 0; pp < lastPage; pp++) { m_Doc->setActiveLayer(baseLayer); if (firstPg) firstPg = false; else m_Doc->addPage(pp); m_Doc->currentPage()->setInitialHeight(pdfDoc->getPageMediaHeight(pp + 1)); m_Doc->currentPage()->setInitialWidth(pdfDoc->getPageMediaWidth(pp + 1)); m_Doc->currentPage()->setHeight(pdfDoc->getPageMediaHeight(pp + 1)); m_Doc->currentPage()->setWidth(pdfDoc->getPageMediaWidth(pp + 1)); m_Doc->currentPage()->MPageNam = CommonStrings::trMasterPageNormal; m_Doc->currentPage()->m_pageSize = "Custom"; m_Doc->setPageSize("Custom"); m_Doc->reformPages(true); if (hasOcg) { for (int a = 0; a < ocgGroups.count(); a++) { OptionalContentGroup *oc = ocgGroups[a]; // m_Doc->setActiveLayer(UnicodeParsedString(oc->getName())); // currentLayer = m_Doc->activeLayer(); oc->setState(OptionalContentGroup::On); // pdfDoc->displayPage(dev, pp + 1, hDPI, vDPI, rotate, useMediaBox, crop, printing); // oc->setState(OptionalContentGroup::Off); } pdfDoc->displayPage(dev, pp + 1, hDPI, vDPI, rotate, useMediaBox, crop, printing); } else pdfDoc->displayPage(dev, pp + 1, hDPI, vDPI, rotate, useMediaBox, crop, printing); } } else { if (hasOcg) { for (int a = 0; a < ocgGroups.count(); a++) { ocgGroups[a]->setState(OptionalContentGroup::On); } } pdfDoc->displayPage(dev, firstPage, hDPI, vDPI, rotate, useMediaBox, crop, printing); } } delete dev; } } delete pdfDoc; } delete globalParams; globalParams = 0; // qDebug() << "converting finished"; // qDebug() << "Imported" << Elements.count() << "Elements"; if (Elements.count() == 0) { if (importedColors.count() != 0) { for (int cd = 0; cd < importedColors.count(); cd++) { m_Doc->PageColors.remove(importedColors[cd]); } } } if (progressDialog) progressDialog->close(); return true; }
int main(int argc, char *argv[]) { // parse args bool ok = parseArgs(argDesc, &argc, argv); if (!ok || argc < 2 || argc > 3 || printHelp) { fprintf(stderr, "pdftoipe version %s\n", PDFTOIPE_VERSION); printUsage("pdftoipe", "<PDF-file> [<XML-file>]", argDesc); return 1; } GooString *fileName = new GooString(argv[1]); globalParams = new GlobalParams(); if (quiet) globalParams->setErrQuiet(quiet); GooString *ownerPW, *userPW; if (ownerPassword[0]) { ownerPW = new GooString(ownerPassword); } else { ownerPW = 0; } if (userPassword[0]) { userPW = new GooString(userPassword); } else { userPW = 0; } // open PDF file PDFDoc *doc = new PDFDoc(fileName, ownerPW, userPW); delete userPW; delete ownerPW; if (!doc->isOk()) return 1; // construct XML file name std::string xmlFileName; if (argc == 3) { xmlFileName = argv[2]; } else { const char *p = fileName->c_str() + fileName->getLength() - 4; if (!strcmp(p, ".pdf") || !strcmp(p, ".PDF")) { xmlFileName = std::string(fileName->c_str(), fileName->getLength() - 4); } else { xmlFileName = fileName->c_str(); } xmlFileName += ".ipe"; } // get page range if (firstPage < 1) firstPage = 1; if (lastPage < 1 || lastPage > doc->getNumPages()) lastPage = doc->getNumPages(); // write XML file XmlOutputDev *xmlOut = new XmlOutputDev(xmlFileName, doc->getXRef(), doc->getCatalog(), firstPage, lastPage); // tell output device about text handling xmlOut->setTextHandling(math, notext, literal, mergeLevel, unicodeLevel); int exitCode = 2; if (xmlOut->isOk()) { doc->displayPages(xmlOut, firstPage, lastPage, // double hDPI, double vDPI, int rotate, // bool useMediaBox, bool crop, bool printing, 72.0, 72.0, 0, false, false, false); exitCode = 0; } if (xmlOut->hasUnicode()) { fprintf(stderr, "The document contains Unicode (non-ASCII) text.\n"); if (unicodeLevel <= 1) fprintf(stderr, "Unknown Unicode characters were replaced by [U+XXX].\n"); else fprintf(stderr, "UTF-8 was set as document encoding in the preamble.\n"); } // clean up delete xmlOut; delete doc; delete globalParams; return exitCode; }
int main(int argc, char *argv[]) { PDFDoc *doc; GString *fileName; GString *ownerPW, *userPW; SplashColor paperColor; SplashOutputDev *splashOut; GBool ok; int exitCode; int pg; exitCode = 99; // parse args ok = parseArgs(argDesc, &argc, argv); if (!ok || argc != 2 || printVersion || printHelp) { fprintf(stderr, "pdf2jpeg version %s\n", xpdfVersion); fprintf(stderr, "%s\n", xpdfCopyright); if (!printVersion) { printUsage("pdf2jpeg", "<PDF-file> -o <jpegfile>", argDesc); } goto err0; } fileName = new GString(argv[1]); // read config file globalParams = new GlobalParams(cfgFileName); globalParams->setupBaseFonts(NULL); // open PDF file if (ownerPassword[0]) { ownerPW = new GString(ownerPassword); } else { ownerPW = NULL; } if (userPassword[0]) { userPW = new GString(userPassword); } else { userPW = NULL; } doc = new PDFDoc(fileName, ownerPW, userPW); if (userPW) { delete userPW; } if (ownerPW) { delete ownerPW; } if (!doc->isOk()) { exitCode = 1; goto err1; } paperColor[0] = paperColor[1] = paperColor[2] = 0xff; splashOut = new SplashOutputDev(splashModeRGB8, 1, gFalse, paperColor); splashOut->startDoc(doc->getXRef()); if(page>=1 && page<=doc->getNumPages()) { double r = resolution; if(width) { int old_width = doc->getPageCropWidth(page); r = 72.0*width/old_width; } doc->displayPage(splashOut, page, r, r, 0, gFalse, gTrue, gFalse); SplashBitmap*bitmap = splashOut->getBitmap(); if(bitmap) { Guchar*rgb = bitmap->getDataPtr(); int width = bitmap->getWidth(); int height = bitmap->getHeight(); jpeg_save(rgb, width, height, quality, output); } } delete splashOut; exitCode = 0; // clean up err1: delete doc; delete globalParams; err0: // check for memory leaks Object::memCheck(stderr); gMemReport(stderr); return exitCode; }
void TestOptionalContent::checkIsVisible() { GooString *fileName = new GooString(TESTDATADIR "/unittestcases/vis_policy_test.pdf"); globalParams = new GlobalParams(); PDFDoc *doc = new PDFDoc( fileName ); QVERIFY( doc ); OCGs *ocgs = doc->getOptContentConfig(); QVERIFY( ocgs ); XRef *xref = doc->getXRef(); Object obj; // In this test, both Ref(21,0) and Ref(2,0) are set to On // AnyOn, one element array: // 22 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOn>>endobj xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QVERIFY( ocgs->optContentIsVisible( &obj ) ); obj.free(); // Same again, looking for any leaks or dubious free()'s xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QVERIFY( ocgs->optContentIsVisible( &obj ) ); obj.free(); // AnyOff, one element array: // 29 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOff>>endobj xref->fetch( 29, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOn, one element array: // 36 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOn>>endobj xref->fetch( 36, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOff, one element array: // 43 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOff>>endobj xref->fetch( 43, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AnyOn, multi-element array: // 50 0 obj<</Type/OCMD/OCGs[21 0 R 28 0 R]/P/AnyOn>>endobj xref->fetch( 50, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOff, multi-element array: // 57 0 obj<</Type/OCMD/P/AnyOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 57, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOn, multi-element array: // 64 0 obj<</Type/OCMD/P/AllOn/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 64, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOff, multi-element array: // 71 0 obj<</Type/OCMD/P/AllOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 71, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); delete doc; delete globalParams; }
void TestOptionalContent::checkVisibilitySetting() { globalParams = new GlobalParams(); GooString *fileName = new GooString(TESTDATADIR "/unittestcases/vis_policy_test.pdf"); PDFDoc *doc = new PDFDoc( fileName ); QVERIFY( doc ); OCGs *ocgs = doc->getOptContentConfig(); QVERIFY( ocgs ); XRef *xref = doc->getXRef(); Object obj; // In this test, both Ref(21,0) and Ref(28,0) start On, // based on the file settings Object ref21obj; ref21obj.initRef( 21, 0 ); Ref ref21 = ref21obj.getRef(); OptionalContentGroup *ocgA = ocgs->findOcgByRef( ref21 ); QVERIFY( ocgA ); QVERIFY( (ocgA->getName()->cmp("A")) == 0 ); QCOMPARE( ocgA->getState(), OptionalContentGroup::On ); Object ref28obj; ref28obj.initRef( 28, 0 ); Ref ref28 = ref28obj.getRef(); OptionalContentGroup *ocgB = ocgs->findOcgByRef( ref28 ); QVERIFY( ocgB ); QVERIFY( (ocgB->getName()->cmp("B")) == 0 ); QCOMPARE( ocgB->getState(), OptionalContentGroup::On ); // turn one Off ocgA->setState( OptionalContentGroup::Off ); // AnyOn, one element array: // 22 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOn>>endobj xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // Same again, looking for any leaks or dubious free()'s xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AnyOff, one element array: // 29 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOff>>endobj xref->fetch( 29, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOn, one element array: // 36 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOn>>endobj xref->fetch( 36, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOff, one element array: // 43 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOff>>endobj xref->fetch( 43, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AnyOn, multi-element array: // 50 0 obj<</Type/OCMD/OCGs[21 0 R 28 0 R]/P/AnyOn>>endobj xref->fetch( 50, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOff, multi-element array: // 57 0 obj<</Type/OCMD/P/AnyOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 57, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOn, multi-element array: // 64 0 obj<</Type/OCMD/P/AllOn/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 64, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOff, multi-element array: // 71 0 obj<</Type/OCMD/P/AllOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 71, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // Turn the other one off as well (i.e. both are Off) ocgB->setState(OptionalContentGroup::Off); // AnyOn, one element array: // 22 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOn>>endobj xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // Same again, looking for any leaks or dubious free()'s xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AnyOff, one element array: // 29 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOff>>endobj xref->fetch( 29, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOn, one element array: // 36 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOn>>endobj xref->fetch( 36, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOff, one element array: // 43 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOff>>endobj xref->fetch( 43, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOn, multi-element array: // 50 0 obj<</Type/OCMD/OCGs[21 0 R 28 0 R]/P/AnyOn>>endobj xref->fetch( 50, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AnyOff, multi-element array: // 57 0 obj<</Type/OCMD/P/AnyOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 57, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOn, multi-element array: // 64 0 obj<</Type/OCMD/P/AllOn/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 64, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOff, multi-element array: // 71 0 obj<</Type/OCMD/P/AllOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 71, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // Turn the first one on again (21 is On, 28 is Off) ocgA->setState(OptionalContentGroup::On); // AnyOn, one element array: // 22 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOn>>endobj xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // Same again, looking for any leaks or dubious free()'s xref->fetch( 22, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOff, one element array: // 29 0 obj<</Type/OCMD/OCGs[21 0 R]/P/AnyOff>>endobj xref->fetch( 29, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOn, one element array: // 36 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOn>>endobj xref->fetch( 36, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOff, one element array: // 43 0 obj<</Type/OCMD/OCGs[28 0 R]/P/AllOff>>endobj xref->fetch( 43, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOn, multi-element array: // 50 0 obj<</Type/OCMD/OCGs[21 0 R 28 0 R]/P/AnyOn>>endobj xref->fetch( 50, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AnyOff, multi-element array: // 57 0 obj<</Type/OCMD/P/AnyOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 57, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), true ); obj.free(); // AllOn, multi-element array: // 64 0 obj<</Type/OCMD/P/AllOn/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 64, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); // AllOff, multi-element array: // 71 0 obj<</Type/OCMD/P/AllOff/OCGs[21 0 R 28 0 R]>>endobj xref->fetch( 71, 0, &obj ); QVERIFY( obj.isDict() ); QCOMPARE( ocgs->optContentIsVisible( &obj ), false ); obj.free(); delete doc; delete globalParams; }
void PDFFormat::init(std::string& filename){ PDFDoc *doc = PDFDocFactory().createPDFDoc(GooString(filename.c_str())); //GBool enc = doc->isEncrypted(); GooString ID; Object obj,id_obj; Dict* trailer = doc->getXRef()->getTrailerDict()->getDict(); trailer->lookupNF("ID",&obj); obj.getArray()->getNF(0,&id_obj); data.ID1.assign(id_obj.getString()->getCString(),16); obj.getArray()->getNF(1,&id_obj); data.ID2.assign(id_obj.getString()->getCString(),16); GBool enc = trailer->hasKey("Encrypt"); if(enc){ is_encrypted = true; trailer->lookupNF("Encrypt",&obj); Object encObj; doc->getXRef()->fetch(obj.getRef().num,obj.getRef().gen,&encObj); encObj.getDict()->lookupNF("Filter",&obj); encObj.getDict()->lookupNF("R",&obj); this->data.R = obj.getInt(); encObj.getDict()->lookupNF("V",&obj); this->data.V = obj.getInt(); encObj.getDict()->lookupNF("P",&obj); this->data.P = obj.getInt(); encObj.getDict()->lookupNF("Length",&obj); this->data.length = obj.getInt(); encObj.getDict()->lookupNF("O",&obj); if ((int)this->data.R <= 4) { /* Revision 4 or less => 32Byte O string */ this->data.O.assign(obj.getString()->getCString(),32); } else { /* Revision 5 or 6 => 48Byte O string */ this->data.O.assign(obj.getString()->getCString(),48); ::memcpy(this->data.O_valid_salt, this->data.O.substr(32, 8).c_str(), 8); ::memcpy(this->data.O_key_salt, this->data.O.substr(40, 8).c_str(), 8); this->data.O.resize(32); } encObj.getDict()->lookupNF("U",&obj); if ((int)this->data.R <= 4) { /* Revision 4 or less => 32Byte U string */ this->data.U.assign(obj.getString()->getCString(),32); } else { /* Revision 5 or 6 => 48Byte U string */ this->data.U.assign(obj.getString()->getCString(),48); ::memcpy(this->data.U_valid_salt, this->data.U.substr(32, 8).c_str(), 8); ::memcpy(this->data.U_key_salt, this->data.U.substr(40, 8).c_str(), 8); this->data.U.resize(32); } if(encObj.getDict()->hasKey("EncryptMetadata")){ encObj.getDict()->lookupNF("EncryptMetadata", &obj); this->data.MetaEncrypted = obj.getBool(); } int v_major = doc->getPDFMajorVersion(); int v_minor = doc->getPDFMinorVersion(); if (verbose) { // Print PDF encryption information from EncObj std::cout << "======= PDF information =======" << std::endl; std::cout << "PDF version: " << v_major << "." << v_minor << std::endl; if ((int)this->data.R == 5) { std::cout << "Extension level 3 detected." << std::endl; } else if ((int)this->data.R == 6) { std::cout << "Extension level 5 detected." << std::endl; } else if ((int)this->data.R > 6) { std::cout << "Warning: Unknown (unsupported) security revision!" << std::endl; } std::cout << "Security revision: " << (int)this->data.R << std::endl; std::cout << "Encryption alg. version: " << (int)this->data.V << std::endl; std::cout << "Key length: " << (int)this->data.length << std::endl; std::cout << "Metadata encrypted: "; if (this->data.MetaEncrypted) { std::cout << "yes"; } else { std::cout << "no"; } std::cout << std::endl; std::cout << "===============================" << std::endl; } }else{ is_encrypted = false; } is_supported = true; }