update to PDFbox 3.0.0 beta1, fix cmap ttf font bug in two consecutive script engine runs by removing cache from org.xbib.graphics.pdfbox.layout.font.Fonts
This commit is contained in:
parent
ca317f41ec
commit
134343ba47
31 changed files with 455 additions and 166 deletions
|
@ -1,5 +1,5 @@
|
||||||
group = org.xbib.graphics
|
group = org.xbib.graphics
|
||||||
name = graphics
|
name = graphics
|
||||||
version = 4.4.1
|
version = 4.5.0
|
||||||
|
|
||||||
org.gradle.warning.mode = ALL
|
org.gradle.warning.mode = ALL
|
||||||
|
|
|
@ -4,4 +4,5 @@ module org.xbib.graphics.ghostscript {
|
||||||
requires java.logging;
|
requires java.logging;
|
||||||
requires transitive java.desktop;
|
requires transitive java.desktop;
|
||||||
requires transitive org.apache.pdfbox;
|
requires transitive org.apache.pdfbox;
|
||||||
|
requires transitive org.apache.pdfbox.io;
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,7 +7,8 @@ import javax.imageio.ImageIO;
|
||||||
import javax.imageio.ImageReadParam;
|
import javax.imageio.ImageReadParam;
|
||||||
import javax.imageio.ImageReader;
|
import javax.imageio.ImageReader;
|
||||||
import javax.imageio.stream.ImageInputStream;
|
import javax.imageio.stream.ImageInputStream;
|
||||||
import org.apache.pdfbox.io.MemoryUsageSetting;
|
|
||||||
|
import org.apache.pdfbox.Loader;
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
import org.apache.pdfbox.pdmodel.PDPage;
|
import org.apache.pdfbox.pdmodel.PDPage;
|
||||||
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
||||||
|
@ -201,7 +202,7 @@ public class PDFRasterizer {
|
||||||
PathMatcher pathMatcher = sourceDir.getFileSystem().getPathMatcher("glob:" + globPattern);
|
PathMatcher pathMatcher = sourceDir.getFileSystem().getPathMatcher("glob:" + globPattern);
|
||||||
List<PDDocument> coverPageDocs = new ArrayList<>();
|
List<PDDocument> coverPageDocs = new ArrayList<>();
|
||||||
try (Stream<Path> files = Files.list(sourceDir);
|
try (Stream<Path> files = Files.list(sourceDir);
|
||||||
PDDocument pdDocument = new PDDocument(MemoryUsageSetting.setupTempFileOnly());
|
PDDocument pdDocument = new PDDocument();
|
||||||
OutputStream outputStream = new BufferedOutputStream(Files.newOutputStream(targetFile))) {
|
OutputStream outputStream = new BufferedOutputStream(Files.newOutputStream(targetFile))) {
|
||||||
pdDocument.setResourceCache(null);
|
pdDocument.setResourceCache(null);
|
||||||
List<Path> entries = files.sorted()
|
List<Path> entries = files.sorted()
|
||||||
|
@ -223,7 +224,7 @@ public class PDFRasterizer {
|
||||||
if (path.getFileName().toString().toLowerCase(Locale.ROOT).endsWith(".pdf")) {
|
if (path.getFileName().toString().toLowerCase(Locale.ROOT).endsWith(".pdf")) {
|
||||||
logger.info("found pdf " + path);
|
logger.info("found pdf " + path);
|
||||||
try (InputStream inputStream = Files.newInputStream(path)) {
|
try (InputStream inputStream = Files.newInputStream(path)) {
|
||||||
PDDocument doc = PDDocument.load(inputStream);
|
PDDocument doc = Loader.loadPDF(inputStream.readAllBytes());
|
||||||
for (int i = 0; i < doc.getNumberOfPages(); i++) {
|
for (int i = 0; i < doc.getNumberOfPages(); i++) {
|
||||||
PDPage page = doc.getPage(i);
|
PDPage page = doc.getPage(i);
|
||||||
PDPage newPage = pdDocument.importPage(page); // shallow copy :(
|
PDPage newPage = pdDocument.importPage(page); // shallow copy :(
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.xbib.graphics.pdfbox.groovy.analyze
|
package org.xbib.graphics.pdfbox.groovy.analyze
|
||||||
|
|
||||||
import groovy.util.logging.Log
|
import groovy.util.logging.Log
|
||||||
|
import org.apache.pdfbox.Loader
|
||||||
import org.apache.pdfbox.contentstream.PDFGraphicsStreamEngine
|
import org.apache.pdfbox.contentstream.PDFGraphicsStreamEngine
|
||||||
import org.apache.pdfbox.cos.COSName
|
import org.apache.pdfbox.cos.COSName
|
||||||
import org.apache.pdfbox.cos.COSStream
|
import org.apache.pdfbox.cos.COSStream
|
||||||
|
@ -23,7 +24,8 @@ class DocumentAnalyzer {
|
||||||
|
|
||||||
DocumentAnalyzer(InputStream inputStream) {
|
DocumentAnalyzer(InputStream inputStream) {
|
||||||
inputStream.withCloseable {
|
inputStream.withCloseable {
|
||||||
PDDocument document = PDDocument.load(inputStream)
|
byte[] bytes = inputStream.readAllBytes()
|
||||||
|
PDDocument document = Loader.loadPDF(bytes)
|
||||||
result."author" = document.getDocumentInformation().author
|
result."author" = document.getDocumentInformation().author
|
||||||
result."creator" = document.getDocumentInformation().creator
|
result."creator" = document.getDocumentInformation().creator
|
||||||
result."producer" = document.getDocumentInformation().producer
|
result."producer" = document.getDocumentInformation().producer
|
||||||
|
|
|
@ -99,7 +99,7 @@ class PdfDocument implements Closeable {
|
||||||
void setPageNumber(int value) {
|
void setPageNumber(int value) {
|
||||||
this.pageNumber = value
|
this.pageNumber = value
|
||||||
contentStream?.close()
|
contentStream?.close()
|
||||||
contentStream = new PDPageContentStream(pdDocument, currentPage, true, true)
|
contentStream = new PDPageContentStream(pdDocument, currentPage, PDPageContentStream.AppendMode.APPEND, true)
|
||||||
toStartPosition()
|
toStartPosition()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -4,27 +4,28 @@ import org.apache.pdfbox.pdmodel.PDDocument
|
||||||
import org.apache.pdfbox.pdmodel.font.PDFont
|
import org.apache.pdfbox.pdmodel.font.PDFont
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType0Font
|
import org.apache.pdfbox.pdmodel.font.PDType0Font
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType1Font
|
import org.apache.pdfbox.pdmodel.font.PDType1Font
|
||||||
|
import org.apache.pdfbox.pdmodel.font.Standard14Fonts
|
||||||
import org.xbib.graphics.pdfbox.groovy.Font
|
import org.xbib.graphics.pdfbox.groovy.Font
|
||||||
|
|
||||||
class PdfFont {
|
class PdfFont {
|
||||||
|
|
||||||
private static final DEFAULT_FONT = PDType1Font.HELVETICA
|
private static final DEFAULT_FONT = new PDType1Font(Standard14Fonts.FontName.HELVETICA)
|
||||||
|
|
||||||
private static fonts = [
|
private static fonts = [
|
||||||
'Times-Roman': [regular: PDType1Font.TIMES_ROMAN,
|
'Times-Roman': [regular: new PDType1Font(Standard14Fonts.FontName.TIMES_ROMAN),
|
||||||
bold: PDType1Font.TIMES_BOLD,
|
bold: new PDType1Font(Standard14Fonts.FontName.TIMES_BOLD),
|
||||||
italic : PDType1Font.TIMES_ITALIC,
|
italic : new PDType1Font(Standard14Fonts.FontName.TIMES_ITALIC),
|
||||||
boldItalic: PDType1Font.TIMES_BOLD_ITALIC],
|
boldItalic: new PDType1Font(Standard14Fonts.FontName.TIMES_BOLD_ITALIC) ],
|
||||||
'Helvetica' : [regular: PDType1Font.HELVETICA,
|
'Helvetica' : [regular: new PDType1Font(Standard14Fonts.FontName.HELVETICA),
|
||||||
bold: PDType1Font.HELVETICA_BOLD,
|
bold: new PDType1Font(Standard14Fonts.FontName.HELVETICA_BOLD),
|
||||||
italic : PDType1Font.HELVETICA_OBLIQUE,
|
italic : new PDType1Font(Standard14Fonts.FontName.HELVETICA_OBLIQUE),
|
||||||
boldItalic: PDType1Font.HELVETICA_BOLD_OBLIQUE],
|
boldItalic: new PDType1Font(Standard14Fonts.FontName.HELVETICA_BOLD_OBLIQUE) ],
|
||||||
'Courier' : [regular: PDType1Font.COURIER,
|
'Courier' : [regular: new PDType1Font(Standard14Fonts.FontName.COURIER),
|
||||||
bold: PDType1Font.COURIER_BOLD,
|
bold: new PDType1Font(Standard14Fonts.FontName.COURIER_BOLD),
|
||||||
italic : PDType1Font.COURIER_OBLIQUE,
|
italic : new PDType1Font(Standard14Fonts.FontName.COURIER_OBLIQUE),
|
||||||
boldItalic: PDType1Font.COURIER_BOLD_OBLIQUE],
|
boldItalic: new PDType1Font(Standard14Fonts.FontName.COURIER_BOLD_OBLIQUE) ],
|
||||||
'Symbol' : [regular: PDType1Font.SYMBOL],
|
'Symbol' : [regular: new PDType1Font(Standard14Fonts.FontName.SYMBOL) ],
|
||||||
'Dingbat' : [regular: PDType1Font.ZAPF_DINGBATS]
|
'Dingbat' : [regular: new PDType1Font(Standard14Fonts.FontName.ZAPF_DINGBATS) ]
|
||||||
]
|
]
|
||||||
|
|
||||||
static boolean addFont(PDDocument document, String name, InputStream inputStream, boolean bold, boolean italic) {
|
static boolean addFont(PDDocument document, String name, InputStream inputStream, boolean bold, boolean italic) {
|
||||||
|
|
|
@ -1,10 +1,13 @@
|
||||||
package org.xbib.graphics.pdfbox.groovy.test
|
package org.xbib.graphics.pdfbox.groovy.test
|
||||||
|
|
||||||
import groovy.util.logging.Log
|
import groovy.util.logging.Log
|
||||||
|
import org.apache.fontbox.ttf.CmapLookup
|
||||||
import org.apache.fontbox.ttf.CmapSubtable
|
import org.apache.fontbox.ttf.CmapSubtable
|
||||||
import org.apache.fontbox.ttf.NamingTable
|
import org.apache.fontbox.ttf.NamingTable
|
||||||
import org.apache.fontbox.ttf.TTFParser
|
import org.apache.fontbox.ttf.TTFParser
|
||||||
import org.apache.fontbox.ttf.TrueTypeFont
|
import org.apache.fontbox.ttf.TrueTypeFont
|
||||||
|
import org.apache.pdfbox.io.RandomAccessRead
|
||||||
|
import org.apache.pdfbox.io.RandomAccessReadBuffer
|
||||||
import org.junit.Test
|
import org.junit.Test
|
||||||
|
|
||||||
import java.nio.file.Files
|
import java.nio.file.Files
|
||||||
|
@ -28,8 +31,9 @@ class LoadFontTest {
|
||||||
private final Map<String, TrueTypeFont> otf = new HashMap<>()
|
private final Map<String, TrueTypeFont> otf = new HashMap<>()
|
||||||
|
|
||||||
private void addOpenTypeFont(String name, InputStream inputStream) {
|
private void addOpenTypeFont(String name, InputStream inputStream) {
|
||||||
TTFParser ttfParser = new TTFParser(false, true)
|
TTFParser ttfParser = new TTFParser(true)
|
||||||
TrueTypeFont trueTypeFont = ttfParser.parse(inputStream)
|
RandomAccessRead read = new RandomAccessReadBuffer(inputStream)
|
||||||
|
TrueTypeFont trueTypeFont = ttfParser.parse(read)
|
||||||
try {
|
try {
|
||||||
NamingTable nameTable = trueTypeFont.getNaming()
|
NamingTable nameTable = trueTypeFont.getNaming()
|
||||||
if (!nameTable) {
|
if (!nameTable) {
|
||||||
|
@ -51,7 +55,7 @@ class LoadFontTest {
|
||||||
log.warning("Missing 'name' entry for PostScript name in font " + inputStream)
|
log.warning("Missing 'name' entry for PostScript name in font " + inputStream)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
CmapSubtable cmapSubtable = trueTypeFont.getUnicodeCmap(true)
|
CmapLookup cmapSubtable = trueTypeFont.getUnicodeCmapLookup(true)
|
||||||
if (!cmapSubtable) {
|
if (!cmapSubtable) {
|
||||||
log.warning('missing cmap table in ' + name)
|
log.warning('missing cmap table in ' + name)
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -5,6 +5,7 @@ import org.apache.pdfbox.pdmodel.PDPage
|
||||||
import org.apache.pdfbox.pdmodel.PDPageContentStream
|
import org.apache.pdfbox.pdmodel.PDPageContentStream
|
||||||
import org.apache.pdfbox.pdmodel.common.PDRectangle
|
import org.apache.pdfbox.pdmodel.common.PDRectangle
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType1Font
|
import org.apache.pdfbox.pdmodel.font.PDType1Font
|
||||||
|
import org.apache.pdfbox.pdmodel.font.Standard14Fonts
|
||||||
import org.apache.pdfbox.pdmodel.graphics.form.PDFormXObject
|
import org.apache.pdfbox.pdmodel.graphics.form.PDFormXObject
|
||||||
import org.apache.pdfbox.pdmodel.graphics.image.LosslessFactory
|
import org.apache.pdfbox.pdmodel.graphics.image.LosslessFactory
|
||||||
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject
|
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject
|
||||||
|
@ -67,7 +68,7 @@ class PdfBoxBarcodeTest {
|
||||||
private static void createText(PDPage page, PDPageContentStream contentStream) {
|
private static void createText(PDPage page, PDPageContentStream contentStream) {
|
||||||
contentStream.moveTo(32.0f, (page.getBBox().height - 80f) as float)
|
contentStream.moveTo(32.0f, (page.getBBox().height - 80f) as float)
|
||||||
contentStream.beginText()
|
contentStream.beginText()
|
||||||
contentStream.setFont(PDType1Font.HELVETICA, 12f)
|
contentStream.setFont(new PDType1Font(Standard14Fonts.FontName.HELVETICA), 12f)
|
||||||
contentStream.showText("Hello World")
|
contentStream.showText("Hello World")
|
||||||
contentStream.endText()
|
contentStream.endText()
|
||||||
contentStream.close()
|
contentStream.close()
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.xbib.graphics.pdfbox.groovy.test
|
package org.xbib.graphics.pdfbox.groovy.test
|
||||||
|
|
||||||
import groovy.xml.XmlParser
|
import groovy.xml.XmlParser
|
||||||
|
import org.apache.pdfbox.Loader
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument
|
import org.apache.pdfbox.pdmodel.PDDocument
|
||||||
import org.xbib.graphics.pdfbox.groovy.Cell
|
import org.xbib.graphics.pdfbox.groovy.Cell
|
||||||
import org.xbib.graphics.pdfbox.groovy.Document
|
import org.xbib.graphics.pdfbox.groovy.Document
|
||||||
|
@ -12,7 +13,7 @@ import org.xbib.graphics.pdfbox.groovy.TextBlock
|
||||||
class PdfDocumentLoader {
|
class PdfDocumentLoader {
|
||||||
|
|
||||||
static Document load(byte[] data) {
|
static Document load(byte[] data) {
|
||||||
PDDocument pdfDoc = PDDocument.load(new ByteArrayInputStream(data))
|
PDDocument pdfDoc = Loader.loadPDF(data)
|
||||||
Document document = new Document(element: pdfDoc)
|
Document document = new Document(element: pdfDoc)
|
||||||
def metaData = new XmlParser().parse(pdfDoc.documentCatalog.metadata.createInputStream())
|
def metaData = new XmlParser().parse(pdfDoc.documentCatalog.metadata.createInputStream())
|
||||||
document.margin.top = metaData.'@marginTop' as Integer
|
document.margin.top = metaData.'@marginTop' as Integer
|
||||||
|
|
|
@ -6,14 +6,17 @@ import org.apache.pdfbox.pdmodel.font.PDType1Font;
|
||||||
import java.awt.Color;
|
import java.awt.Color;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
|
||||||
public class Cell<T extends PDPage> {
|
public class Cell<T extends PDPage> {
|
||||||
|
|
||||||
private float width;
|
private float width;
|
||||||
private Float height;
|
private Float height;
|
||||||
private String text;
|
private String text;
|
||||||
|
|
||||||
private PDFont font = PDType1Font.HELVETICA;
|
private PDFont font = new PDType1Font(HELVETICA);
|
||||||
private PDFont fontBold = PDType1Font.HELVETICA_BOLD;
|
private PDFont fontBold = new PDType1Font(HELVETICA_BOLD);
|
||||||
|
|
||||||
private float fontSize = 8;
|
private float fontSize = 8;
|
||||||
private Color fillColor;
|
private Color fillColor;
|
||||||
|
|
|
@ -13,6 +13,10 @@ import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Stack;
|
import java.util.Stack;
|
||||||
|
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_OBLIQUE;
|
||||||
|
|
||||||
public class Paragraph {
|
public class Paragraph {
|
||||||
|
|
||||||
private float width;
|
private float width;
|
||||||
|
@ -74,9 +78,9 @@ public class Paragraph {
|
||||||
this.font = font;
|
this.font = font;
|
||||||
// check if we have different default font for italic and bold text
|
// check if we have different default font for italic and bold text
|
||||||
if (FontUtils.getDefaultfonts().isEmpty()) {
|
if (FontUtils.getDefaultfonts().isEmpty()) {
|
||||||
fontBold = PDType1Font.HELVETICA_BOLD;
|
fontBold = new PDType1Font(HELVETICA_BOLD);
|
||||||
fontItalic = PDType1Font.HELVETICA_OBLIQUE;
|
fontItalic = new PDType1Font(HELVETICA_OBLIQUE);
|
||||||
fontBoldItalic = PDType1Font.HELVETICA_BOLD_OBLIQUE;
|
fontBoldItalic = new PDType1Font(HELVETICA_BOLD_OBLIQUE);
|
||||||
} else {
|
} else {
|
||||||
fontBold = FontUtils.getDefaultfonts().get("fontBold");
|
fontBold = FontUtils.getDefaultfonts().get("fontBold");
|
||||||
fontBoldItalic = FontUtils.getDefaultfonts().get("fontBoldItalic");
|
fontBoldItalic = FontUtils.getDefaultfonts().get("fontBoldItalic");
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
package org.xbib.graphics.pdfbox.layout.element;
|
package org.xbib.graphics.pdfbox.layout.element;
|
||||||
|
|
||||||
import org.apache.pdfbox.io.MemoryUsageSetting;
|
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
import org.apache.pdfbox.pdmodel.PDDocumentInformation;
|
import org.apache.pdfbox.pdmodel.PDDocumentInformation;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.render.Layout;
|
import org.xbib.graphics.pdfbox.layout.element.render.Layout;
|
||||||
|
@ -45,17 +44,7 @@ public class Document implements Element, Closeable, RenderListener {
|
||||||
* Creates a Document.
|
* Creates a Document.
|
||||||
*/
|
*/
|
||||||
public Document() {
|
public Document() {
|
||||||
this(PageFormats.A4_PORTRAIT, true);
|
this(PageFormats.A4_PORTRAIT);
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a Document based on the given page format. By default, a
|
|
||||||
* {@link VerticalLayout} is used.
|
|
||||||
*
|
|
||||||
* @param pageFormat the page format box to use.
|
|
||||||
*/
|
|
||||||
public Document(PageFormat pageFormat) {
|
|
||||||
this(pageFormat, true);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -71,18 +60,17 @@ public class Document implements Element, Closeable, RenderListener {
|
||||||
float marginRight,
|
float marginRight,
|
||||||
float marginTop,
|
float marginTop,
|
||||||
float marginBottom) {
|
float marginBottom) {
|
||||||
this(marginLeft, marginRight, marginTop, marginBottom, true);
|
this(PageFormat.builder().margins(marginLeft, marginRight, marginTop, marginBottom).build());
|
||||||
}
|
}
|
||||||
|
|
||||||
public Document(float marginLeft,
|
/**
|
||||||
float marginRight,
|
* Creates a Document based on the given page format. By default, a
|
||||||
float marginTop,
|
* {@link VerticalLayout} is used.
|
||||||
float marginBottom, boolean memory) {
|
*
|
||||||
this(PageFormat.builder().margins(marginLeft, marginRight, marginTop, marginBottom).build(), memory);
|
* @param pageFormat the page format box to use.
|
||||||
}
|
*/
|
||||||
|
public Document(PageFormat pageFormat) {
|
||||||
public Document(PageFormat pageFormat, boolean memory) {
|
this.pdDocument = new PDDocument();
|
||||||
this.pdDocument = new PDDocument(memory ? MemoryUsageSetting.setupMainMemoryOnly() : MemoryUsageSetting.setupTempFileOnly());
|
|
||||||
this.pdDocumentInformation = new PDDocumentInformation();
|
this.pdDocumentInformation = new PDDocumentInformation();
|
||||||
setPageFormat(pageFormat);
|
setPageFormat(pageFormat);
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,6 +2,8 @@ package org.xbib.graphics.pdfbox.layout.element;
|
||||||
|
|
||||||
import org.xbib.graphics.pdfbox.layout.font.Font;
|
import org.xbib.graphics.pdfbox.layout.font.Font;
|
||||||
|
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
public class TextElement implements Element {
|
public class TextElement implements Element {
|
||||||
|
|
||||||
private final boolean markup;
|
private final boolean markup;
|
||||||
|
@ -17,6 +19,8 @@ public class TextElement implements Element {
|
||||||
this.value = value;
|
this.value = value;
|
||||||
this.font = font;
|
this.font = font;
|
||||||
this.fontsize = fontsize;
|
this.fontsize = fontsize;
|
||||||
|
Objects.requireNonNull(value, "you must specify a value");
|
||||||
|
Objects.requireNonNull(font, "you must specify a font");
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getValue() {
|
public String getValue() {
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package org.xbib.graphics.pdfbox.layout.element.scripting;
|
package org.xbib.graphics.pdfbox.layout.element.scripting;
|
||||||
|
|
||||||
|
import java.io.Closeable;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.scripting.command.Command;
|
import org.xbib.graphics.pdfbox.layout.element.scripting.command.Command;
|
||||||
import org.xbib.settings.Settings;
|
import org.xbib.settings.Settings;
|
||||||
|
@ -7,7 +8,7 @@ import org.xbib.settings.Settings;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
public class Engine {
|
public class Engine implements Closeable {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(Engine.class.getName());
|
private static final Logger logger = Logger.getLogger(Engine.class.getName());
|
||||||
|
|
||||||
|
@ -73,4 +74,8 @@ public class Engine {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void close() throws IOException {
|
||||||
|
state.close();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,11 +3,12 @@ package org.xbib.graphics.pdfbox.layout.element.scripting;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.Document;
|
import org.xbib.graphics.pdfbox.layout.element.Document;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.Element;
|
import org.xbib.graphics.pdfbox.layout.element.Element;
|
||||||
|
|
||||||
|
import java.io.Closeable;
|
||||||
|
import java.io.IOException;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Stack;
|
import java.util.Stack;
|
||||||
import java.util.stream.Collectors;
|
|
||||||
|
|
||||||
public class State {
|
public class State implements Closeable {
|
||||||
|
|
||||||
private final Stack<Element> elements = new Stack<>();
|
private final Stack<Element> elements = new Stack<>();
|
||||||
|
|
||||||
|
@ -26,8 +27,26 @@ public class State {
|
||||||
List<Document> list = elements.stream()
|
List<Document> list = elements.stream()
|
||||||
.filter(e -> e instanceof Document)
|
.filter(e -> e instanceof Document)
|
||||||
.map(e -> (Document) e)
|
.map(e -> (Document) e)
|
||||||
.collect(Collectors.toList());
|
.toList();
|
||||||
int size = list.size();
|
int size = list.size();
|
||||||
return size == 0 ? null : list.get(size - 1);
|
return size == 0 ? null : list.get(size - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Close all documents and free resources.
|
||||||
|
* @throws IOException if a document can not be closed.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void close() throws IOException {
|
||||||
|
elements.stream()
|
||||||
|
.filter(e -> e instanceof Document)
|
||||||
|
.map(e -> (Document) e)
|
||||||
|
.forEach(d -> {
|
||||||
|
try {
|
||||||
|
d.close();
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,7 +11,6 @@ import org.xbib.graphics.pdfbox.layout.element.scripting.Engine;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.scripting.State;
|
import org.xbib.graphics.pdfbox.layout.element.scripting.State;
|
||||||
import org.xbib.graphics.pdfbox.layout.text.Alignment;
|
import org.xbib.graphics.pdfbox.layout.text.Alignment;
|
||||||
import org.xbib.graphics.pdfbox.layout.position.Position;
|
import org.xbib.graphics.pdfbox.layout.position.Position;
|
||||||
import org.xbib.graphics.pdfbox.layout.text.TextSequence;
|
|
||||||
import org.xbib.settings.Settings;
|
import org.xbib.settings.Settings;
|
||||||
|
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
|
|
@ -2,25 +2,34 @@ package org.xbib.graphics.pdfbox.layout.font;
|
||||||
|
|
||||||
import org.apache.pdfbox.pdmodel.font.PDFont;
|
import org.apache.pdfbox.pdmodel.font.PDFont;
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType1Font;
|
import org.apache.pdfbox.pdmodel.font.PDType1Font;
|
||||||
|
import org.apache.pdfbox.pdmodel.font.Standard14Fonts;
|
||||||
|
|
||||||
import java.io.IOException;
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ROMAN;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* In order to easy handling with fonts, this enum bundles the
|
* In order to easy handling with fonts, this enum bundles the
|
||||||
* plain/italic/bold/bold-italic variants of the three standard font types
|
* plain/italic/bold/bold-italic variants of the three standard font types
|
||||||
* {@link PDType1Font#TIMES_ROMAN Times},{@link PDType1Font#COURIER Courier} and
|
* Times, Courier, Helveticy.
|
||||||
* {@link PDType1Font#HELVETICA Helveticy}.
|
|
||||||
*/
|
*/
|
||||||
public enum BaseFont implements Font {
|
public enum BaseFont implements Font {
|
||||||
|
|
||||||
TIMES(PDType1Font.TIMES_ROMAN, PDType1Font.TIMES_BOLD,
|
TIMES(new PDType1Font(TIMES_ROMAN), new PDType1Font(TIMES_BOLD),
|
||||||
PDType1Font.TIMES_ITALIC, PDType1Font.TIMES_BOLD_ITALIC),
|
new PDType1Font(TIMES_ITALIC), new PDType1Font(TIMES_BOLD_ITALIC)),
|
||||||
|
|
||||||
COURIER(PDType1Font.COURIER, PDType1Font.COURIER_BOLD,
|
COURIER(new PDType1Font(Standard14Fonts.FontName.COURIER), new PDType1Font(COURIER_BOLD),
|
||||||
PDType1Font.COURIER_OBLIQUE, PDType1Font.COURIER_BOLD_OBLIQUE),
|
new PDType1Font(COURIER_OBLIQUE), new PDType1Font(COURIER_BOLD_OBLIQUE)),
|
||||||
|
|
||||||
HELVETICA(PDType1Font.HELVETICA, PDType1Font.HELVETICA_BOLD,
|
HELVETICA(new PDType1Font(Standard14Fonts.FontName.HELVETICA), new PDType1Font(HELVETICA_BOLD),
|
||||||
PDType1Font.HELVETICA_OBLIQUE, PDType1Font.HELVETICA_BOLD_OBLIQUE);
|
new PDType1Font(HELVETICA_OBLIQUE), new PDType1Font(HELVETICA_BOLD_OBLIQUE));
|
||||||
|
|
||||||
private final PDFont plainFont;
|
private final PDFont plainFont;
|
||||||
|
|
||||||
|
|
|
@ -2,23 +2,16 @@ package org.xbib.graphics.pdfbox.layout.font;
|
||||||
|
|
||||||
import org.xbib.graphics.pdfbox.layout.element.Document;
|
import org.xbib.graphics.pdfbox.layout.element.Document;
|
||||||
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
public enum Fonts {
|
public enum Fonts {
|
||||||
HELVETICA,
|
HELVETICA,
|
||||||
TIMES,
|
TIMES,
|
||||||
COURIER,
|
COURIER,
|
||||||
NOTOSANS;
|
NOTOSANS;
|
||||||
|
|
||||||
private final Map<String, Font> map = new HashMap<>();
|
|
||||||
|
|
||||||
public Font getFont(Document document) {
|
public Font getFont(Document document) {
|
||||||
return map.computeIfAbsent(name(), name -> {
|
|
||||||
if ("notosans".equalsIgnoreCase(name())) {
|
if ("notosans".equalsIgnoreCase(name())) {
|
||||||
return new NotoSansFont(document);
|
return new NotoSansFont(document);
|
||||||
}
|
}
|
||||||
return BaseFont.valueOf(name());
|
return BaseFont.valueOf(name());
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,6 +5,7 @@ import org.apache.pdfbox.pdmodel.PDPage;
|
||||||
import org.apache.pdfbox.pdmodel.common.PDRectangle;
|
import org.apache.pdfbox.pdmodel.common.PDRectangle;
|
||||||
import org.apache.pdfbox.pdmodel.graphics.color.PDColor;
|
import org.apache.pdfbox.pdmodel.graphics.color.PDColor;
|
||||||
import org.apache.pdfbox.pdmodel.graphics.color.PDDeviceRGB;
|
import org.apache.pdfbox.pdmodel.graphics.color.PDDeviceRGB;
|
||||||
|
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAnnotationHighlight;
|
||||||
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAnnotationTextMarkup;
|
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAnnotationTextMarkup;
|
||||||
import org.junit.jupiter.api.Test;
|
import org.junit.jupiter.api.Test;
|
||||||
import org.xbib.graphics.pdfbox.layout.element.Document;
|
import org.xbib.graphics.pdfbox.layout.element.Document;
|
||||||
|
@ -66,8 +67,7 @@ public class CustomAnnotationTest {
|
||||||
.getAnnotationsOfType(HighlightAnnotation.class);
|
.getAnnotationsOfType(HighlightAnnotation.class);
|
||||||
for (HighlightAnnotation highlightAnnotation : HighlightAnnotations) {
|
for (HighlightAnnotation highlightAnnotation : HighlightAnnotations) {
|
||||||
// use PDF text markup to implement the highlight
|
// use PDF text markup to implement the highlight
|
||||||
PDAnnotationTextMarkup markup = new PDAnnotationTextMarkup(
|
PDAnnotationTextMarkup markup = new PDAnnotationHighlight();
|
||||||
PDAnnotationTextMarkup.SUB_TYPE_HIGHLIGHT);
|
|
||||||
// use the bounding box of the drawn object to position the
|
// use the bounding box of the drawn object to position the
|
||||||
// highlight
|
// highlight
|
||||||
PDRectangle bounds = new PDRectangle();
|
PDRectangle bounds = new PDRectangle();
|
||||||
|
|
|
@ -13,11 +13,11 @@ import java.io.FileOutputStream;
|
||||||
public class HelloNotoFontTest {
|
public class HelloNotoFontTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void test() throws Exception {
|
public void testDocumentOne() throws Exception {
|
||||||
Document document = new Document(PageFormats.A4_PORTRAIT);
|
Document document = new Document(PageFormats.A4_PORTRAIT);
|
||||||
|
Font font = new NotoSansFont(document);
|
||||||
Paragraph paragraph = new Paragraph();
|
Paragraph paragraph = new Paragraph();
|
||||||
paragraph.add(new Indent(32, SpaceUnit.pt));
|
paragraph.add(new Indent(32, SpaceUnit.pt));
|
||||||
Font font = new NotoSansFont(document);
|
|
||||||
paragraph.addMarkup("Hello Noto Regular\n", 12, font);
|
paragraph.addMarkup("Hello Noto Regular\n", 12, font);
|
||||||
paragraph.addMarkup("*Hello Noto Bold*\n", 12, font);
|
paragraph.addMarkup("*Hello Noto Bold*\n", 12, font);
|
||||||
paragraph.addMarkup("_Hello Noto Italic_\n", 12, font);
|
paragraph.addMarkup("_Hello Noto Italic_\n", 12, font);
|
||||||
|
@ -25,6 +25,31 @@ public class HelloNotoFontTest {
|
||||||
paragraph.addText("Hello Unicode Text: Zwrotki dla Dorotki : arcyksiążę fiołków\n", 12, font);
|
paragraph.addText("Hello Unicode Text: Zwrotki dla Dorotki : arcyksiążę fiołków\n", 12, font);
|
||||||
paragraph.addMarkup("Hello Unicode Markup: _Zwrotki dla Dorotki : arcyksiążę fiołków_\n", 12, font);
|
paragraph.addMarkup("Hello Unicode Markup: _Zwrotki dla Dorotki : arcyksiążę fiołków_\n", 12, font);
|
||||||
document.add(paragraph);
|
document.add(paragraph);
|
||||||
|
Paragraph anotherParagraph = new Paragraph();
|
||||||
|
anotherParagraph.add(new Indent(32, SpaceUnit.pt));
|
||||||
|
anotherParagraph.addMarkup("Hello Noto Regular\n", 12, font);
|
||||||
|
document.add(anotherParagraph);
|
||||||
document.render().save(new FileOutputStream("build/hellonotofont.pdf")).close();
|
document.render().save(new FileOutputStream("build/hellonotofont.pdf")).close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testDocumentTwo() throws Exception {
|
||||||
|
Document document = new Document(PageFormats.A4_PORTRAIT);
|
||||||
|
Font font = new NotoSansFont(document);
|
||||||
|
Paragraph paragraph = new Paragraph();
|
||||||
|
paragraph.add(new Indent(32, SpaceUnit.pt));
|
||||||
|
paragraph.addMarkup("Hello Noto Regular 2\n", 12, font);
|
||||||
|
paragraph.addMarkup("*Hello Noto Bold*\n", 12, font);
|
||||||
|
paragraph.addMarkup("_Hello Noto Italic_\n", 12, font);
|
||||||
|
paragraph.addMarkup("*_Hello Noto Bold Italic_*\n", 12, font);
|
||||||
|
paragraph.addText("Hello Unicode Text: Zwrotki dla Dorotki : arcyksiążę fiołków\n", 12, font);
|
||||||
|
paragraph.addMarkup("Hello Unicode Markup: _Zwrotki dla Dorotki : arcyksiążę fiołków_\n", 12, font);
|
||||||
|
document.add(paragraph);
|
||||||
|
Paragraph anotherParagraph = new Paragraph();
|
||||||
|
anotherParagraph.add(new Indent(32, SpaceUnit.pt));
|
||||||
|
anotherParagraph.addMarkup("Hello Noto Regular 2\n", 12, font);
|
||||||
|
document.add(anotherParagraph);
|
||||||
|
document.render().save(new FileOutputStream("build/hellonotofont2.pdf")).close();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,13 +10,27 @@ import java.io.FileOutputStream;
|
||||||
public class ScriptingTest {
|
public class ScriptingTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void script() throws Exception {
|
public void scriptOne() throws Exception {
|
||||||
Settings settings = Settings.settingsBuilder()
|
Settings settings = Settings.settingsBuilder()
|
||||||
.loadFromResource("json", getClass().getResourceAsStream("scripting.json"))
|
.loadFromResource("json", getClass().getResourceAsStream("scripting.json"))
|
||||||
.build();
|
.build();
|
||||||
Engine engine = new Engine();
|
try (Engine engine = new Engine()) {
|
||||||
engine.execute(settings);
|
engine.execute(settings);
|
||||||
Document document = engine.getState().getDocument();
|
Document document = engine.getState().getDocument();
|
||||||
document.render().save(new FileOutputStream("build/scripting.pdf")).close();
|
document.render().save(new FileOutputStream("build/scripting1.pdf")).close();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void scriptTwo() throws Exception {
|
||||||
|
Settings settings = Settings.settingsBuilder()
|
||||||
|
.loadFromResource("json", getClass().getResourceAsStream("scripting.json"))
|
||||||
|
.build();
|
||||||
|
try (Engine engine = new Engine()) {
|
||||||
|
engine.execute(settings);
|
||||||
|
Document document = engine.getState().getDocument();
|
||||||
|
document.render().save(new FileOutputStream("build/scripting2.pdf")).close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -108,7 +108,7 @@
|
||||||
"elements": [
|
"elements": [
|
||||||
{
|
{
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"value": "Hello World 5",
|
"value": "Hello World 5 Zwrotki dla Dorotki : arcyksiążę fiołków",
|
||||||
"fontsize": 20,
|
"fontsize": 20,
|
||||||
"font": "notosans"
|
"font": "notosans"
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
package org.xbib.graphics.pdfbox.print;
|
package org.xbib.graphics.pdfbox.print;
|
||||||
|
|
||||||
import org.apache.pdfbox.io.MemoryUsageSetting;
|
import org.apache.pdfbox.Loader;
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
import org.apache.pdfbox.printing.PDFPageable;
|
import org.apache.pdfbox.printing.PDFPageable;
|
||||||
|
|
||||||
|
@ -86,7 +86,8 @@ public class PrintUtility {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void print(InputStream inputStream, Printer printer) throws Exception {
|
public static void print(InputStream inputStream, Printer printer) throws Exception {
|
||||||
PDDocument document = PDDocument.load(inputStream, MemoryUsageSetting.setupTempFileOnly());
|
byte[] bytes = inputStream.readAllBytes();
|
||||||
|
PDDocument document = Loader.loadPDF(bytes);
|
||||||
PrinterJob job = PrinterJob.getPrinterJob();
|
PrinterJob job = PrinterJob.getPrinterJob();
|
||||||
job.setPageable(new PDFPageable(document));
|
job.setPageable(new PDFPageable(document));
|
||||||
job.setPrintService(printer.getService());
|
job.setPrintService(printer.getService());
|
||||||
|
|
|
@ -251,15 +251,14 @@ public class PdfBoxGraphics2D extends Graphics2D {
|
||||||
PDRectangle bbox,
|
PDRectangle bbox,
|
||||||
PdfBoxGraphics2D parentGfx)
|
PdfBoxGraphics2D parentGfx)
|
||||||
throws IOException {
|
throws IOException {
|
||||||
this(document, createXObject(document, bbox), parentGfx);
|
this(document, createAppearanceStream(document, bbox), parentGfx);
|
||||||
}
|
}
|
||||||
|
|
||||||
public PdfBoxGraphics2D(PDDocument document,
|
public PdfBoxGraphics2D(PDDocument document,
|
||||||
PDFormXObject xFormObject,
|
PDAppearanceStream pdAppearanceStream,
|
||||||
PdfBoxGraphics2D parentGfx)
|
PdfBoxGraphics2D parentGfx)
|
||||||
throws IOException {
|
throws IOException {
|
||||||
this(document, xFormObject, new PDPageContentStream(document, xFormObject,
|
this(document, pdAppearanceStream, new PDPageContentStream(document, pdAppearanceStream, pdAppearanceStream.getStream().createOutputStream(COSName.FLATE_DECODE)), parentGfx);
|
||||||
xFormObject.getStream().createOutputStream(COSName.FLATE_DECODE)), parentGfx);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public PdfBoxGraphics2D(PDDocument document,
|
public PdfBoxGraphics2D(PDDocument document,
|
||||||
|
@ -1152,17 +1151,17 @@ public class PdfBoxGraphics2D extends Graphics2D {
|
||||||
}
|
}
|
||||||
|
|
||||||
private void checkNoCopyActive() {
|
private void checkNoCopyActive() {
|
||||||
if (copyList.size() > 0) {
|
if (!copyList.isEmpty()) {
|
||||||
throw new IllegalStateException("Don't use the main context as long as a copy is active! Child context is missing a .dispose() call\n"
|
throw new IllegalStateException("Don't use the main context as long as a copy is active! Child context is missing a .dispose() call\n"
|
||||||
+ gatherDebugCopyInfo(this));
|
+ gatherDebugCopyInfo(this));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static PDFormXObject createXObject(PDDocument document, PDRectangle bbox) {
|
private static PDAppearanceStream createAppearanceStream(PDDocument document, PDRectangle bbox) {
|
||||||
PDFormXObject xFormObject = new PDAppearanceStream(document);
|
PDAppearanceStream appearanceStream = new PDAppearanceStream(document);
|
||||||
xFormObject.setResources(new PDResources());
|
appearanceStream.setResources(new PDResources());
|
||||||
xFormObject.setBBox(bbox);
|
appearanceStream.setBBox(bbox);
|
||||||
return xFormObject;
|
return appearanceStream;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static String gatherDebugCopyInfo(PdfBoxGraphics2D gfx) {
|
private static String gatherDebugCopyInfo(PdfBoxGraphics2D gfx) {
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
package org.xbib.graphics.pdfbox.font;
|
package org.xbib.graphics.pdfbox.font;
|
||||||
|
|
||||||
import org.apache.fontbox.ttf.TrueTypeCollection;
|
import org.apache.fontbox.ttf.TrueTypeCollection;
|
||||||
import org.apache.pdfbox.io.IOUtils;
|
|
||||||
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
||||||
import org.apache.pdfbox.pdmodel.font.PDFont;
|
import org.apache.pdfbox.pdmodel.font.PDFont;
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType0Font;
|
import org.apache.pdfbox.pdmodel.font.PDType0Font;
|
||||||
|
@ -28,6 +27,21 @@ import java.util.Map;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.SYMBOL;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ROMAN;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.ZAPF_DINGBATS;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Default implementation to draw fonts. You can reuse instances of this class
|
* Default implementation to draw fonts. You can reuse instances of this class
|
||||||
* within a PDDocument for more then one {@link PdfBoxGraphics2D}.
|
* within a PDDocument for more then one {@link PdfBoxGraphics2D}.
|
||||||
|
@ -72,7 +86,7 @@ public class DefaultFontDrawer implements FontDrawer, Closeable {
|
||||||
public void registerFont(String fontName, InputStream fontStream) throws IOException {
|
public void registerFont(String fontName, InputStream fontStream) throws IOException {
|
||||||
File fontFile = File.createTempFile("pdfboxgfx2dfont", ".ttf");
|
File fontFile = File.createTempFile("pdfboxgfx2dfont", ".ttf");
|
||||||
try (FileOutputStream out = new FileOutputStream(fontFile)) {
|
try (FileOutputStream out = new FileOutputStream(fontFile)) {
|
||||||
IOUtils.copy(fontStream, out);
|
fontStream.transferTo(out);
|
||||||
}
|
}
|
||||||
fontFile.deleteOnExit();
|
fontFile.deleteOnExit();
|
||||||
tempFiles.add(fontFile);
|
tempFiles.add(fontFile);
|
||||||
|
@ -412,10 +426,10 @@ public class DefaultFontDrawer implements FontDrawer, Closeable {
|
||||||
return chooseMatchingTimes(font);
|
return chooseMatchingTimes(font);
|
||||||
}
|
}
|
||||||
if (fontNameEqualsAnyOf(font, "Symbol")) {
|
if (fontNameEqualsAnyOf(font, "Symbol")) {
|
||||||
return PDType1Font.SYMBOL;
|
return new PDType1Font(SYMBOL);
|
||||||
}
|
}
|
||||||
if (fontNameEqualsAnyOf(font, "ZapfDingbats", "Dingbats")) {
|
if (fontNameEqualsAnyOf(font, "ZapfDingbats", "Dingbats")) {
|
||||||
return PDType1Font.ZAPF_DINGBATS;
|
return new PDType1Font(ZAPF_DINGBATS);
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
@ -429,18 +443,17 @@ public class DefaultFontDrawer implements FontDrawer, Closeable {
|
||||||
*/
|
*/
|
||||||
public static PDFont chooseMatchingHelvetica(Font font) {
|
public static PDFont chooseMatchingHelvetica(Font font) {
|
||||||
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
||||||
return PDType1Font.HELVETICA_BOLD_OBLIQUE;
|
return new PDType1Font(HELVETICA_BOLD_OBLIQUE);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
||||||
return PDType1Font.HELVETICA_OBLIQUE;
|
return new PDType1Font(HELVETICA_OBLIQUE);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
||||||
return PDType1Font.HELVETICA_BOLD;
|
return new PDType1Font(HELVETICA_BOLD);
|
||||||
}
|
}
|
||||||
return PDType1Font.HELVETICA;
|
return new PDType1Font(HELVETICA);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a PDType1Font.COURIER-variant, which matches the given font
|
* Get a PDType1Font.COURIER-variant, which matches the given font
|
||||||
*
|
*
|
||||||
|
@ -450,15 +463,15 @@ public class DefaultFontDrawer implements FontDrawer, Closeable {
|
||||||
*/
|
*/
|
||||||
public static PDFont chooseMatchingCourier(Font font) {
|
public static PDFont chooseMatchingCourier(Font font) {
|
||||||
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
||||||
return PDType1Font.COURIER_BOLD_OBLIQUE;
|
return new PDType1Font(COURIER_BOLD_OBLIQUE);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
||||||
return PDType1Font.COURIER_OBLIQUE;
|
return new PDType1Font(COURIER_OBLIQUE);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
||||||
return PDType1Font.COURIER_BOLD;
|
return new PDType1Font(COURIER_BOLD);
|
||||||
}
|
}
|
||||||
return PDType1Font.COURIER;
|
return new PDType1Font(COURIER);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -470,15 +483,15 @@ public class DefaultFontDrawer implements FontDrawer, Closeable {
|
||||||
*/
|
*/
|
||||||
public static PDFont chooseMatchingTimes(Font font) {
|
public static PDFont chooseMatchingTimes(Font font) {
|
||||||
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
if ((font.getStyle() & (Font.ITALIC | Font.BOLD)) == (Font.ITALIC | Font.BOLD)) {
|
||||||
return PDType1Font.TIMES_BOLD_ITALIC;
|
return new PDType1Font(TIMES_BOLD_ITALIC);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
if ((font.getStyle() & Font.ITALIC) == Font.ITALIC) {
|
||||||
return PDType1Font.TIMES_ITALIC;
|
return new PDType1Font(TIMES_ITALIC);
|
||||||
}
|
}
|
||||||
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
if ((font.getStyle() & Font.BOLD) == Font.BOLD) {
|
||||||
return PDType1Font.TIMES_BOLD;
|
return new PDType1Font(TIMES_BOLD);
|
||||||
}
|
}
|
||||||
return PDType1Font.TIMES_ROMAN;
|
return new PDType1Font(TIMES_ROMAN);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean fontNameEqualsAnyOf(Font font, String... names) {
|
public static boolean fontNameEqualsAnyOf(Font font, String... names) {
|
||||||
|
|
|
@ -7,7 +7,6 @@ import org.apache.pdfbox.cos.COSDictionary;
|
||||||
import org.apache.pdfbox.cos.COSFloat;
|
import org.apache.pdfbox.cos.COSFloat;
|
||||||
import org.apache.pdfbox.cos.COSName;
|
import org.apache.pdfbox.cos.COSName;
|
||||||
import org.apache.pdfbox.cos.COSStream;
|
import org.apache.pdfbox.cos.COSStream;
|
||||||
import org.apache.pdfbox.multipdf.PDFCloneUtility;
|
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
||||||
import org.apache.pdfbox.pdmodel.PDResources;
|
import org.apache.pdfbox.pdmodel.PDResources;
|
||||||
|
|
|
@ -0,0 +1,201 @@
|
||||||
|
/*
|
||||||
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||||
|
* contributor license agreements. See the NOTICE file distributed with
|
||||||
|
* this work for additional information regarding copyright ownership.
|
||||||
|
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||||
|
* (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.xbib.graphics.pdfbox.paint;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import org.apache.pdfbox.cos.COSArray;
|
||||||
|
import org.apache.pdfbox.cos.COSBase;
|
||||||
|
import org.apache.pdfbox.cos.COSDictionary;
|
||||||
|
import org.apache.pdfbox.cos.COSName;
|
||||||
|
import org.apache.pdfbox.cos.COSObject;
|
||||||
|
import org.apache.pdfbox.cos.COSStream;
|
||||||
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
|
import org.apache.pdfbox.pdmodel.common.COSObjectable;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Copied from org.apache.pdfbox.multipdf.util
|
||||||
|
*/
|
||||||
|
public class PDFCloneUtility {
|
||||||
|
|
||||||
|
private final PDDocument destination;
|
||||||
|
private final Map<COSBase, COSBase> clonedVersion = new HashMap<>();
|
||||||
|
private final Set<COSBase> clonedValues = new HashSet<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a new instance for the given target document.
|
||||||
|
*
|
||||||
|
* @param dest the destination PDF document that will receive the clones
|
||||||
|
*/
|
||||||
|
PDFCloneUtility(PDDocument dest) {
|
||||||
|
this.destination = dest;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the destination PDF document this cloner instance is set up for.
|
||||||
|
*
|
||||||
|
* @return the destination PDF document
|
||||||
|
*/
|
||||||
|
PDDocument getDestination() {
|
||||||
|
return this.destination;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Deep-clones the given object for inclusion into a different PDF document identified by the destination parameter.
|
||||||
|
* <p>
|
||||||
|
* Expert use only, don’t use it if you don’t know exactly what you are doing.
|
||||||
|
*
|
||||||
|
* @param base the initial object as the root of the deep-clone operation
|
||||||
|
* @return the cloned instance of the base object
|
||||||
|
* @throws IOException if an I/O error occurs
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
public <TCOSBase extends COSBase> TCOSBase cloneForNewDocument(TCOSBase base) throws IOException {
|
||||||
|
if (base == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
COSBase retval = clonedVersion.get(base);
|
||||||
|
if (retval != null) {
|
||||||
|
// we are done, it has already been converted.
|
||||||
|
return (TCOSBase) retval;
|
||||||
|
}
|
||||||
|
if (clonedValues.contains(base)) {
|
||||||
|
// Don't clone a clone
|
||||||
|
return base;
|
||||||
|
}
|
||||||
|
retval = cloneCOSBaseForNewDocument(base);
|
||||||
|
clonedVersion.put(base, retval);
|
||||||
|
clonedValues.add(retval);
|
||||||
|
return (TCOSBase) retval;
|
||||||
|
}
|
||||||
|
|
||||||
|
COSBase cloneCOSBaseForNewDocument(COSBase base) throws IOException {
|
||||||
|
if (base instanceof COSObject) {
|
||||||
|
return cloneForNewDocument(((COSObject) base).getObject());
|
||||||
|
}
|
||||||
|
if (base instanceof COSArray) {
|
||||||
|
return cloneCOSArray((COSArray) base);
|
||||||
|
}
|
||||||
|
if (base instanceof COSStream) {
|
||||||
|
return cloneCOSStream((COSStream) base);
|
||||||
|
}
|
||||||
|
if (base instanceof COSDictionary) {
|
||||||
|
return cloneCOSDictionary((COSDictionary) base);
|
||||||
|
}
|
||||||
|
return base;
|
||||||
|
}
|
||||||
|
|
||||||
|
private COSArray cloneCOSArray(COSArray array) throws IOException {
|
||||||
|
COSArray newArray = new COSArray();
|
||||||
|
for (int i = 0; i < array.size(); i++) {
|
||||||
|
COSBase value = array.get(i);
|
||||||
|
if (hasSelfReference(array, value)) {
|
||||||
|
newArray.add(newArray);
|
||||||
|
} else {
|
||||||
|
newArray.add(cloneForNewDocument(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return newArray;
|
||||||
|
}
|
||||||
|
|
||||||
|
private COSStream cloneCOSStream(COSStream stream) throws IOException {
|
||||||
|
COSStream newStream = destination.getDocument().createCOSStream();
|
||||||
|
try (OutputStream output = newStream.createRawOutputStream();
|
||||||
|
InputStream input = stream.createRawInputStream()) {
|
||||||
|
input.transferTo(output);
|
||||||
|
}
|
||||||
|
clonedVersion.put(stream, newStream);
|
||||||
|
for (Map.Entry<COSName, COSBase> entry : stream.entrySet()) {
|
||||||
|
COSBase value = entry.getValue();
|
||||||
|
if (hasSelfReference(stream, value)) {
|
||||||
|
newStream.setItem(entry.getKey(), newStream);
|
||||||
|
} else {
|
||||||
|
newStream.setItem(entry.getKey(), cloneForNewDocument(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return newStream;
|
||||||
|
}
|
||||||
|
|
||||||
|
private COSDictionary cloneCOSDictionary(COSDictionary dictionary) throws IOException {
|
||||||
|
COSDictionary newDictionary = new COSDictionary();
|
||||||
|
clonedVersion.put(dictionary, newDictionary);
|
||||||
|
for (Map.Entry<COSName, COSBase> entry : dictionary.entrySet()) {
|
||||||
|
COSBase value = entry.getValue();
|
||||||
|
if (hasSelfReference(dictionary, value)) {
|
||||||
|
newDictionary.setItem(entry.getKey(), newDictionary);
|
||||||
|
} else {
|
||||||
|
newDictionary.setItem(entry.getKey(), cloneForNewDocument(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return newDictionary;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Merges two objects of the same type by deep-cloning its members. <br>
|
||||||
|
* Base and target must be instances of the same class.
|
||||||
|
*
|
||||||
|
* @param base the base object to be cloned
|
||||||
|
* @param target the merge target
|
||||||
|
* @throws IOException if an I/O error occurs
|
||||||
|
*/
|
||||||
|
void cloneMerge(final COSObjectable base, COSObjectable target) throws IOException {
|
||||||
|
if (base == null || base == target) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
cloneMergeCOSBase(base.getCOSObject(), target.getCOSObject());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void cloneMergeCOSBase(final COSBase source, final COSBase target) throws IOException {
|
||||||
|
COSBase sourceBase = source instanceof COSObject ? ((COSObject) source).getObject() : source;
|
||||||
|
COSBase targetBase = target instanceof COSObject ? ((COSObject) target).getObject() : target;
|
||||||
|
if (sourceBase instanceof COSArray array && targetBase instanceof COSArray) {
|
||||||
|
for (int i = 0; i < array.size(); i++) {
|
||||||
|
((COSArray) targetBase).add(cloneForNewDocument(array.get(i)));
|
||||||
|
}
|
||||||
|
} else if (sourceBase instanceof COSDictionary sourceDict && targetBase instanceof COSDictionary targetDict) {
|
||||||
|
for (Map.Entry<COSName, COSBase> entry : sourceDict.entrySet()) {
|
||||||
|
COSName key = entry.getKey();
|
||||||
|
COSBase value = entry.getValue();
|
||||||
|
if (targetDict.getItem(key) != null) {
|
||||||
|
cloneMerge(value, targetDict.getItem(key));
|
||||||
|
} else {
|
||||||
|
targetDict.setItem(key, cloneForNewDocument(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check whether an element (of an array or a dictionary) points to its parent.
|
||||||
|
*
|
||||||
|
* @param parent COSArray or COSDictionary
|
||||||
|
* @param value an element
|
||||||
|
*/
|
||||||
|
private boolean hasSelfReference(COSBase parent, COSBase value) {
|
||||||
|
if (value instanceof COSObject) {
|
||||||
|
COSBase actual = ((COSObject) value).getObject();
|
||||||
|
return actual == parent;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,12 +1,25 @@
|
||||||
package org.xbib.graphics.pdfbox.test;
|
package org.xbib.graphics.pdfbox.test;
|
||||||
|
|
||||||
import org.apache.pdfbox.pdmodel.font.PDType1Font;
|
import org.apache.pdfbox.pdmodel.font.PDType1Font;
|
||||||
import org.junit.jupiter.api.Assertions;
|
|
||||||
import org.junit.jupiter.api.Test;
|
import org.junit.jupiter.api.Test;
|
||||||
import org.xbib.graphics.pdfbox.font.CoreFontDrawer;
|
import org.xbib.graphics.pdfbox.font.CoreFontDrawer;
|
||||||
|
|
||||||
import java.awt.Font;
|
import java.awt.Font;
|
||||||
|
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.COURIER_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_OBLIQUE;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.SYMBOL;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_BOLD_ITALIC;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.TIMES_ROMAN;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.ZAPF_DINGBATS;
|
||||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
import static org.junit.jupiter.api.Assertions.assertNull;
|
import static org.junit.jupiter.api.Assertions.assertNull;
|
||||||
|
|
||||||
|
@ -19,51 +32,29 @@ public class FontDrawerTest {
|
||||||
Font anyFontItalic = anyFont.deriveFont(Font.ITALIC);
|
Font anyFontItalic = anyFont.deriveFont(Font.ITALIC);
|
||||||
Font anyFontBoldItalic = anyFont.deriveFont(Font.BOLD | Font.ITALIC);
|
Font anyFontBoldItalic = anyFont.deriveFont(Font.BOLD | Font.ITALIC);
|
||||||
|
|
||||||
Assertions.assertEquals(PDType1Font.COURIER,
|
assertEquals(new PDType1Font(COURIER).getName(), CoreFontDrawer.chooseMatchingCourier(anyFont).getName());
|
||||||
CoreFontDrawer.chooseMatchingCourier(anyFont));
|
assertEquals(new PDType1Font(COURIER_BOLD).getName(), CoreFontDrawer.chooseMatchingCourier(anyFontBold).getName());
|
||||||
assertEquals(PDType1Font.COURIER_BOLD,
|
assertEquals(new PDType1Font(COURIER_OBLIQUE).getName(), CoreFontDrawer.chooseMatchingCourier(anyFontItalic).getName());
|
||||||
CoreFontDrawer.chooseMatchingCourier(anyFontBold));
|
assertEquals(new PDType1Font(COURIER_BOLD_OBLIQUE).getName(), CoreFontDrawer.chooseMatchingCourier(anyFontBoldItalic).getName());
|
||||||
assertEquals(PDType1Font.COURIER_OBLIQUE,
|
assertEquals(new PDType1Font(HELVETICA).getName(), CoreFontDrawer.chooseMatchingHelvetica(anyFont).getName());
|
||||||
CoreFontDrawer.chooseMatchingCourier(anyFontItalic));
|
assertEquals(new PDType1Font(HELVETICA_BOLD).getName(), CoreFontDrawer.chooseMatchingHelvetica(anyFontBold).getName());
|
||||||
assertEquals(PDType1Font.COURIER_BOLD_OBLIQUE,
|
assertEquals(new PDType1Font(HELVETICA_OBLIQUE).getName(), CoreFontDrawer.chooseMatchingHelvetica(anyFontItalic).getName());
|
||||||
CoreFontDrawer.chooseMatchingCourier(anyFontBoldItalic));
|
assertEquals(new PDType1Font(HELVETICA_BOLD_OBLIQUE).getName(), CoreFontDrawer.chooseMatchingHelvetica(anyFontBoldItalic).getName());
|
||||||
|
assertEquals(new PDType1Font(TIMES_ROMAN).getName(), CoreFontDrawer.chooseMatchingTimes(anyFont).getName());
|
||||||
assertEquals(PDType1Font.HELVETICA,
|
assertEquals(new PDType1Font(TIMES_BOLD).getName(), CoreFontDrawer.chooseMatchingTimes(anyFontBold).getName());
|
||||||
CoreFontDrawer.chooseMatchingHelvetica(anyFont));
|
assertEquals(new PDType1Font(TIMES_ITALIC).getName(), CoreFontDrawer.chooseMatchingTimes(anyFontItalic).getName());
|
||||||
assertEquals(PDType1Font.HELVETICA_BOLD,
|
assertEquals(new PDType1Font(TIMES_BOLD_ITALIC).getName(), CoreFontDrawer.chooseMatchingTimes(anyFontBoldItalic).getName());
|
||||||
CoreFontDrawer.chooseMatchingHelvetica(anyFontBold));
|
|
||||||
assertEquals(PDType1Font.HELVETICA_OBLIQUE,
|
|
||||||
CoreFontDrawer.chooseMatchingHelvetica(anyFontItalic));
|
|
||||||
assertEquals(PDType1Font.HELVETICA_BOLD_OBLIQUE,
|
|
||||||
CoreFontDrawer.chooseMatchingHelvetica(anyFontBoldItalic));
|
|
||||||
|
|
||||||
assertEquals(PDType1Font.TIMES_ROMAN,
|
|
||||||
CoreFontDrawer.chooseMatchingTimes(anyFont));
|
|
||||||
assertEquals(PDType1Font.TIMES_BOLD,
|
|
||||||
CoreFontDrawer.chooseMatchingTimes(anyFontBold));
|
|
||||||
assertEquals(PDType1Font.TIMES_ITALIC,
|
|
||||||
CoreFontDrawer.chooseMatchingTimes(anyFontItalic));
|
|
||||||
assertEquals(PDType1Font.TIMES_BOLD_ITALIC,
|
|
||||||
CoreFontDrawer.chooseMatchingTimes(anyFontBoldItalic));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testDefaultFontMapping() {
|
public void testDefaultFontMapping() {
|
||||||
assertEquals(PDType1Font.HELVETICA,
|
assertEquals(new PDType1Font(HELVETICA).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode(Font.DIALOG)).getName());
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode(Font.DIALOG)));
|
assertEquals(new PDType1Font(HELVETICA).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode(Font.DIALOG_INPUT)).getName());
|
||||||
assertEquals(PDType1Font.HELVETICA,
|
assertEquals(new PDType1Font(HELVETICA).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode("Arial")).getName());
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode(Font.DIALOG_INPUT)));
|
assertEquals(new PDType1Font(COURIER).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode(Font.MONOSPACED)).getName());
|
||||||
assertEquals(PDType1Font.HELVETICA,
|
assertEquals(new PDType1Font(TIMES_ROMAN).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode(Font.SERIF)).getName());
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode("Arial")));
|
assertEquals(new PDType1Font(ZAPF_DINGBATS).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode("Dingbats")).getName());
|
||||||
assertEquals(PDType1Font.COURIER,
|
assertEquals(new PDType1Font(SYMBOL).getName(), CoreFontDrawer.mapToCoreFonts(Font.decode("Symbol")).getName());
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode(Font.MONOSPACED)));
|
|
||||||
assertEquals(PDType1Font.TIMES_ROMAN,
|
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode(Font.SERIF)));
|
|
||||||
assertEquals(PDType1Font.ZAPF_DINGBATS,
|
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode("Dingbats")));
|
|
||||||
assertEquals(PDType1Font.SYMBOL,
|
|
||||||
CoreFontDrawer.mapToCoreFonts(Font.decode("Symbol")));
|
|
||||||
assertNull(CoreFontDrawer.mapToCoreFonts(Font.decode("Georgia")));
|
assertNull(CoreFontDrawer.mapToCoreFonts(Font.decode("Georgia")));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,9 @@ import java.awt.image.BufferedImage;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA;
|
||||||
|
import static org.apache.pdfbox.pdmodel.font.Standard14Fonts.FontName.HELVETICA_BOLD;
|
||||||
|
|
||||||
class PdfBoxGraphics2DTestBase {
|
class PdfBoxGraphics2DTestBase {
|
||||||
|
|
||||||
enum Mode {
|
enum Mode {
|
||||||
|
@ -29,7 +32,7 @@ class PdfBoxGraphics2DTestBase {
|
||||||
void exportGraphic(String dir, String name, GraphicsExporter exporter) {
|
void exportGraphic(String dir, String name, GraphicsExporter exporter) {
|
||||||
try {
|
try {
|
||||||
PDDocument document = new PDDocument();
|
PDDocument document = new PDDocument();
|
||||||
PDFont helvetica = PDType1Font.HELVETICA;
|
PDFont helvetica = new PDType1Font(HELVETICA);
|
||||||
File parentDir = new File("build/test/" + dir);
|
File parentDir = new File("build/test/" + dir);
|
||||||
parentDir.mkdirs();
|
parentDir.mkdirs();
|
||||||
BufferedImage image = new BufferedImage(400, 400, BufferedImage.TYPE_4BYTE_ABGR);
|
BufferedImage image = new BufferedImage(400, 400, BufferedImage.TYPE_4BYTE_ABGR);
|
||||||
|
@ -45,7 +48,7 @@ class PdfBoxGraphics2DTestBase {
|
||||||
contentStream.beginText();
|
contentStream.beginText();
|
||||||
contentStream.setStrokingColor(0f, 0f, 0f);
|
contentStream.setStrokingColor(0f, 0f, 0f);
|
||||||
contentStream.setNonStrokingColor(0f, 0f, 0f);
|
contentStream.setNonStrokingColor(0f, 0f, 0f);
|
||||||
contentStream.setFont(PDType1Font.HELVETICA_BOLD, 15);
|
contentStream.setFont(new PDType1Font(HELVETICA_BOLD), 15);
|
||||||
contentStream.setTextMatrix(Matrix.getTranslateInstance(10, 800));
|
contentStream.setTextMatrix(Matrix.getTranslateInstance(10, 800));
|
||||||
contentStream.showText("Mode " + m);
|
contentStream.showText("Mode " + m);
|
||||||
contentStream.endText();
|
contentStream.endText();
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package org.xbib.graphics.pdfbox.test;
|
package org.xbib.graphics.pdfbox.test;
|
||||||
|
|
||||||
|
import org.apache.pdfbox.Loader;
|
||||||
import org.apache.pdfbox.pdmodel.PDDocument;
|
import org.apache.pdfbox.pdmodel.PDDocument;
|
||||||
import org.apache.pdfbox.pdmodel.PDPage;
|
import org.apache.pdfbox.pdmodel.PDPage;
|
||||||
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
import org.apache.pdfbox.pdmodel.PDPageContentStream;
|
||||||
|
@ -29,6 +30,7 @@ import java.awt.Stroke;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
|
||||||
public class PdfRerenderTest {
|
public class PdfRerenderTest {
|
||||||
|
|
||||||
|
@ -55,7 +57,9 @@ public class PdfRerenderTest {
|
||||||
File parentDir = new File("build/test");
|
File parentDir = new File("build/test");
|
||||||
parentDir.mkdirs();
|
parentDir.mkdirs();
|
||||||
PDDocument document = new PDDocument();
|
PDDocument document = new PDDocument();
|
||||||
PDDocument sourceDoc = PDDocument.load(PdfRerenderTest.class.getResourceAsStream(name));
|
InputStream inputStream = PdfRerenderTest.class.getResourceAsStream(name);
|
||||||
|
byte[] bytes = inputStream.readAllBytes();
|
||||||
|
PDDocument sourceDoc = Loader.loadPDF(bytes);
|
||||||
|
|
||||||
for (PDPage sourcePage : sourceDoc.getPages()) {
|
for (PDPage sourcePage : sourceDoc.getPages()) {
|
||||||
PDRectangle mediaBox = sourcePage.getMediaBox();
|
PDRectangle mediaBox = sourcePage.getMediaBox();
|
||||||
|
@ -87,7 +91,9 @@ public class PdfRerenderTest {
|
||||||
parentDir.mkdirs();
|
parentDir.mkdirs();
|
||||||
|
|
||||||
PDDocument document = new PDDocument();
|
PDDocument document = new PDDocument();
|
||||||
PDDocument sourceDoc = PDDocument.load(PdfRerenderTest.class.getResourceAsStream(name));
|
InputStream inputStream = PdfRerenderTest.class.getResourceAsStream(name);
|
||||||
|
byte[] bytes = inputStream.readAllBytes();
|
||||||
|
PDDocument sourceDoc = Loader.loadPDF(bytes);
|
||||||
|
|
||||||
for (PDPage sourcePage : sourceDoc.getPages()) {
|
for (PDPage sourcePage : sourceDoc.getPages()) {
|
||||||
PDPage rerenderedPage = new PDPage(sourcePage.getMediaBox());
|
PDPage rerenderedPage = new PDPage(sourcePage.getMediaBox());
|
||||||
|
@ -113,7 +119,9 @@ public class PdfRerenderTest {
|
||||||
parentDir.mkdirs();
|
parentDir.mkdirs();
|
||||||
|
|
||||||
PDDocument document = new PDDocument();
|
PDDocument document = new PDDocument();
|
||||||
PDDocument sourceDoc = PDDocument.load(PdfRerenderTest.class.getResourceAsStream(name));
|
InputStream inputStream = PdfRerenderTest.class.getResourceAsStream(name);
|
||||||
|
byte[] bytes = inputStream.readAllBytes();
|
||||||
|
PDDocument sourceDoc = Loader.loadPDF(bytes);
|
||||||
|
|
||||||
for (PDPage sourcePage : sourceDoc.getPages()) {
|
for (PDPage sourcePage : sourceDoc.getPages()) {
|
||||||
PDPage rerenderedPage = new PDPage(sourcePage.getMediaBox());
|
PDPage rerenderedPage = new PDPage(sourcePage.getMediaBox());
|
||||||
|
|
|
@ -39,7 +39,7 @@ dependencyResolutionManagement {
|
||||||
library('bytebuddy', 'net.bytebuddy', 'byte-buddy').version('1.14.4')
|
library('bytebuddy', 'net.bytebuddy', 'byte-buddy').version('1.14.4')
|
||||||
library('objenesis', 'org.objenesis', 'objenesis').version('2.6')
|
library('objenesis', 'org.objenesis', 'objenesis').version('2.6')
|
||||||
library('jna', 'net.java.dev.jna', 'jna').version('5.13.0')
|
library('jna', 'net.java.dev.jna', 'jna').version('5.13.0')
|
||||||
library('pdfbox', 'org.apache.pdfbox', 'pdfbox').version('2.0.28')
|
library('pdfbox', 'org.apache.pdfbox', 'pdfbox').version('3.0.0-beta1')
|
||||||
library('zxing', 'com.google.zxing', 'javase').version('3.4.1')
|
library('zxing', 'com.google.zxing', 'javase').version('3.4.1')
|
||||||
library('reflections', 'org.reflections', 'reflections').version('0.9.11')
|
library('reflections', 'org.reflections', 'reflections').version('0.9.11')
|
||||||
library('jfreechart', 'org.jfree', 'jfreechart').version('1.5.2')
|
library('jfreechart', 'org.jfree', 'jfreechart').version('1.5.2')
|
||||||
|
|
Loading…
Reference in a new issue