--- backend/pdf/ev-poppler.cc.orig 2009-04-15 22:10:52.000000000 +0200 +++ backend/pdf/ev-poppler.cc 2009-05-10 23:52:10.000000000 +0200 @@ -19,6 +19,7 @@ #include "config.h" +#include #include #include #include @@ -50,6 +51,11 @@ #include "ev-attachment.h" #include "ev-image.h" +#include +#include +#include +#include + #if (defined (HAVE_POPPLER_PAGE_RENDER)) && (defined (HAVE_CAIRO_PDF) || defined (HAVE_CAIRO_PS)) #define HAVE_CAIRO_PRINT #endif @@ -128,6 +134,7 @@ PopplerAction *action); static void pdf_document_search_free (PdfDocumentSearch *search); static void pdf_print_context_free (PdfPrintContext *ctx); +static char* pdf_document_get_format_from_metadata (char* metadata); EV_BACKEND_REGISTER_WITH_CODE (PdfDocument, pdf_document, { @@ -570,6 +577,7 @@ PopplerViewerPreferences view_prefs; PopplerPermissions permissions; EvPage *page; + char* metadata; info = g_new0 (EvDocumentInfo, 1); @@ -606,8 +614,16 @@ "creation-date", &(info->creation_date), "mod-date", &(info->modified_date), "linearized", &(info->linearized), + "metadata", &metadata, NULL); + if (metadata != NULL) + { + char* format = pdf_document_get_format_from_metadata(metadata); + if (format != NULL) + info->format = format; + } + info->n_pages = ev_document_get_n_pages (document); if (info->n_pages > 0) { @@ -2484,3 +2500,92 @@ iface->hide_layer = pdf_document_layers_hide_layer; iface->layer_is_visible = pdf_document_layers_layer_is_visible; } + +// reference: +// http://www.pdfa.org/lib/exe/fetch.php?id=pdfa%3Aen%3Atechdoc&cache=cache&media=pdfa:techdoc:tn0001_pdfa-1_and_namespaces_2008-03-18.pdf +static char* +pdf_document_get_format_from_metadata (char* metadata) +{ + xmlDocPtr doc = xmlParseMemory(metadata, strlen(metadata)); + if (doc == NULL) + return NULL; // invalid xml metadata + + xmlXPathContextPtr xpathCtx = xmlXPathNewContext(doc); + if (xpathCtx == NULL) + { + xmlFreeDoc(doc); + return NULL; // invalid xpath context + } + + // add pdf/a namespaces + xmlXPathRegisterNs(xpathCtx, BAD_CAST "x", BAD_CAST "adobe:ns:meta/"); + xmlXPathRegisterNs(xpathCtx, BAD_CAST "rdf", BAD_CAST "http://www.w3.org/1999/02/22-rdf-syntax-ns#"); + xmlXPathRegisterNs(xpathCtx, BAD_CAST "pdfaid", BAD_CAST "http://www.aiim.org/pdfa/ns/id/"); + + xmlChar* part = NULL; + xmlChar* conf = NULL; + xmlXPathObjectPtr xpathObj; + + // reads pdf/a part + // first syntax: child node + xpathObj = xmlXPathEvalExpression(BAD_CAST "/x:xmpmeta/rdf:RDF/rdf:Description/pdfaid:part", xpathCtx); + if (xpathObj != NULL) + { + if (xpathObj->nodesetval != NULL && xpathObj->nodesetval->nodeNr != 0) + part = xmlNodeGetContent(xpathObj->nodesetval->nodeTab[0]); + + xmlXPathFreeObject(xpathObj); + } + if (part == NULL) + { + // second syntax: attribute + xpathObj = xmlXPathEvalExpression(BAD_CAST "/x:xmpmeta/rdf:RDF/rdf:Description/@pdfaid:part", xpathCtx); + if (xpathObj != NULL) + { + if (xpathObj->nodesetval != NULL && xpathObj->nodesetval->nodeNr != 0) + part = xmlNodeGetContent(xpathObj->nodesetval->nodeTab[0]); + + xmlXPathFreeObject(xpathObj); + } + } + + // reads pdf/a conformance + // first syntax: child node + xpathObj = xmlXPathEvalExpression(BAD_CAST "/x:xmpmeta/rdf:RDF/rdf:Description/pdfaid:conformance", xpathCtx); + if (xpathObj != NULL) + { + if (xpathObj->nodesetval != NULL && xpathObj->nodesetval->nodeNr != 0) + conf = xmlNodeGetContent(xpathObj->nodesetval->nodeTab[0]); + + xmlXPathFreeObject(xpathObj); + } + if (conf == NULL) + { + // second syntax: attribute + xpathObj = xmlXPathEvalExpression(BAD_CAST "/x:xmpmeta/rdf:RDF/rdf:Description/@pdfaid:conformance", xpathCtx); + if (xpathObj != NULL) + { + if (xpathObj->nodesetval != NULL && xpathObj->nodesetval->nodeNr != 0) + conf = xmlNodeGetContent(xpathObj->nodesetval->nodeTab[0]); + + xmlXPathFreeObject(xpathObj); + } + } + + char* result = NULL; + if (part != NULL && conf != NULL) + { + // makes conf lowercase + for(int i = 0; conf[i]; i++) + conf[i] = tolower(conf[i]); + + // return buffer + result = new char[20]; + snprintf(result, 20, "PDF/A - %s%s", part, conf); + } + + // Cleanup + xmlXPathFreeContext(xpathCtx); + xmlFreeDoc(doc); + return result; +} --- backend/pdf/Makefile.in.orig 2009-05-10 23:57:49.000000000 +0200 +++ backend/pdf/Makefile.in 2009-05-10 23:54:17.000000000 +0200 @@ -323,7 +323,8 @@ $(BACKEND_CFLAGS) \ $(POPPLER_CFLAGS) \ $(WARN_CXXFLAGS) \ - $(DISABLE_DEPRECATED) + $(DISABLE_DEPRECATED) \ + `pkg-config --cflags libxml-2.0` backend_LTLIBRARIES = libpdfdocument.la libpdfdocument_la_SOURCES = \