/** Namespace URI for the Adobe PDF Schema */
String ADOBE_PDF_NAMESPACE = "http://ns.adobe.com/pdf/1.3/";
+
+ /** Namespace URI for the PDF/A Identification Schema */
+ String PDF_A_IDENTIFICATION = "http://www.aiim.org/pdfa/ns/id";
}
/*
- * Copyright 1999-2004 The Apache Software Foundation.
+ * Copyright 1999-2004,2006 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
p.append("<< /Type /Font");
p.append("\n/BaseFont /");
p.append(this.basefont);
+ p.append(" \n/CIDToGIDMap ");
if (cidMap != null) {
- p.append(" \n/CIDToGIDMap ");
p.append(cidMap.referencePDF());
+ } else {
+ p.append("/Identity");
+ //This is the default. We still write it because PDF/A requires it.
}
p.append(" \n/Subtype /");
p.append(getPDFNameForCIDFontType(this.cidtype));
import java.io.InputStream;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;
this.position += bin.length;
}
+ /** @return the "ID" entry for the file trailer */
+ protected String getIDEntry() {
+ try {
+ MessageDigest digest = MessageDigest.getInstance("MD5");
+ DateFormat df = new SimpleDateFormat("yyyy'-'MM'-'dd'T'HH':'mm':'ss'.'SSS");
+ digest.update(df.format(new Date()).getBytes());
+ //Ignoring the filename here for simplicity even though it's recommended by the PDF spec
+ digest.update(String.valueOf(this.position).getBytes());
+ digest.update(getInfo().toPDF());
+ byte[] res = digest.digest();
+ String s = PDFText.toHex(res);
+ return "/ID [" + s + " " + s + "]";
+ } catch (NoSuchAlgorithmException e) {
+ if (getPDFAMode().isPDFA1LevelB()) {
+ throw new UnsupportedOperationException("MD5 not available: " + e.getMessage());
+ } else {
+ return ""; //Entry is optional if PDF/A is not active
+ }
+ }
+ }
+
/**
* write the trailer
*
+ "/Info "
+ this.info.referencePDF()
+ "\n"
+ + getIDEntry()
+ + "\n"
+ encryptEntry
+ ">>\n"
+ "startxref\n"
/*
- * Copyright 1999-2004 The Apache Software Foundation.
+ * Copyright 1999-2004,2006 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
}
}
+ /**
+ * Validates the PDF object prior to serialization.
+ */
+ protected void validate() {
+ if (getDocumentSafely().getPDFAMode().isPDFA1LevelB()) {
+ if (this.getClass() == PDFFont.class) {
+ throw new PDFConformanceException("For PDF/A-1, all fonts, even the base 14"
+ + " fonts, have to be embedded!");
+ }
+ }
+ }
+
/**
* @see org.apache.fop.pdf.PDFObject#toPDFString()
*/
public String toPDFString() {
+ validate();
StringBuffer p = new StringBuffer(128);
p.append(getObjectID());
p.append("<< /Type /Font\n/Subtype /"
/*
- * Copyright 1999-2004 The Apache Software Foundation.
+ * Copyright 1999-2004,2006 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
this.fontfile = fontfile;
}
+ /** @return the FontFile or null if the font is not embedded */
+ public AbstractPDFStream getFontFile() {
+ return this.fontfile;
+ }
+
// public void setCharSet(){}//for subset fonts
/**
/*
- * Copyright 1999-2004 The Apache Software Foundation.
+ * Copyright 1999-2004,2006 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
this.descriptor = descriptor;
}
+ /** @return the FontDescriptor or null if there is none */
+ public PDFFontDescriptor getDescriptor() {
+ return this.descriptor;
+ }
+
+ /** @see org.apache.fop.pdf.PDFFont#validate() */
+ protected void validate() {
+ if (getDocumentSafely().getPDFAMode().isPDFA1LevelB()) {
+ if (this.getDescriptor().getFontFile() == null) {
+ throw new PDFConformanceException("For PDF/A-1, all fonts have to be embedded!");
+ }
+ }
+ }
+
/**
* @see org.apache.fop.pdf.PDFFont#fillInPDF(StringBuffer)
*/
desc.appendChild(el);
el.appendChild(doc.createTextNode(pdfDoc.getPDFVersionString()));
+ //PDF/A identification
+ PDFAMode pdfaMode = pdfDoc.getPDFAMode();
+ if (pdfaMode.isPDFA1LevelB()) {
+ desc = doc.createElementNS(XMPConstants.RDF_NAMESPACE, "rdf:Description");
+ desc.setAttribute("about", "");
+ desc.setAttributeNS(xmlns, "xmlns:pdfaid", XMPConstants.PDF_A_IDENTIFICATION);
+ rdf.appendChild(desc);
+ el = doc.createElementNS(XMPConstants.PDF_A_IDENTIFICATION, "pdfaid:part");
+ desc.appendChild(el);
+ el.appendChild(doc.createTextNode("1")); //PDF/A-1
+ el = doc.createElementNS(XMPConstants.PDF_A_IDENTIFICATION, "pdfaid:conformance");
+ desc.appendChild(el);
+ if (pdfaMode == PDFAMode.PDFA_1A) {
+ el.appendChild(doc.createTextNode("A")); //PDF/A-1a
+ } else {
+ el.appendChild(doc.createTextNode("B")); //PDF/A-1b
+ }
+ }
+
return doc;
}
/*
- * Copyright 1999-2005 The Apache Software Foundation.
+ * Copyright 1999-2006 The Apache Software Foundation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
private String buildDictionaryFromPS(String lengthEntry,
String dictEntries) {
+ if (getDocumentSafely().getPDFAMode().isPDFA1LevelB()) {
+ throw new PDFConformanceException("PostScript XObjects are prohibited when PDF/A"
+ + " is active. Convert EPS graphics to another format.");
+ }
StringBuffer sb = new StringBuffer(128);
sb.append(getObjectID());
sb.append("<</Type /XObject\n");