From 21682bdca71d422e03b4452fa841b6b542d0c22f Mon Sep 17 00:00:00 2001 From: Luis Bernardo Date: Wed, 14 Aug 2013 22:35:37 +0000 Subject: [PATCH] FOP-2252: OpenType CFF support for FOP; patch submitted by Robert Meyer git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/trunk@1514076 13f79535-47bb-0310-9956-ffa450edef68 --- findbugs-exclude.xml | 219 +- lib/fontbox-1.8.0-SNAPSHOT.jar | Bin 0 -> 207498 bytes lib/xmlgraphics-commons-svn-trunk.jar | Bin 629283 -> 629507 bytes .../OTFAdvancedTypographicTableReader.java | 85 +- src/java/org/apache/fop/fonts/FontLoader.java | 4 +- .../org/apache/fop/fonts/MultiByteFont.java | 69 +- .../org/apache/fop/fonts/SingleByteFont.java | 2 +- .../org/apache/fop/fonts/apps/TTFReader.java | 4 +- .../fop/fonts/autodetect/FontInfoFinder.java | 4 +- .../apache/fop/fonts/truetype/GlyfTable.java | 4 +- ...TTFDirTabEntry.java => OFDirTabEntry.java} | 6 +- .../{TTFFontLoader.java => OFFontLoader.java} | 121 +- .../{TTFMtxEntry.java => OFMtxEntry.java} | 2 +- .../{TTFTableName.java => OFTableName.java} | 76 +- .../apache/fop/fonts/truetype/OTFFile.java | 109 + .../fop/fonts/truetype/OTFSubSetFile.java | 1092 +++++++++ .../apache/fop/fonts/truetype/OpenFont.java | 1937 ++++++++++++++++ .../apache/fop/fonts/truetype/TTFFile.java | 2011 +---------------- .../fop/fonts/truetype/TTFSubSetFile.java | 106 +- .../apache/fop/pdf/PDFCFFStreamType0C.java | 74 + .../org/apache/fop/pdf/PDFEncryptionJCE.java | 99 +- src/java/org/apache/fop/pdf/PDFFactory.java | 57 +- .../org/apache/fop/pdf/PDFFontDescriptor.java | 2 + .../org/apache/fop/render/ps/PSFontUtils.java | 183 +- .../org/apache/fop/render/ps/PSPainter.java | 49 +- .../fop/fonts/cff/CFFDataReaderTestCase.java | 154 ++ .../fop/fonts/truetype/GlyfTableTestCase.java | 7 +- .../fop/fonts/truetype/OTFFileTestCase.java | 86 + .../fonts/truetype/OTFSubSetFileTestCase.java | 148 ++ .../fop/fonts/truetype/TTFFileTestCase.java | 14 +- .../fonts/truetype/TTFFontLoaderTestCase.java | 6 +- .../fonts/truetype/TTFSubSetFileTestCase.java | 7 +- .../fonts/truetype/TTFTableNameTestCase.java | 126 +- test/resources/fonts/otf/AlexBrushRegular.otf | Bin 0 -> 39796 bytes .../resources/fonts/otf/SourceSansProBold.otf | Bin 0 -> 104072 bytes 35 files changed, 4554 insertions(+), 2309 deletions(-) create mode 100644 lib/fontbox-1.8.0-SNAPSHOT.jar rename src/java/org/apache/fop/fonts/truetype/{TTFDirTabEntry.java => OFDirTabEntry.java} (96%) rename src/java/org/apache/fop/fonts/truetype/{TTFFontLoader.java => OFFontLoader.java} (66%) rename src/java/org/apache/fop/fonts/truetype/{TTFMtxEntry.java => OFMtxEntry.java} (99%) rename src/java/org/apache/fop/fonts/truetype/{TTFTableName.java => OFTableName.java} (56%) create mode 100644 src/java/org/apache/fop/fonts/truetype/OTFFile.java create mode 100644 src/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java create mode 100644 src/java/org/apache/fop/fonts/truetype/OpenFont.java create mode 100644 src/java/org/apache/fop/pdf/PDFCFFStreamType0C.java create mode 100644 test/java/org/apache/fop/fonts/cff/CFFDataReaderTestCase.java create mode 100644 test/java/org/apache/fop/fonts/truetype/OTFFileTestCase.java create mode 100644 test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java create mode 100644 test/resources/fonts/otf/AlexBrushRegular.otf create mode 100644 test/resources/fonts/otf/SourceSansProBold.otf diff --git a/findbugs-exclude.xml b/findbugs-exclude.xml index 31edec268..2becac909 100644 --- a/findbugs-exclude.xml +++ b/findbugs-exclude.xml @@ -1,7 +1,7 @@ - + @@ -408,6 +408,11 @@ + + + + + @@ -834,7 +839,7 @@ - + @@ -989,7 +994,7 @@ - + @@ -2143,37 +2148,37 @@ - + - + - + - + - + - + - + @@ -2623,7 +2628,7 @@ - + @@ -2852,7 +2857,7 @@ - + @@ -2902,7 +2907,7 @@ - + @@ -3082,7 +3087,7 @@ - + @@ -3747,7 +3752,7 @@ - + @@ -5021,7 +5026,7 @@ - + @@ -5226,4 +5231,186 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lib/fontbox-1.8.0-SNAPSHOT.jar b/lib/fontbox-1.8.0-SNAPSHOT.jar new file mode 100644 index 0000000000000000000000000000000000000000..e20e1ad7b51b6917d785938983a8581428dc1a41 GIT binary patch literal 207498 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%0A1hy}n&&eX-p()d4h1hJ_y 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 literal 0 HcmV?d00001 diff --git a/lib/xmlgraphics-commons-svn-trunk.jar b/lib/xmlgraphics-commons-svn-trunk.jar index c7ff1d6a4347d91d982efbdfa3aa0c1388e945a5..22b0f5d52d418ceb006a6989d9856b9019d61596 100644 GIT binary patch delta 63431 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 z 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 z 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 0) { readScriptList(tableTag, scriptList); } @@ -3245,7 +3246,7 @@ public final class OTFAdvancedTypographicTableReader { } } - private void readGDEFClassDefTable(TTFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { + private void readGDEFClassDefTable(OFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { initATSubState(); in.seekSet(subtableOffset); // subtable is a bare class definition table @@ -3257,7 +3258,7 @@ public final class OTFAdvancedTypographicTableReader { resetATSubState(); } - private void readGDEFAttachmentTable(TTFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { + private void readGDEFAttachmentTable(OFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { initATSubState(); in.seekSet(subtableOffset); // read coverage offset @@ -3275,7 +3276,7 @@ public final class OTFAdvancedTypographicTableReader { resetATSubState(); } - private void readGDEFLigatureCaretTable(TTFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { + private void readGDEFLigatureCaretTable(OFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { initATSubState(); in.seekSet(subtableOffset); // read coverage offset @@ -3305,7 +3306,7 @@ public final class OTFAdvancedTypographicTableReader { resetATSubState(); } - private void readGDEFMarkAttachmentTable(TTFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { + private void readGDEFMarkAttachmentTable(OFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { initATSubState(); in.seekSet(subtableOffset); // subtable is a bare class definition table @@ -3317,7 +3318,7 @@ public final class OTFAdvancedTypographicTableReader { resetATSubState(); } - private void readGDEFMarkGlyphsTableFormat1(TTFTableName tableTag, int lookupSequence, long subtableOffset, int subtableFormat) throws IOException { + private void readGDEFMarkGlyphsTableFormat1(OFTableName tableTag, int lookupSequence, long subtableOffset, int subtableFormat) throws IOException { initATSubState(); in.seekSet(subtableOffset); // skip over format (already known) @@ -3351,7 +3352,7 @@ public final class OTFAdvancedTypographicTableReader { resetATSubState(); } - private void readGDEFMarkGlyphsTable(TTFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { + private void readGDEFMarkGlyphsTable(OFTableName tableTag, int lookupSequence, long subtableOffset) throws IOException { in.seekSet(subtableOffset); // read mark set subtable format int sf = in.readTTFUShort(); @@ -3367,17 +3368,17 @@ public final class OTFAdvancedTypographicTableReader { * @throws IOException In case of a I/O problem */ private void readGDEF() throws IOException { - TTFTableName tableTag = TTFTableName.GDEF; + OFTableName tableTag = OFTableName.GDEF; // Initialize temporary state initATState(); // Read glyph definition (GDEF) table - TTFDirTabEntry dirTab = ttf.getDirectoryEntry(tableTag); + OFDirTabEntry dirTab = otf.getDirectoryEntry(tableTag); if (gdef != null) { if (log.isDebugEnabled()) { log.debug(tableTag + ": ignoring duplicate table"); } } else if (dirTab != null) { - ttf.seekTab(in, tableTag, 0); + otf.seekTab(in, tableTag, 0); long version = in.readTTFULong(); if (log.isDebugEnabled()) { log.debug(tableTag + " version: " + (version / 65536) + "." + (version % 65536)); @@ -3440,17 +3441,17 @@ public final class OTFAdvancedTypographicTableReader { * @throws IOException In case of a I/O problem */ private void readGSUB() throws IOException { - TTFTableName tableTag = TTFTableName.GSUB; + OFTableName tableTag = OFTableName.GSUB; // Initialize temporary state initATState(); // Read glyph substitution (GSUB) table - TTFDirTabEntry dirTab = ttf.getDirectoryEntry(tableTag); + OFDirTabEntry dirTab = otf.getDirectoryEntry(tableTag); if (gpos != null) { if (log.isDebugEnabled()) { log.debug(tableTag + ": ignoring duplicate table"); } } else if (dirTab != null) { - ttf.seekTab(in, tableTag, 0); + otf.seekTab(in, tableTag, 0); int version = in.readTTFLong(); if (log.isDebugEnabled()) { log.debug(tableTag + " version: " + (version / 65536) + "." + (version % 65536)); @@ -3477,17 +3478,17 @@ public final class OTFAdvancedTypographicTableReader { * @throws IOException In case of a I/O problem */ private void readGPOS() throws IOException { - TTFTableName tableTag = TTFTableName.GPOS; + OFTableName tableTag = OFTableName.GPOS; // Initialize temporary state initATState(); // Read glyph positioning (GPOS) table - TTFDirTabEntry dirTab = ttf.getDirectoryEntry(tableTag); + OFDirTabEntry dirTab = otf.getDirectoryEntry(tableTag); if (gpos != null) { if (log.isDebugEnabled()) { log.debug(tableTag + ": ignoring duplicate table"); } } else if (dirTab != null) { - ttf.seekTab(in, tableTag, 0); + otf.seekTab(in, tableTag, 0); int version = in.readTTFLong(); if (log.isDebugEnabled()) { log.debug(tableTag + " version: " + (version / 65536) + "." + (version % 65536)); diff --git a/src/java/org/apache/fop/fonts/FontLoader.java b/src/java/org/apache/fop/fonts/FontLoader.java index f7ee24cbc..09e38260e 100644 --- a/src/java/org/apache/fop/fonts/FontLoader.java +++ b/src/java/org/apache/fop/fonts/FontLoader.java @@ -26,7 +26,7 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.fop.apps.io.InternalResourceResolver; -import org.apache.fop.fonts.truetype.TTFFontLoader; +import org.apache.fop.fonts.truetype.OFFontLoader; import org.apache.fop.fonts.type1.Type1FontLoader; /** @@ -105,7 +105,7 @@ public abstract class FontLoader { } loader = new Type1FontLoader(fontFileURI, embedded, useKerning, resourceResolver); } else { - loader = new TTFFontLoader(fontFileURI, subFontName, embedded, embeddingMode, + loader = new OFFontLoader(fontFileURI, subFontName, embedded, embeddingMode, encodingMode, useKerning, useAdvanced, resourceResolver); } return loader.getFont(); diff --git a/src/java/org/apache/fop/fonts/MultiByteFont.java b/src/java/org/apache/fop/fonts/MultiByteFont.java index 83f6491f3..68be7bed8 100644 --- a/src/java/org/apache/fop/fonts/MultiByteFont.java +++ b/src/java/org/apache/fop/fonts/MultiByteFont.java @@ -22,6 +22,7 @@ package org.apache.fop.fonts; import java.nio.CharBuffer; import java.nio.IntBuffer; import java.util.BitSet; +import java.util.LinkedHashMap; import java.util.Map; import org.apache.commons.logging.Log; @@ -67,6 +68,15 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl private int firstUnmapped; private int lastUnmapped; + private boolean isOTFFile = false; + + // since for most users the most likely glyphs are in the first cmap segments we store their mapping. + private static final int NUM_MOST_LIKELY_GLYPHS = 256; + private int[] mostLikelyGlyphs = new int[NUM_MOST_LIKELY_GLYPHS]; + + //A map to store each used glyph from the CID set against the glyph name. + private LinkedHashMap usedGlyphNames = new LinkedHashMap(); + /** * Default constructor */ @@ -111,6 +121,14 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl return cidType; } + public void setIsOTFFile(boolean isOTFFile) { + this.isOTFFile = isOTFFile; + } + + public boolean isOTFFile() { + return this.isOTFFile; + } + /** * Sets the CIDType. * @param cidType The cidType to set @@ -147,6 +165,14 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl return this.cidSet; } + public void mapUsedGlyphName(int gid, String value) { + usedGlyphNames.put(gid, value); + } + + public LinkedHashMap getUsedGlyphNames() { + return usedGlyphNames; + } + /** {@inheritDoc} */ @Override public String getEncodingName() { @@ -177,10 +203,15 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl * @return the glyph index (or 0 if the glyph is not available) */ // [TBD] - needs optimization, i.e., change from linear search to binary search - private int findGlyphIndex(int c) { + public int findGlyphIndex(int c) { int idx = c; int retIdx = SingleByteEncoding.NOT_FOUND_CODE_POINT; + // for most users the most likely glyphs are in the first cmap segments (meaning the one with + // the lowest unicode start values) + if (idx < NUM_MOST_LIKELY_GLYPHS && mostLikelyGlyphs[idx] != 0) { + return mostLikelyGlyphs[idx]; + } for (int i = 0; (i < cmap.length) && retIdx == 0; i++) { if (cmap[i].getUnicodeStart() <= idx && cmap[i].getUnicodeEnd() >= idx) { @@ -188,6 +219,9 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl retIdx = cmap[i].getGlyphStartIndex() + idx - cmap[i].getUnicodeStart(); + if (idx < NUM_MOST_LIKELY_GLYPHS) { + mostLikelyGlyphs[idx] = retIdx; + } } } return retIdx; @@ -281,22 +315,6 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl return findCharacterFromGlyphIndex(gi, true); } - - /** {@inheritDoc} */ - @Override - public char mapChar(char c) { - notifyMapOperation(); - int glyphIndex = findGlyphIndex(c); - if (glyphIndex == SingleByteEncoding.NOT_FOUND_CODE_POINT) { - warnMissingGlyph(c); - glyphIndex = findGlyphIndex(Typeface.NOT_FOUND); - } - if (isEmbeddable()) { - glyphIndex = cidSet.mapChar(glyphIndex, c); - } - return (char) glyphIndex; - } - protected BitSet getGlyphIndices() { BitSet bitset = new BitSet(); bitset.set(0); @@ -327,6 +345,23 @@ public class MultiByteFont extends CIDFont implements Substitutable, Positionabl return chars; } + /** {@inheritDoc} */ + @Override + public char mapChar(char c) { + notifyMapOperation(); + int glyphIndex = findGlyphIndex(c); + if (glyphIndex == SingleByteEncoding.NOT_FOUND_CODE_POINT) { + warnMissingGlyph(c); + if (!isOTFFile) { + glyphIndex = findGlyphIndex(Typeface.NOT_FOUND); + } + } + if (isEmbeddable()) { + glyphIndex = cidSet.mapChar(glyphIndex, c); + } + return (char) glyphIndex; + } + /** {@inheritDoc} */ @Override public boolean hasChar(char c) { diff --git a/src/java/org/apache/fop/fonts/SingleByteFont.java b/src/java/org/apache/fop/fonts/SingleByteFont.java index cd11c7849..a61d846e6 100644 --- a/src/java/org/apache/fop/fonts/SingleByteFont.java +++ b/src/java/org/apache/fop/fonts/SingleByteFont.java @@ -32,7 +32,7 @@ import org.apache.commons.logging.LogFactory; import org.apache.xmlgraphics.fonts.Glyphs; import org.apache.fop.apps.io.InternalResourceResolver; -import org.apache.fop.fonts.truetype.TTFFile.PostScriptVersion; +import org.apache.fop.fonts.truetype.OpenFont.PostScriptVersion; /** * Generic SingleByte font diff --git a/src/java/org/apache/fop/fonts/apps/TTFReader.java b/src/java/org/apache/fop/fonts/apps/TTFReader.java index db858e285..fc003d201 100644 --- a/src/java/org/apache/fop/fonts/apps/TTFReader.java +++ b/src/java/org/apache/fop/fonts/apps/TTFReader.java @@ -38,6 +38,7 @@ import org.apache.fop.Version; import org.apache.fop.fonts.CMapSegment; import org.apache.fop.fonts.FontUtil; import org.apache.fop.fonts.truetype.FontFileReader; +import org.apache.fop.fonts.truetype.OFFontLoader; import org.apache.fop.fonts.truetype.TTFFile; // CSOFF: InnerAssignmentCheck @@ -216,7 +217,8 @@ public class TTFReader extends AbstractFontReader { InputStream stream = new FileInputStream(fileName); try { FontFileReader reader = new FontFileReader(stream); - boolean supported = ttfFile.readFont(reader, fontName); + String header = OFFontLoader.readHeader(reader); + boolean supported = ttfFile.readFont(reader, header, fontName); if (!supported) { return null; } diff --git a/src/java/org/apache/fop/fonts/autodetect/FontInfoFinder.java b/src/java/org/apache/fop/fonts/autodetect/FontInfoFinder.java index e115264bb..21ebd4937 100644 --- a/src/java/org/apache/fop/fonts/autodetect/FontInfoFinder.java +++ b/src/java/org/apache/fop/fonts/autodetect/FontInfoFinder.java @@ -43,8 +43,8 @@ import org.apache.fop.fonts.FontTriplet; import org.apache.fop.fonts.FontUtil; import org.apache.fop.fonts.MultiByteFont; import org.apache.fop.fonts.truetype.FontFileReader; +import org.apache.fop.fonts.truetype.OFFontLoader; import org.apache.fop.fonts.truetype.TTFFile; -import org.apache.fop.fonts.truetype.TTFFontLoader; /** * Attempts to determine correct FontInfo @@ -220,7 +220,7 @@ public class FontInfoFinder { log.debug("Loading " + fontName); } try { - TTFFontLoader ttfLoader = new TTFFontLoader(fontURI, fontName, true, + OFFontLoader ttfLoader = new OFFontLoader(fontURI, fontName, true, EmbeddingMode.AUTO, EncodingMode.AUTO, useKerning, useAdvanced, resourceResolver); customFont = ttfLoader.getFont(); diff --git a/src/java/org/apache/fop/fonts/truetype/GlyfTable.java b/src/java/org/apache/fop/fonts/truetype/GlyfTable.java index f26ac2ffd..90abccaf2 100644 --- a/src/java/org/apache/fop/fonts/truetype/GlyfTable.java +++ b/src/java/org/apache/fop/fonts/truetype/GlyfTable.java @@ -31,7 +31,7 @@ import java.util.TreeSet; */ public class GlyfTable { - private final TTFMtxEntry[] mtxTab; + private final OFMtxEntry[] mtxTab; private final long tableOffset; @@ -47,7 +47,7 @@ public class GlyfTable { /** All the glyphs that are composed, but do not appear in the subset. */ private Set composedGlyphs = new TreeSet(); - GlyfTable(FontFileReader in, TTFMtxEntry[] metrics, TTFDirTabEntry dirTableEntry, + GlyfTable(FontFileReader in, OFMtxEntry[] metrics, OFDirTabEntry dirTableEntry, Map glyphs) throws IOException { mtxTab = metrics; tableOffset = dirTableEntry.getOffset(); diff --git a/src/java/org/apache/fop/fonts/truetype/TTFDirTabEntry.java b/src/java/org/apache/fop/fonts/truetype/OFDirTabEntry.java similarity index 96% rename from src/java/org/apache/fop/fonts/truetype/TTFDirTabEntry.java rename to src/java/org/apache/fop/fonts/truetype/OFDirTabEntry.java index c273d4471..a9c471d5e 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFDirTabEntry.java +++ b/src/java/org/apache/fop/fonts/truetype/OFDirTabEntry.java @@ -26,17 +26,17 @@ import java.io.UnsupportedEncodingException; /** * This class represents an entry to a TrueType font's Dir Tab. */ -public class TTFDirTabEntry { +public class OFDirTabEntry { private byte[] tag = new byte[4]; private int checksum; private long offset; private long length; - public TTFDirTabEntry() { + public OFDirTabEntry() { } - public TTFDirTabEntry(long offset, long length) { + public OFDirTabEntry(long offset, long length) { this.offset = offset; this.length = length; } diff --git a/src/java/org/apache/fop/fonts/truetype/TTFFontLoader.java b/src/java/org/apache/fop/fonts/truetype/OFFontLoader.java similarity index 66% rename from src/java/org/apache/fop/fonts/truetype/TTFFontLoader.java rename to src/java/org/apache/fop/fonts/truetype/OFFontLoader.java index b7adbd4c9..f15837bb8 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFFontLoader.java +++ b/src/java/org/apache/fop/fonts/truetype/OFFontLoader.java @@ -37,13 +37,13 @@ import org.apache.fop.fonts.FontType; import org.apache.fop.fonts.MultiByteFont; import org.apache.fop.fonts.NamedCharacter; import org.apache.fop.fonts.SingleByteFont; -import org.apache.fop.fonts.truetype.TTFFile.PostScriptVersion; +import org.apache.fop.fonts.truetype.OpenFont.PostScriptVersion; import org.apache.fop.util.HexEncoder; /** * Loads a TrueType font into memory directly from the original font file. */ -public class TTFFontLoader extends FontLoader { +public class OFFontLoader extends FontLoader { private MultiByteFont multiFont; private SingleByteFont singleFont; @@ -56,7 +56,7 @@ public class TTFFontLoader extends FontLoader { * @param fontFileURI the URI representing the font file * @param resourceResolver the resource resolver for font URI resolution */ - public TTFFontLoader(URI fontFileURI, InternalResourceResolver resourceResolver) { + public OFFontLoader(URI fontFileURI, InternalResourceResolver resourceResolver) { this(fontFileURI, null, true, EmbeddingMode.AUTO, EncodingMode.AUTO, true, true, resourceResolver); } @@ -72,7 +72,7 @@ public class TTFFontLoader extends FontLoader { * @param useAdvanced true to enable loading advanced info if available, false to disable * @param resolver the FontResolver for font URI resolution */ - public TTFFontLoader(URI fontFileURI, String subFontName, boolean embedded, + public OFFontLoader(URI fontFileURI, String subFontName, boolean embedded, EmbeddingMode embeddingMode, EncodingMode encodingMode, boolean useKerning, boolean useAdvanced, InternalResourceResolver resolver) { super(fontFileURI, embedded, useKerning, useAdvanced, resolver); @@ -101,26 +101,30 @@ public class TTFFontLoader extends FontLoader { private void read(String ttcFontName) throws IOException { InputStream in = resourceResolver.getResource(this.fontFileURI); try { - TTFFile ttf = new TTFFile(useKerning, useAdvanced); FontFileReader reader = new FontFileReader(in); - boolean supported = ttf.readFont(reader, ttcFontName); + String header = readHeader(reader); + boolean isCFF = header.equals("OTTO"); + OpenFont otf = (isCFF) ? new OTFFile() : new TTFFile(useKerning, useAdvanced); + boolean supported = otf.readFont(reader, header, ttcFontName); if (!supported) { - throw new IOException("TrueType font is not supported: " + fontFileURI); + throw new IOException("The font does not have a Unicode cmap table: " + fontFileURI); } - buildFont(ttf, ttcFontName); + buildFont(otf, ttcFontName); loaded = true; } finally { IOUtils.closeQuietly(in); } } - - private void buildFont(TTFFile ttf, String ttcFontName) { - if (ttf.isCFF()) { - throw new UnsupportedOperationException( - "OpenType fonts with CFF data are not supported, yet"); + public static String readHeader(FontFileReader fontFile) throws IOException { + if (fontFile != null) { + fontFile.seekSet(0); + return fontFile.readTTFString(4); // TTF_FIXED_SIZE (4 bytes) } + return null; + } + private void buildFont(OpenFont otf, String ttcFontName) { boolean isCid = this.embedded; if (this.encodingMode == EncodingMode.SINGLE_BYTE) { isCid = false; @@ -128,6 +132,7 @@ public class TTFFontLoader extends FontLoader { if (isCid) { multiFont = new MultiByteFont(resourceResolver, embeddingMode); + multiFont.setIsOTFFile(otf instanceof OTFFile); returnFont = multiFont; multiFont.setTTCName(ttcFontName); } else { @@ -135,43 +140,47 @@ public class TTFFontLoader extends FontLoader { returnFont = singleFont; } - returnFont.setFontName(ttf.getPostScriptName()); - returnFont.setFullName(ttf.getFullName()); - returnFont.setFamilyNames(ttf.getFamilyNames()); - returnFont.setFontSubFamilyName(ttf.getSubFamilyName()); - returnFont.setCapHeight(ttf.getCapHeight()); - returnFont.setXHeight(ttf.getXHeight()); - returnFont.setAscender(ttf.getLowerCaseAscent()); - returnFont.setDescender(ttf.getLowerCaseDescent()); - returnFont.setFontBBox(ttf.getFontBBox()); - returnFont.setFlags(ttf.getFlags()); - returnFont.setStemV(Integer.parseInt(ttf.getStemV())); //not used for TTF - returnFont.setItalicAngle(Integer.parseInt(ttf.getItalicAngle())); + returnFont.setFontName(otf.getPostScriptName()); + returnFont.setFullName(otf.getFullName()); + returnFont.setFamilyNames(otf.getFamilyNames()); + returnFont.setFontSubFamilyName(otf.getSubFamilyName()); + returnFont.setCapHeight(otf.getCapHeight()); + returnFont.setXHeight(otf.getXHeight()); + returnFont.setAscender(otf.getLowerCaseAscent()); + returnFont.setDescender(otf.getLowerCaseDescent()); + returnFont.setFontBBox(otf.getFontBBox()); + returnFont.setFlags(otf.getFlags()); + returnFont.setStemV(Integer.parseInt(otf.getStemV())); //not used for TTF + returnFont.setItalicAngle(Integer.parseInt(otf.getItalicAngle())); returnFont.setMissingWidth(0); - returnFont.setWeight(ttf.getWeightClass()); + returnFont.setWeight(otf.getWeightClass()); returnFont.setEmbeddingMode(this.embeddingMode); if (isCid) { - multiFont.setCIDType(CIDFontType.CIDTYPE2); - int[] wx = ttf.getWidths(); + if (otf instanceof OTFFile) { + multiFont.setCIDType(CIDFontType.CIDTYPE0); + } else { + multiFont.setCIDType(CIDFontType.CIDTYPE2); + } + int[] wx = otf.getWidths(); multiFont.setWidthArray(wx); } else { singleFont.setFontType(FontType.TRUETYPE); - singleFont.setEncoding(ttf.getCharSetName()); - returnFont.setFirstChar(ttf.getFirstChar()); - returnFont.setLastChar(ttf.getLastChar()); - singleFont.setTrueTypePostScriptVersion(ttf.getPostScriptVersion()); - copyWidthsSingleByte(ttf); + singleFont.setEncoding(otf.getCharSetName()); + returnFont.setFirstChar(otf.getFirstChar()); + returnFont.setLastChar(otf.getLastChar()); + singleFont.setTrueTypePostScriptVersion(otf.getPostScriptVersion()); + copyWidthsSingleByte(otf); } - returnFont.setCMap(getCMap(ttf)); + returnFont.setCMap(getCMap(otf)); - if (useKerning) { - copyKerning(ttf, isCid); + if (otf.getKerning() != null && useKerning) { + copyKerning(otf, isCid); } if (useAdvanced) { - copyAdvanced(ttf); + copyAdvanced(otf); } if (this.embedded) { - if (ttf.isEmbeddable()) { + if (otf.isEmbeddable()) { returnFont.setEmbedURI(this.fontFileURI); } else { String msg = "The font " + this.fontFileURI + " is not embeddable due to a" @@ -181,25 +190,25 @@ public class TTFFontLoader extends FontLoader { } } - private CMapSegment[] getCMap(TTFFile ttf) { - CMapSegment[] array = new CMapSegment[ttf.getCMaps().size()]; - return ttf.getCMaps().toArray(array); + private CMapSegment[] getCMap(OpenFont otf) { + CMapSegment[] array = new CMapSegment[otf.getCMaps().size()]; + return otf.getCMaps().toArray(array); } - private void copyWidthsSingleByte(TTFFile ttf) { - int[] wx = ttf.getWidths(); + private void copyWidthsSingleByte(OpenFont otf) { + int[] wx = otf.getWidths(); for (int i = singleFont.getFirstChar(); i <= singleFont.getLastChar(); i++) { - singleFont.setWidth(i, ttf.getCharWidth(i)); + singleFont.setWidth(i, otf.getCharWidth(i)); } - for (CMapSegment segment : ttf.getCMaps()) { + for (CMapSegment segment : otf.getCMaps()) { if (segment.getUnicodeStart() < 0xFFFE) { for (char u = (char)segment.getUnicodeStart(); u <= segment.getUnicodeEnd(); u++) { int codePoint = singleFont.getEncoding().mapChar(u); if (codePoint <= 0) { int glyphIndex = segment.getGlyphStartIndex() + u - segment.getUnicodeStart(); - String glyphName = ttf.getGlyphName(glyphIndex); - if (glyphName.length() == 0 && ttf.getPostScriptVersion() != PostScriptVersion.V2) { + String glyphName = otf.getGlyphName(glyphIndex); + if (glyphName.length() == 0 && otf.getPostScriptVersion() != PostScriptVersion.V2) { glyphName = "u" + HexEncoder.encode(u); } if (glyphName.length() > 0) { @@ -216,22 +225,22 @@ public class TTFFontLoader extends FontLoader { /** * Copy kerning information. */ - private void copyKerning(TTFFile ttf, boolean isCid) { + private void copyKerning(OpenFont otf, boolean isCid) { // Get kerning Set kerningSet; if (isCid) { - kerningSet = ttf.getKerning().keySet(); + kerningSet = otf.getKerning().keySet(); } else { - kerningSet = ttf.getAnsiKerning().keySet(); + kerningSet = otf.getAnsiKerning().keySet(); } for (Integer kpx1 : kerningSet) { Map h2; if (isCid) { - h2 = ttf.getKerning().get(kpx1); + h2 = otf.getKerning().get(kpx1); } else { - h2 = ttf.getAnsiKerning().get(kpx1); + h2 = otf.getAnsiKerning().get(kpx1); } returnFont.putKerningEntry(kpx1, h2); } @@ -240,12 +249,12 @@ public class TTFFontLoader extends FontLoader { /** * Copy advanced typographic information. */ - private void copyAdvanced(TTFFile ttf) { + private void copyAdvanced(OpenFont otf) { if (returnFont instanceof MultiByteFont) { MultiByteFont mbf = (MultiByteFont) returnFont; - mbf.setGDEF(ttf.getGDEF()); - mbf.setGSUB(ttf.getGSUB()); - mbf.setGPOS(ttf.getGPOS()); + mbf.setGDEF(otf.getGDEF()); + mbf.setGSUB(otf.getGSUB()); + mbf.setGPOS(otf.getGPOS()); } } diff --git a/src/java/org/apache/fop/fonts/truetype/TTFMtxEntry.java b/src/java/org/apache/fop/fonts/truetype/OFMtxEntry.java similarity index 99% rename from src/java/org/apache/fop/fonts/truetype/TTFMtxEntry.java rename to src/java/org/apache/fop/fonts/truetype/OFMtxEntry.java index 6884a633d..89af2296f 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFMtxEntry.java +++ b/src/java/org/apache/fop/fonts/truetype/OFMtxEntry.java @@ -24,7 +24,7 @@ import java.util.List; /** * This class represents a TrueType Mtx Entry. */ -class TTFMtxEntry { +class OFMtxEntry { private int wx; private int lsb; diff --git a/src/java/org/apache/fop/fonts/truetype/TTFTableName.java b/src/java/org/apache/fop/fonts/truetype/OFTableName.java similarity index 56% rename from src/java/org/apache/fop/fonts/truetype/TTFTableName.java rename to src/java/org/apache/fop/fonts/truetype/OFTableName.java index e5ad63128..f6264129a 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFTableName.java +++ b/src/java/org/apache/fop/fonts/truetype/OFTableName.java @@ -24,98 +24,104 @@ package org.apache.fop.fonts.truetype; * Represents table names as found in a TrueType font's Table Directory. * TrueType fonts may have custom tables so we cannot use an enum. */ -public final class TTFTableName { +public final class OFTableName { /** The first table in a TrueType font file containing metadata about other tables. */ - public static final TTFTableName TABLE_DIRECTORY = new TTFTableName("tableDirectory"); + public static final OFTableName TABLE_DIRECTORY = new OFTableName("tableDirectory"); + + /** Baseline data */ + public static final OFTableName BASE = new OFTableName("BASE"); + + /** CFF data/ */ + public static final OFTableName CFF = new OFTableName("CFF "); /** Embedded bitmap data. */ - public static final TTFTableName EBDT = new TTFTableName("EBDT"); + public static final OFTableName EBDT = new OFTableName("EBDT"); /** Embedded bitmap location data. */ - public static final TTFTableName EBLC = new TTFTableName("EBLC"); + public static final OFTableName EBLC = new OFTableName("EBLC"); /** Embedded bitmap scaling data. */ - public static final TTFTableName EBSC = new TTFTableName("EBSC"); + public static final OFTableName EBSC = new OFTableName("EBSC"); /** A FontForge specific table. */ - public static final TTFTableName FFTM = new TTFTableName("FFTM"); + public static final OFTableName FFTM = new OFTableName("FFTM"); /** Divides glyphs into various classes that make using the GPOS/GSUB tables easier. */ - public static final TTFTableName GDEF = new TTFTableName("GDEF"); + public static final OFTableName GDEF = new OFTableName("GDEF"); /** Provides kerning information, mark-to-base, etc. for opentype fonts. */ - public static final TTFTableName GPOS = new TTFTableName("GPOS"); + public static final OFTableName GPOS = new OFTableName("GPOS"); /** Provides ligature information, swash, etc. for opentype fonts. */ - public static final TTFTableName GSUB = new TTFTableName("GSUB"); + public static final OFTableName GSUB = new OFTableName("GSUB"); /** Linear threshold table. */ - public static final TTFTableName LTSH = new TTFTableName("LTSH"); + public static final OFTableName LTSH = new OFTableName("LTSH"); /** OS/2 and Windows specific metrics. */ - public static final TTFTableName OS2 = new TTFTableName("OS/2"); + public static final OFTableName OS2 = new OFTableName("OS/2"); /** PCL 5 data. */ - public static final TTFTableName PCLT = new TTFTableName("PCLT"); + public static final OFTableName PCLT = new OFTableName("PCLT"); /** Vertical Device Metrics table. */ - public static final TTFTableName VDMX = new TTFTableName("VDMX"); + public static final OFTableName VDMX = new OFTableName("VDMX"); /** Character to glyph mapping. */ - public static final TTFTableName CMAP = new TTFTableName("cmap"); + public static final OFTableName CMAP = new OFTableName("cmap"); /** Control Value Table. */ - public static final TTFTableName CVT = new TTFTableName("cvt "); + public static final OFTableName CVT = new OFTableName("cvt "); /** Font program. */ - public static final TTFTableName FPGM = new TTFTableName("fpgm"); + public static final OFTableName FPGM = new OFTableName("fpgm"); /** Grid-fitting and scan conversion procedure (grayscale). */ - public static final TTFTableName GASP = new TTFTableName("gasp"); + public static final OFTableName GASP = new OFTableName("gasp"); /** Glyph data. */ - public static final TTFTableName GLYF = new TTFTableName("glyf"); + public static final OFTableName GLYF = new OFTableName("glyf"); /** Horizontal device metrics. */ - public static final TTFTableName HDMX = new TTFTableName("hdmx"); + public static final OFTableName HDMX = new OFTableName("hdmx"); /** Font header. */ - public static final TTFTableName HEAD = new TTFTableName("head"); + public static final OFTableName HEAD = new OFTableName("head"); /** Horizontal header. */ - public static final TTFTableName HHEA = new TTFTableName("hhea"); + public static final OFTableName HHEA = new OFTableName("hhea"); /** Horizontal metrics. */ - public static final TTFTableName HMTX = new TTFTableName("hmtx"); + public static final OFTableName HMTX = new OFTableName("hmtx"); /** Kerning. */ - public static final TTFTableName KERN = new TTFTableName("kern"); + public static final OFTableName KERN = new OFTableName("kern"); /** Index to location. */ - public static final TTFTableName LOCA = new TTFTableName("loca"); + public static final OFTableName LOCA = new OFTableName("loca"); /** Maximum profile. */ - public static final TTFTableName MAXP = new TTFTableName("maxp"); + public static final OFTableName MAXP = new OFTableName("maxp"); /** Naming table. */ - public static final TTFTableName NAME = new TTFTableName("name"); + public static final OFTableName NAME = new OFTableName("name"); /** PostScript information. */ - public static final TTFTableName POST = new TTFTableName("post"); + public static final OFTableName POST = new OFTableName("post"); /** CVT Program. */ - public static final TTFTableName PREP = new TTFTableName("prep"); + public static final OFTableName PREP = new OFTableName("prep"); /** Vertical Metrics header. */ - public static final TTFTableName VHEA = new TTFTableName("vhea"); + public static final OFTableName VHEA = new OFTableName("vhea"); /** Vertical Metrics. */ - public static final TTFTableName VMTX = new TTFTableName("vmtx"); + public static final OFTableName VMTX = new OFTableName("vmtx"); private final String name; - private TTFTableName(String name) { + private OFTableName(String name) { this.name = name; } @@ -131,9 +137,9 @@ public final class TTFTableName { * @param tableName table name as in the Table Directory * @return TTFTableName */ - public static TTFTableName getValue(String tableName) { + public static OFTableName getValue(String tableName) { if (tableName != null) { - return new TTFTableName(tableName); + return new OFTableName(tableName); } throw new IllegalArgumentException("A TrueType font table name must not be null"); } @@ -148,10 +154,10 @@ public final class TTFTableName { if (o == this) { return true; } - if (!(o instanceof TTFTableName)) { + if (!(o instanceof OFTableName)) { return false; } - TTFTableName to = (TTFTableName) o; + OFTableName to = (OFTableName) o; return this.name.equals(to.getName()); } diff --git a/src/java/org/apache/fop/fonts/truetype/OTFFile.java b/src/java/org/apache/fop/fonts/truetype/OTFFile.java new file mode 100644 index 000000000..3976b5994 --- /dev/null +++ b/src/java/org/apache/fop/fonts/truetype/OTFFile.java @@ -0,0 +1,109 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.truetype; + +import java.io.IOException; + +import org.apache.fontbox.cff.CFFDataInput; +import org.apache.fontbox.cff.CFFFont; +import org.apache.fontbox.cff.CFFFont.Mapping; +import org.apache.fontbox.cff.CFFParser; + +public class OTFFile extends OpenFont { + + protected CFFFont fileFont; + + public OTFFile() throws IOException { + checkForFontbox(); + } + + private void checkForFontbox() throws IOException { + try { + Class.forName("org.apache.fontbox.cff.CFFFont"); + } catch (ClassNotFoundException ex) { + throw new IOException("The Fontbox jar was not found in the classpath. This is " + + "required for OTF CFF ssupport."); + } + } + + @Override + protected void updateBBoxAndOffset() throws IOException { + UnicodeMapping[] mappings = unicodeMappings.toArray(new UnicodeMapping[0]); + for (int i = 0; i < mappings.length; i++) { + int glyphIdx = mappings[i].getGlyphIndex(); + Mapping m = fileFont.getGIDMappings().get(glyphIdx); + int[] bbox = fileFont.getBoundingBox(m.getSID()); + String name = fileFont.getNameOfCharFromCode(m.getSID()); + mtxTab[glyphIdx].setBoundingBox(bbox); + mtxTab[glyphIdx].setName(name); + } + } + + @Override + protected void initializeFont(FontFileReader in) throws IOException { + fontFile = in; + fontFile.seekSet(0); + CFFParser parser = new CFFParser(); + fileFont = parser.parse(in.getAllBytes()).get(0); + } + + protected void readName() throws IOException { + Object familyName = fileFont.getProperty("FamilyName"); + if (familyName != null && !familyName.equals("")) { + familyNames.add(familyName.toString()); + fullName = familyName.toString(); + } else { + fullName = fileFont.getName(); + familyNames.add(fullName); + } + } + + /** + * Reads the CFFData from a given font file + * @param fontFile The font file being read + * @return The byte data found in the CFF table + */ + public static byte[] getCFFData(FontFileReader fontFile) throws IOException { + byte[] cff = new byte[0]; + CFFDataInput input = new CFFDataInput(fontFile.getAllBytes()); + input.readBytes(4); //OTTO + short numTables = input.readShort(); + input.readShort(); //searchRange + input.readShort(); //entrySelector + input.readShort(); //rangeShift + + for (int q = 0; q < numTables; q++) { + String tagName = new String(input.readBytes(4)); + readLong(input); //Checksum + long offset = readLong(input); + long length = readLong(input); + if (tagName.equals("CFF ")) { + cff = new byte[(int)length]; + System.arraycopy(fontFile.getAllBytes(), (int)offset, cff, 0, cff.length); + break; + } + } + return cff; + } + + private static long readLong(CFFDataInput input) throws IOException { + return (input.readCard16() << 16) | input.readCard16(); + } +} diff --git a/src/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java b/src/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java new file mode 100644 index 000000000..dbea48216 --- /dev/null +++ b/src/java/org/apache/fop/fonts/truetype/OTFSubSetFile.java @@ -0,0 +1,1092 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.truetype; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.Comparator; +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; + +import org.apache.fontbox.cff.CFFStandardString; +import org.apache.fontbox.cff.encoding.CFFEncoding; + +import org.apache.fop.fonts.MultiByteFont; +import org.apache.fop.fonts.cff.CFFDataReader; +import org.apache.fop.fonts.cff.CFFDataReader.CFFIndexData; +import org.apache.fop.fonts.cff.CFFDataReader.DICTEntry; +import org.apache.fop.fonts.cff.CFFDataReader.FDSelect; +import org.apache.fop.fonts.cff.CFFDataReader.FontDict; +import org.apache.fop.fonts.cff.CFFDataReader.Format0FDSelect; +import org.apache.fop.fonts.cff.CFFDataReader.Format3FDSelect; + +/** + * Reads an OpenType CFF file and generates a subset + * The OpenType specification can be found at the Microsoft + * Typography site: http://www.microsoft.com/typography/otspec/ + */ +public class OTFSubSetFile extends OTFFile { + + private byte[] output; + private int currentPos = 0; + private int realSize = 0; + + /** A map containing each glyph to be included in the subset + * with their existing and new GID's **/ + private LinkedHashMap subsetGlyphs; + + /** A map of the new GID to SID used to construct the charset table **/ + private LinkedHashMap gidToSID; + + private CFFIndexData localIndexSubr; + private CFFIndexData globalIndexSubr; + + /** List of subroutines to write to the local / global indexes in the subset font **/ + private List subsetLocalIndexSubr; + private List subsetGlobalIndexSubr; + + /** For fonts which have an FDSelect or ROS flag in Top Dict, this is used to store the + * local subroutine indexes for each group as opposed to the above subsetLocalIndexSubr */ + private ArrayList> fdSubrs; + + /** The subset FD Select table used to store the mappings between glyphs and their + * associated FDFont object which point to a private dict and local subroutines. */ + private LinkedHashMap subsetFDSelect; + + /** A list of unique subroutines from the global / local subroutine indexes */ + private List localUniques; + private List globalUniques; + + /** A store of the number of subroutines each global / local subroutine will store **/ + private int subsetLocalSubrCount; + private int subsetGlobalSubrCount; + + /** A list of char string data for each glyph to be stored in the subset font **/ + private List subsetCharStringsIndex; + + /** The embedded name to change in the name table **/ + private String embeddedName; + + /** An array used to hold the string index data for the subset font **/ + private List stringIndexData = new ArrayList(); + + /** The CFF reader object used to read data and offsets from the original font file */ + private CFFDataReader cffReader = null; + + /** The class used to represent this font **/ + private MultiByteFont mbFont; + + /** The number of standard strings in CFF **/ + private static final int NUM_STANDARD_STRINGS = 391; + /** The operator used to identify a local subroutine reference */ + private static final int LOCAL_SUBROUTINE = 10; + /** The operator used to identify a global subroutine reference */ + private static final int GLOBAL_SUBROUTINE = 29; + + public OTFSubSetFile() throws IOException { + super(); + } + + public void readFont(FontFileReader in, String embeddedName, String header, + MultiByteFont mbFont) throws IOException { + this.mbFont = mbFont; + readFont(in, embeddedName, header, mbFont.getUsedGlyphs()); + } + + /** + * Reads and creates a subset of the font. + * + * @param in FontFileReader to read from + * @param name Name to be checked for in the font file + * @param header The header of the font file + * @param glyphs Map of glyphs (glyphs has old index as (Integer) key and + * new index as (Integer) value) + * @throws IOException in case of an I/O problem + */ + void readFont(FontFileReader in, String embeddedName, String header, + Map usedGlyphs) throws IOException { + fontFile = in; + + currentPos = 0; + realSize = 0; + + this.embeddedName = embeddedName; + + //Sort by the new GID and store in a LinkedHashMap + subsetGlyphs = sortByValue(usedGlyphs); + + output = new byte[in.getFileSize()]; + + initializeFont(in); + + cffReader = new CFFDataReader(fontFile); + + //Create the CIDFontType0C data + createCFF(); + } + + private LinkedHashMap sortByValue(Map map) { + List> list = new ArrayList>(map.entrySet()); + Collections.sort(list, new Comparator>() { + public int compare(Entry o1, Entry o2) { + return ((Comparable) o1.getValue()).compareTo(o2.getValue()); + } + }); + + LinkedHashMap result = new LinkedHashMap(); + for (Entry entry : list) { + result.put(entry.getKey(), entry.getValue()); + } + return result; + } + + private void createCFF() throws IOException { + //Header + writeBytes(cffReader.getHeader()); + + //Name Index + writeIndex(Arrays.asList(embeddedName.getBytes())); + + //Keep offset of the topDICT so it can be updated once all data has been written + int topDictOffset = currentPos; + //Top DICT Index and Data + byte[] topDictIndex = cffReader.getTopDictIndex().getByteData(); + int offSize = topDictIndex[2]; + writeBytes(topDictIndex, 0, 3 + (offSize * 2)); + int topDictDataOffset = currentPos; + writeTopDICT(); + + //Create the char string index data and related local / global subroutines + if (cffReader.getFDSelect() == null) { + createCharStringData(); + } else { + createCharStringDataCID(); + } + + //If it is a CID-Keyed font, store each FD font and add each SID + List fontNameSIDs = null; + List subsetFDFonts = null; + if (cffReader.getFDSelect() != null) { + subsetFDFonts = getUsedFDFonts(); + fontNameSIDs = storeFDStrings(subsetFDFonts); + } + + //String index + writeStringIndex(); + + //Global subroutine index + writeIndex(subsetGlobalIndexSubr); + + //Encoding + int encodingOffset = currentPos; + writeEncoding(fileFont.getEncoding()); + + //Charset table + int charsetOffset = currentPos; + writeCharsetTable(cffReader.getFDSelect() != null); + + //FDSelect table + int fdSelectOffset = currentPos; + if (cffReader.getFDSelect() != null) { + writeFDSelect(); + } + + //Char Strings Index + int charStringOffset = currentPos; + writeIndex(subsetCharStringsIndex); + + if (cffReader.getFDSelect() == null) { + //Keep offset to modify later with the local subroutine index offset + int privateDictOffset = currentPos; + writePrivateDict(); + + //Local subroutine index + int localIndexOffset = currentPos; + writeIndex(subsetLocalIndexSubr); + + //Update the offsets + updateOffsets(topDictOffset, charsetOffset, charStringOffset, privateDictOffset, + localIndexOffset, encodingOffset); + } else { + List privateDictOffsets = writeCIDDictsAndSubrs(subsetFDFonts); + int fdArrayOffset = writeFDArray(subsetFDFonts, privateDictOffsets, fontNameSIDs); + + updateCIDOffsets(topDictDataOffset, fdArrayOffset, fdSelectOffset, charsetOffset, + charStringOffset, encodingOffset); + } + } + + private List storeFDStrings(List uniqueNewRefs) throws IOException { + ArrayList fontNameSIDs = new ArrayList(); + List fdFonts = cffReader.getFDFonts(); + for (int i = 0; i < uniqueNewRefs.size(); i++) { + FontDict fdFont = fdFonts.get(uniqueNewRefs.get(i)); + byte[] fdFontByteData = fdFont.getByteData(); + Map fdFontDict = cffReader.parseDictData(fdFontByteData); + fontNameSIDs.add(stringIndexData.size() + NUM_STANDARD_STRINGS); + stringIndexData.add(cffReader.getStringIndex().getValue(fdFontDict.get("FontName") + .getOperands().get(0).intValue() - NUM_STANDARD_STRINGS)); + } + return fontNameSIDs; + } + + private void writeBytes(byte[] out) { + for (int i = 0; i < out.length; i++) { + output[currentPos++] = out[i]; + realSize++; + } + } + + private void writeBytes(byte[] out, int offset, int length) { + for (int i = offset; i < offset + length; i++) { + output[currentPos++] = out[i]; + realSize++; + } + } + + private void writeEncoding(CFFEncoding encoding) throws IOException { + LinkedHashMap topDICT = cffReader.getTopDictEntries(); + DICTEntry encodingEntry = topDICT.get("Encoding"); + if (encodingEntry != null && encodingEntry.getOperands().get(0).intValue() != 0 + && encodingEntry.getOperands().get(0).intValue() != 1) { + writeByte(0); + writeByte(gidToSID.size()); + for (int gid : gidToSID.keySet()) { + int code = encoding.getCode(gidToSID.get(gid)); + writeByte(code); + } + } + } + + private void writeTopDICT() throws IOException { + LinkedHashMap topDICT = cffReader.getTopDictEntries(); + List topDictStringEntries = Arrays.asList("version", "Notice", "Copyright", + "FullName", "FamilyName", "Weight", "PostScript"); + for (Map.Entry dictEntry : topDICT.entrySet()) { + String dictKey = dictEntry.getKey(); + DICTEntry entry = dictEntry.getValue(); + //If the value is an SID, update the reference but keep the size the same + if (dictKey.equals("ROS")) { + writeROSEntry(entry); + } else if (dictKey.equals("CIDCount")) { + writeCIDCount(entry); + } else if (topDictStringEntries.contains(dictKey)) { + writeTopDictStringEntry(entry); + } else { + writeBytes(entry.getByteData()); + } + } + } + + private void writeROSEntry(DICTEntry dictEntry) throws IOException { + int sidA = dictEntry.getOperands().get(0).intValue(); + if (sidA > 390) { + stringIndexData.add(cffReader.getStringIndex().getValue(sidA - NUM_STANDARD_STRINGS)); + } + int sidAStringIndex = stringIndexData.size() + 390; + int sidB = dictEntry.getOperands().get(1).intValue(); + if (sidB > 390) { + stringIndexData.add("Identity".getBytes()); + } + int sidBStringIndex = stringIndexData.size() + 390; + byte[] cidEntryByteData = dictEntry.getByteData(); + cidEntryByteData = updateOffset(cidEntryByteData, 0, dictEntry.getOperandLengths().get(0), + sidAStringIndex); + cidEntryByteData = updateOffset(cidEntryByteData, dictEntry.getOperandLengths().get(0), + dictEntry.getOperandLengths().get(1), sidBStringIndex); + cidEntryByteData = updateOffset(cidEntryByteData, dictEntry.getOperandLengths().get(0) + + dictEntry.getOperandLengths().get(1), dictEntry.getOperandLengths().get(2), 139); + writeBytes(cidEntryByteData); + } + + private void writeCIDCount(DICTEntry dictEntry) throws IOException { + byte[] cidCountByteData = dictEntry.getByteData(); + cidCountByteData = updateOffset(cidCountByteData, 0, dictEntry.getOperandLengths().get(0), + subsetGlyphs.size()); + writeBytes(cidCountByteData); + } + + private void writeTopDictStringEntry(DICTEntry dictEntry) throws IOException { + int sid = dictEntry.getOperands().get(0).intValue(); + if (sid > 391) { + stringIndexData.add(cffReader.getStringIndex().getValue(sid - 391)); + } + + byte[] newDictEntry = createNewRef(stringIndexData.size() + 390, dictEntry.getOperator(), + dictEntry.getOperandLength()); + writeBytes(newDictEntry); + } + + private void writeStringIndex() throws IOException { + Map topDICT = cffReader.getTopDictEntries(); + int charsetOffset = topDICT.get("charset").getOperands().get(0).intValue(); + + gidToSID = new LinkedHashMap(); + + for (int gid : subsetGlyphs.keySet()) { + int sid = cffReader.getSIDFromGID(charsetOffset, gid); + //Check whether the SID falls into the standard string set + if (sid < NUM_STANDARD_STRINGS) { + gidToSID.put(subsetGlyphs.get(gid), sid); + if (mbFont != null) { + mbFont.mapUsedGlyphName(subsetGlyphs.get(gid), + CFFStandardString.getName(sid)); + } + } else { + int index = sid - NUM_STANDARD_STRINGS; + if (index <= cffReader.getStringIndex().getNumObjects()) { + if (mbFont != null) { + mbFont.mapUsedGlyphName(subsetGlyphs.get(gid), + new String(cffReader.getStringIndex().getValue(index))); + } + gidToSID.put(subsetGlyphs.get(gid), stringIndexData.size() + 391); + stringIndexData.add(cffReader.getStringIndex().getValue(index)); + } else { + if (mbFont != null) { + mbFont.mapUsedGlyphName(subsetGlyphs.get(gid), ".notdef"); + } + gidToSID.put(subsetGlyphs.get(gid), index); + } + } + } + //Write the String Index + writeIndex(stringIndexData); + } + + private void createCharStringDataCID() throws IOException { + CFFIndexData charStringsIndex = cffReader.getCharStringIndex(); + + FDSelect fontDictionary = cffReader.getFDSelect(); + if (fontDictionary instanceof Format0FDSelect) { + throw new UnsupportedOperationException("OTF CFF CID Format0 currently not implemented"); + } else if (fontDictionary instanceof Format3FDSelect) { + Format3FDSelect fdSelect = (Format3FDSelect)fontDictionary; + Map subsetGroups = new HashMap(); + + List uniqueGroups = new ArrayList(); + for (int gid : subsetGlyphs.keySet()) { + Integer[] ranges = fdSelect.getRanges().keySet().toArray(new Integer[0]); + for (int i = 0; i < ranges.length; i++) { + int nextRange = -1; + if (i < ranges.length - 1) { + nextRange = ranges[i + 1]; + } else { + nextRange = fdSelect.getSentinelGID(); + } + if (gid >= ranges[i] && gid < nextRange) { + subsetGroups.put(gid, fdSelect.getRanges().get(ranges[i])); + if (!uniqueGroups.contains(fdSelect.getRanges().get(ranges[i]))) { + uniqueGroups.add(fdSelect.getRanges().get(ranges[i])); + } + } + } + } + + //Prepare resources + globalIndexSubr = cffReader.getGlobalIndexSubr(); + + //Create the new char string index + subsetCharStringsIndex = new ArrayList(); + + globalUniques = new ArrayList(); + + subsetFDSelect = new LinkedHashMap(); + + List> foundLocalUniques = new ArrayList>(); + for (int i = 0; i < uniqueGroups.size(); i++) { + foundLocalUniques.add(new ArrayList()); + } + for (int gid : subsetGlyphs.keySet()) { + int group = subsetGroups.get(gid); + localIndexSubr = cffReader.getFDFonts().get(group).getLocalSubrData(); + localUniques = foundLocalUniques.get(uniqueGroups.indexOf(subsetGroups.get(gid))); + + FDIndexReference newFDReference = new FDIndexReference( + uniqueGroups.indexOf(subsetGroups.get(gid)), subsetGroups.get(gid)); + subsetFDSelect.put(subsetGlyphs.get(gid), newFDReference); + byte[] data = charStringsIndex.getValue(gid); + preScanForSubsetIndexSize(data); + } + + //Create the two lists which are to store the local and global subroutines + subsetGlobalIndexSubr = new ArrayList(); + + fdSubrs = new ArrayList>(); + subsetGlobalSubrCount = globalUniques.size(); + globalUniques.clear(); + localUniques = null; + + for (int l = 0; l < foundLocalUniques.size(); l++) { + fdSubrs.add(new ArrayList()); + } + List> foundLocalUniquesB = new ArrayList>(); + for (int k = 0; k < uniqueGroups.size(); k++) { + foundLocalUniquesB.add(new ArrayList()); + } + for (Integer gid : subsetGlyphs.keySet()) { + int group = subsetGroups.get(gid); + localIndexSubr = cffReader.getFDFonts().get(group).getLocalSubrData(); + localUniques = foundLocalUniquesB.get(subsetFDSelect.get(subsetGlyphs.get(gid)).getNewFDIndex()); + byte[] data = charStringsIndex.getValue(gid); + subsetLocalIndexSubr = fdSubrs.get(subsetFDSelect.get(subsetGlyphs.get(gid)).getNewFDIndex()); + subsetLocalSubrCount = foundLocalUniques.get(subsetFDSelect.get(subsetGlyphs.get(gid)).getNewFDIndex()).size(); + data = readCharStringData(data, subsetLocalSubrCount); + subsetCharStringsIndex.add(data); + } + } + } + + private void writeFDSelect() { + writeByte(0); //Format + for (Integer gid : subsetFDSelect.keySet()) { + writeByte(subsetFDSelect.get(gid).getNewFDIndex()); + } + } + + private List getUsedFDFonts() { + List uniqueNewRefs = new ArrayList(); + for (int gid : subsetFDSelect.keySet()) { + int fdIndex = subsetFDSelect.get(gid).getOldFDIndex(); + if (!uniqueNewRefs.contains(fdIndex)) { + uniqueNewRefs.add(fdIndex); + } + } + return uniqueNewRefs; + } + + private List writeCIDDictsAndSubrs(List uniqueNewRefs) + throws IOException { + List privateDictOffsets = new ArrayList(); + List fdFonts = cffReader.getFDFonts(); + for (int i = 0; i < uniqueNewRefs.size(); i++) { + FontDict curFDFont = fdFonts.get(uniqueNewRefs.get(i)); + HashMap fdPrivateDict = cffReader.parseDictData( + curFDFont.getPrivateDictData()); + int privateDictOffset = currentPos; + privateDictOffsets.add(privateDictOffset); + byte[] fdPrivateDictByteData = curFDFont.getPrivateDictData(); + if (fdPrivateDict.get("Subrs") != null) { + fdPrivateDictByteData = updateOffset(fdPrivateDictByteData, fdPrivateDict.get("Subrs").getOffset(), + fdPrivateDict.get("Subrs").getOperandLength(), + fdPrivateDictByteData.length); + } + writeBytes(fdPrivateDictByteData); + writeIndex(fdSubrs.get(i)); + } + return privateDictOffsets; + } + + private int writeFDArray(List uniqueNewRefs, List privateDictOffsets, + List fontNameSIDs) + throws IOException { + int offset = currentPos; + List fdFonts = cffReader.getFDFonts(); + + writeCard16(uniqueNewRefs.size()); + writeByte(1); //Offset size + writeByte(1); //First offset + + int count = 1; + for (int i = 0; i < uniqueNewRefs.size(); i++) { + FontDict fdFont = fdFonts.get(uniqueNewRefs.get(i)); + count += fdFont.getByteData().length; + writeByte(count); + } + + for (int i = 0; i < uniqueNewRefs.size(); i++) { + FontDict fdFont = fdFonts.get(uniqueNewRefs.get(i)); + byte[] fdFontByteData = fdFont.getByteData(); + Map fdFontDict = cffReader.parseDictData(fdFontByteData); + //Update the SID to the FontName + fdFontByteData = updateOffset(fdFontByteData, fdFontDict.get("FontName").getOffset() - 1, + fdFontDict.get("FontName").getOperandLengths().get(0), + fontNameSIDs.get(i)); + //Update the Private dict reference + fdFontByteData = updateOffset(fdFontByteData, fdFontDict.get("Private").getOffset() + + fdFontDict.get("Private").getOperandLengths().get(0), + fdFontDict.get("Private").getOperandLengths().get(1), + privateDictOffsets.get(i)); + writeBytes(fdFontByteData); + } + return offset; + } + + private class FDIndexReference { + private int newFDIndex; + private int oldFDIndex; + + public FDIndexReference(int newFDIndex, int oldFDIndex) { + this.newFDIndex = newFDIndex; + this.oldFDIndex = oldFDIndex; + } + + public int getNewFDIndex() { + return newFDIndex; + } + + public int getOldFDIndex() { + return oldFDIndex; + } + } + + private void createCharStringData() throws IOException { + Map topDICT = cffReader.getTopDictEntries(); + + CFFIndexData charStringsIndex = cffReader.getCharStringIndex(); + + DICTEntry privateEntry = topDICT.get("Private"); + if (privateEntry != null) { + int privateOffset = privateEntry.getOperands().get(1).intValue(); + Map privateDICT = cffReader.getPrivateDict(privateEntry); + + int localSubrOffset = privateOffset + privateDICT.get("Subrs").getOperands().get(0).intValue(); + localIndexSubr = cffReader.readIndex(localSubrOffset); + } + + globalIndexSubr = cffReader.getGlobalIndexSubr(); + + //Create the two lists which are to store the local and global subroutines + subsetLocalIndexSubr = new ArrayList(); + subsetGlobalIndexSubr = new ArrayList(); + + //Create the new char string index + subsetCharStringsIndex = new ArrayList(); + + localUniques = new ArrayList(); + globalUniques = new ArrayList(); + + for (int gid : subsetGlyphs.keySet()) { + byte[] data = charStringsIndex.getValue(gid); + preScanForSubsetIndexSize(data); + } + + //Store the size of each subset index and clear the unique arrays + subsetLocalSubrCount = localUniques.size(); + subsetGlobalSubrCount = globalUniques.size(); + localUniques.clear(); + globalUniques.clear(); + + for (int gid : subsetGlyphs.keySet()) { + byte[] data = charStringsIndex.getValue(gid); + //Retrieve modified char string data and fill local / global subroutine arrays + data = readCharStringData(data, subsetLocalSubrCount); + subsetCharStringsIndex.add(data); + } + } + + private void preScanForSubsetIndexSize(byte[] data) throws IOException { + boolean hasLocalSubroutines = localIndexSubr != null && localIndexSubr.getNumObjects() > 0; + boolean hasGlobalSubroutines = globalIndexSubr != null && globalIndexSubr.getNumObjects() > 0; + BytesNumber operand = new BytesNumber(-1, -1); + for (int dataPos = 0; dataPos < data.length; dataPos++) { + int b0 = data[dataPos] & 0xff; + if (b0 == LOCAL_SUBROUTINE && hasLocalSubroutines) { + int subrNumber = getSubrNumber(localIndexSubr.getNumObjects(), operand.getNumber()); + + if (!localUniques.contains(subrNumber) && subrNumber < localIndexSubr.getNumObjects()) { + localUniques.add(subrNumber); + byte[] subr = localIndexSubr.getValue(subrNumber); + preScanForSubsetIndexSize(subr); + } + operand.clearNumber(); + } else if (b0 == GLOBAL_SUBROUTINE && hasGlobalSubroutines) { + int subrNumber = getSubrNumber(globalIndexSubr.getNumObjects(), operand.getNumber()); + + if (!globalUniques.contains(subrNumber) && subrNumber < globalIndexSubr.getNumObjects()) { + globalUniques.add(subrNumber); + byte[] subr = globalIndexSubr.getValue(subrNumber); + preScanForSubsetIndexSize(subr); + } + operand.clearNumber(); + } else if ((b0 >= 0 && b0 <= 27) || (b0 >= 29 && b0 <= 31)) { + operand.clearNumber(); + if (b0 == 19 || b0 == 20) { + dataPos += 1; + } + } else if (b0 == 28 || (b0 >= 32 && b0 <= 255)) { + operand = readNumber(b0, data, dataPos); + dataPos += operand.getNumBytes() - 1; + } + } + } + + private int getSubrNumber(int numSubroutines, int operand) { + int bias = getBias(numSubroutines); + return bias + operand; + } + + private byte[] readCharStringData(byte[] data, int subsetLocalSubrCount) throws IOException { + boolean hasLocalSubroutines = localIndexSubr != null && localIndexSubr.getNumObjects() > 0; + boolean hasGlobalSubroutines = globalIndexSubr != null && globalIndexSubr.getNumObjects() > 0; + BytesNumber operand = new BytesNumber(-1, -1); + for (int dataPos = 0; dataPos < data.length; dataPos++) { + int b0 = data[dataPos] & 0xff; + if (b0 == 10 && hasLocalSubroutines) { + int subrNumber = getSubrNumber(localIndexSubr.getNumObjects(), operand.getNumber()); + + int newRef = getNewRefForReference(subrNumber, localUniques, localIndexSubr, subsetLocalIndexSubr, + subsetLocalSubrCount); + + if (newRef != -1) { + byte[] newData = constructNewRefData(dataPos, data, operand, subsetLocalSubrCount, + newRef, new int[] {10}); + dataPos -= data.length - newData.length; + data = newData; + } + + operand.clearNumber(); + } else if (b0 == 29 && hasGlobalSubroutines) { + int subrNumber = getSubrNumber(globalIndexSubr.getNumObjects(), operand.getNumber()); + + int newRef = getNewRefForReference(subrNumber, globalUniques, globalIndexSubr, subsetGlobalIndexSubr, + subsetGlobalSubrCount); + + if (newRef != -1) { + byte[] newData = constructNewRefData(dataPos, data, operand, subsetGlobalSubrCount, + newRef, new int[] {29}); + dataPos -= (data.length - newData.length); + data = newData; + } + + operand.clearNumber(); + } else if ((b0 >= 0 && b0 <= 27) || (b0 >= 29 && b0 <= 31)) { + operand.clearNumber(); + if (b0 == 19 || b0 == 20) { + dataPos += 1; + } + } else if (b0 == 28 || (b0 >= 32 && b0 <= 255)) { + operand = readNumber(b0, data, dataPos); + dataPos += operand.getNumBytes() - 1; + } + } + + //Return the data with the modified references to our arrays + return data; + } + + private int getNewRefForReference(int subrNumber, List uniquesArray, + CFFIndexData indexSubr, List subsetIndexSubr, int subrCount) throws IOException { + int newRef = -1; + if (!uniquesArray.contains(subrNumber)) { + if (subrNumber < indexSubr.getNumObjects()) { + byte[] subr = indexSubr.getValue(subrNumber); + subr = readCharStringData(subr, subrCount); + if (!uniquesArray.contains(subrNumber)) { + uniquesArray.add(subrNumber); + subsetIndexSubr.add(subr); + newRef = subsetIndexSubr.size() - 1; + } else { + newRef = uniquesArray.indexOf(subrNumber); + } + } + } else { + newRef = uniquesArray.indexOf(subrNumber); + } + return newRef; + } + + private int getBias(int subrCount) { + if (subrCount < 1240) { + return 107; + } else if (subrCount < 33900) { + return 1131; + } else { + return 32768; + } + } + + private byte[] constructNewRefData(int curDataPos, byte[] currentData, BytesNumber operand, + int fullSubsetIndexSize, int curSubsetIndexSize, int[] operatorCode) { + //Create the new array with the modified reference + byte[] newData; + int startRef = curDataPos - operand.getNumBytes(); + int length = operand.getNumBytes() + 1; + byte[] preBytes = new byte[startRef]; + System.arraycopy(currentData, 0, preBytes, 0, startRef); + int newBias = getBias(fullSubsetIndexSize); + int newRef = curSubsetIndexSize - newBias; + byte[] newRefBytes = createNewRef(newRef, operatorCode, -1); + newData = concatArray(preBytes, newRefBytes); + byte[] postBytes = new byte[currentData.length - (startRef + length)]; + System.arraycopy(currentData, startRef + length, postBytes, 0, + currentData.length - (startRef + length)); + return concatArray(newData, postBytes); + } + + public static byte[] createNewRef(int newRef, int[] operatorCode, int forceLength) { + byte[] newRefBytes; + int sizeOfOperator = operatorCode.length; + if ((forceLength == -1 && newRef <= 107) || forceLength == 1) { + newRefBytes = new byte[1 + sizeOfOperator]; + //The index values are 0 indexed + newRefBytes[0] = (byte)(newRef + 139); + for (int i = 0; i < operatorCode.length; i++) { + newRefBytes[1 + i] = (byte)operatorCode[i]; + } + } else if ((forceLength == -1 && newRef <= 1131) || forceLength == 2) { + newRefBytes = new byte[2 + sizeOfOperator]; + if (newRef <= 363) { + newRefBytes[0] = (byte)247; + } else if (newRef <= 619) { + newRefBytes[0] = (byte)248; + } else if (newRef <= 875) { + newRefBytes[0] = (byte)249; + } else { + newRefBytes[0] = (byte)250; + } + newRefBytes[1] = (byte)(newRef - 108); + for (int i = 0; i < operatorCode.length; i++) { + newRefBytes[2 + i] = (byte)operatorCode[i]; + } + } else if ((forceLength == -1 && newRef <= 32767) || forceLength == 3) { + newRefBytes = new byte[3 + sizeOfOperator]; + newRefBytes[0] = 28; + newRefBytes[1] = (byte)(newRef >> 8); + newRefBytes[2] = (byte)newRef; + for (int i = 0; i < operatorCode.length; i++) { + newRefBytes[3 + i] = (byte)operatorCode[i]; + } + } else { + newRefBytes = new byte[5 + sizeOfOperator]; + newRefBytes[0] = 29; + newRefBytes[1] = (byte)(newRef >> 24); + newRefBytes[2] = (byte)(newRef >> 16); + newRefBytes[3] = (byte)(newRef >> 8); + newRefBytes[4] = (byte)newRef; + for (int i = 0; i < operatorCode.length; i++) { + newRefBytes[5 + i] = (byte)operatorCode[i]; + } + } + return newRefBytes; + } + + public static byte[] concatArray(byte[] a, byte[] b) { + int aLen = a.length; + int bLen = b.length; + byte[] c = new byte[aLen + bLen]; + System.arraycopy(a, 0, c, 0, aLen); + System.arraycopy(b, 0, c, aLen, bLen); + return c; + } + + private int writeIndex(List dataArray) { + int hdrTotal = 3; + //2 byte number of items + this.writeCard16(dataArray.size()); + //Offset Size: 1 byte = 256, 2 bytes = 65536 etc. + int totLength = 0; + for (int i = 0; i < dataArray.size(); i++) { + totLength += dataArray.get(i).length; + } + int offSize = 1; + if (totLength <= (1 << 8)) { + offSize = 1; + } else if (totLength <= (1 << 16)) { + offSize = 2; + } else if (totLength <= (1 << 24)) { + offSize = 3; + } else { + offSize = 4; + } + this.writeByte(offSize); + //Count the first offset 1 + hdrTotal += offSize; + int total = 0; + for (int i = 0; i < dataArray.size(); i++) { + hdrTotal += offSize; + int length = dataArray.get(i).length; + switch (offSize) { + case 1: + if (i == 0) { + writeByte(1); + } + total += length; + writeByte(total + 1); + break; + case 2: + if (i == 0) { + writeCard16(1); + } + total += length; + writeCard16(total + 1); + break; + case 3: + if (i == 0) { + writeThreeByteNumber(1); + } + total += length; + writeThreeByteNumber(total + 1); + break; + case 4: + if (i == 0) { + writeULong(1); + } + total += length; + writeULong(total + 1); + break; + default: + throw new AssertionError("Offset Size was not an expected value."); + } + } + for (int i = 0; i < dataArray.size(); i++) { + writeBytes(dataArray.get(i)); + } + return hdrTotal + total; + } + + + private BytesNumber readNumber(int b0, byte[] input, int curPos) throws IOException { + if (b0 == 28) { + int b1 = input[curPos + 1] & 0xff; + int b2 = input[curPos + 2] & 0xff; + return new BytesNumber(Integer.valueOf((short) (b1 << 8 | b2)), 3); + } else if (b0 >= 32 && b0 <= 246) { + return new BytesNumber(Integer.valueOf(b0 - 139), 1); + } else if (b0 >= 247 && b0 <= 250) { + int b1 = input[curPos + 1] & 0xff; + return new BytesNumber(Integer.valueOf((b0 - 247) * 256 + b1 + 108), 2); + } else if (b0 >= 251 && b0 <= 254) { + int b1 = input[curPos + 1] & 0xff; + return new BytesNumber(Integer.valueOf(-(b0 - 251) * 256 - b1 - 108), 2); + } else if (b0 == 255) { + int b1 = input[curPos + 1] & 0xff; + int b2 = input[curPos + 2] & 0xff; + return new BytesNumber(Integer.valueOf((short)(b1 << 8 | b2)), 5); + } else { + throw new IllegalArgumentException(); + } + } + + /** + * A class used to store the last number operand and also it's size in bytes + */ + private static final class BytesNumber { + private int number; + private int numBytes; + + public BytesNumber(int number, int numBytes) { + this.number = number; + this.numBytes = numBytes; + } + + public int getNumber() { + return this.number; + } + + public int getNumBytes() { + return this.numBytes; + } + + public void clearNumber() { + this.number = -1; + this.numBytes = -1; + } + } + + private void writeCharsetTable(boolean cidFont) throws IOException { + writeByte(0); + for (int gid : gidToSID.keySet()) { + if (cidFont && gid == 0) { + continue; + } + writeCard16((cidFont) ? gid : gidToSID.get(gid)); + } + } + + private void writePrivateDict() throws IOException { + Map topDICT = cffReader.getTopDictEntries(); + + DICTEntry privateEntry = topDICT.get("Private"); + if (privateEntry != null) { + writeBytes(cffReader.getPrivateDictBytes(privateEntry)); + } + } + + private void updateOffsets(int topDictOffset, int charsetOffset, int charStringOffset, + int privateDictOffset, int localIndexOffset, int encodingOffset) + throws IOException { + Map topDICT = cffReader.getTopDictEntries(); + Map privateDICT = null; + + DICTEntry privateEntry = topDICT.get("Private"); + if (privateEntry != null) { + privateDICT = cffReader.getPrivateDict(privateEntry); + } + + int dataPos = 3 + (cffReader.getTopDictIndex().getOffSize() + * cffReader.getTopDictIndex().getOffsets().length); + int dataTopDictOffset = topDictOffset + dataPos; + + updateFixedOffsets(topDICT, dataTopDictOffset, charsetOffset, charStringOffset, encodingOffset); + + if (privateDICT != null) { + //Private index offset in the top dict + int oldPrivateOffset = dataTopDictOffset + privateEntry.getOffset(); + output = updateOffset(output, oldPrivateOffset + privateEntry.getOperandLengths().get(0), + privateEntry.getOperandLengths().get(1), privateDictOffset); + + //Update the local subroutine index offset in the private dict + DICTEntry subroutines = privateDICT.get("Subrs"); + int oldLocalSubrOffset = privateDictOffset + subroutines.getOffset(); + //Value needs to be converted to -139 etc. + int encodeValue = 0; + if (subroutines.getOperandLength() == 1) { + encodeValue = 139; + } + output = updateOffset(output, oldLocalSubrOffset, subroutines.getOperandLength(), + (localIndexOffset - privateDictOffset) + encodeValue); + } + } + + private void updateFixedOffsets(Map topDICT, int dataTopDictOffset, + int charsetOffset, int charStringOffset, int encodingOffset) { + //Charset offset in the top dict + DICTEntry charset = topDICT.get("charset"); + int oldCharsetOffset = dataTopDictOffset + charset.getOffset(); + output = updateOffset(output, oldCharsetOffset, charset.getOperandLength(), charsetOffset); + + //Char string index offset in the private dict + DICTEntry charString = topDICT.get("CharStrings"); + int oldCharStringOffset = dataTopDictOffset + charString.getOffset(); + output = updateOffset(output, oldCharStringOffset, charString.getOperandLength(), charStringOffset); + + DICTEntry encodingEntry = topDICT.get("Encoding"); + if (encodingEntry != null && encodingEntry.getOperands().get(0).intValue() != 0 + && encodingEntry.getOperands().get(0).intValue() != 1) { + int oldEncodingOffset = dataTopDictOffset + encodingEntry.getOffset(); + output = updateOffset(output, oldEncodingOffset, encodingEntry.getOperandLength(), encodingOffset); + } + } + + private void updateCIDOffsets(int topDictDataOffset, int fdArrayOffset, int fdSelectOffset, + int charsetOffset, int charStringOffset, int encodingOffset) { + LinkedHashMap topDict = cffReader.getTopDictEntries(); + + DICTEntry fdArrayEntry = topDict.get("FDArray"); + if (fdArrayEntry != null) { + output = updateOffset(output, topDictDataOffset + fdArrayEntry.getOffset() - 1, + fdArrayEntry.getOperandLength(), fdArrayOffset); + } + + DICTEntry fdSelect = topDict.get("FDSelect"); + if (fdSelect != null) { + output = updateOffset(output, topDictDataOffset + fdSelect.getOffset() - 1, + fdSelect.getOperandLength(), fdSelectOffset); + } + + updateFixedOffsets(topDict, topDictDataOffset, charsetOffset, charStringOffset, encodingOffset); + } + + private byte[] updateOffset(byte[] out, int position, int length, int replacement) { + switch (length) { + case 1: + out[position] = (byte)(replacement & 0xFF); + break; + case 2: + if (replacement <= 363) { + out[position] = (byte)247; + } else if (replacement <= 619) { + out[position] = (byte)248; + } else if (replacement <= 875) { + out[position] = (byte)249; + } else { + out[position] = (byte)250; + } + out[position + 1] = (byte)(replacement - 108); + break; + case 3: + out[position] = (byte)28; + out[position + 1] = (byte)((replacement >> 8) & 0xFF); + out[position + 2] = (byte)(replacement & 0xFF); + break; + case 5: + out[position] = (byte)29; + out[position + 1] = (byte)((replacement >> 24) & 0xFF); + out[position + 2] = (byte)((replacement >> 16) & 0xFF); + out[position + 3] = (byte)((replacement >> 8) & 0xFF); + out[position + 4] = (byte)(replacement & 0xFF); + break; + default: + } + return out; + } + + /** + * Appends a byte to the output array, + * updates currentPost but not realSize + */ + private void writeByte(int b) { + output[currentPos++] = (byte)b; + realSize++; + } + + /** + * Appends a USHORT to the output array, + * updates currentPost but not realSize + */ + private void writeCard16(int s) { + byte b1 = (byte)((s >> 8) & 0xff); + byte b2 = (byte)(s & 0xff); + writeByte(b1); + writeByte(b2); + } + + private void writeThreeByteNumber(int s) { + byte b1 = (byte)((s >> 16) & 0xFF); + byte b2 = (byte)((s >> 8) & 0xFF); + byte b3 = (byte)(s & 0xFF); + output[currentPos++] = b1; + output[currentPos++] = b2; + output[currentPos++] = b3; + realSize += 3; + } + + /** + * Appends a ULONG to the output array, + * at the given position + */ + private void writeULong(int s) { + byte b1 = (byte)((s >> 24) & 0xff); + byte b2 = (byte)((s >> 16) & 0xff); + byte b3 = (byte)((s >> 8) & 0xff); + byte b4 = (byte)(s & 0xff); + output[currentPos++] = b1; + output[currentPos++] = b2; + output[currentPos++] = b3; + output[currentPos++] = b4; + realSize += 4; + } + + /** + * Returns a subset of the fonts (readFont() MUST be called first in order to create the + * subset). + * @return byte array + */ + public byte[] getFontSubset() { + byte[] ret = new byte[realSize]; + System.arraycopy(output, 0, ret, 0, realSize); + return ret; + } +} diff --git a/src/java/org/apache/fop/fonts/truetype/OpenFont.java b/src/java/org/apache/fop/fonts/truetype/OpenFont.java new file mode 100644 index 000000000..ce9a2b388 --- /dev/null +++ b/src/java/org/apache/fop/fonts/truetype/OpenFont.java @@ -0,0 +1,1937 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.truetype; + +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStream; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.BitSet; +import java.util.Collections; +import java.util.Comparator; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Set; +import java.util.SortedSet; +import java.util.TreeSet; + +import org.apache.commons.io.IOUtils; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; + +import org.apache.xmlgraphics.fonts.Glyphs; + +import org.apache.fop.complexscripts.fonts.AdvancedTypographicTableFormatException; +import org.apache.fop.complexscripts.fonts.GlyphDefinitionTable; +import org.apache.fop.complexscripts.fonts.GlyphPositioningTable; +import org.apache.fop.complexscripts.fonts.GlyphSubstitutionTable; +import org.apache.fop.complexscripts.fonts.OTFAdvancedTypographicTableReader; +import org.apache.fop.fonts.CMapSegment; +import org.apache.fop.fonts.FontUtil; +import org.apache.fop.fonts.MultiByteFont; + +public abstract class OpenFont { + + static final byte NTABS = 24; + static final int MAX_CHAR_CODE = 255; + static final int ENC_BUF_SIZE = 1024; + + private static final String[] MAC_GLYPH_ORDERING = { + /* 0x000 */ + ".notdef", ".null", "nonmarkingreturn", "space", + "exclam", "quotedbl", "numbersign", "dollar", + "percent", "ampersand", "quotesingle", "parenleft", + "parenright", "asterisk", "plus", "comma", + /* 0x010 */ + "hyphen", "period", "slash", "zero", + "one", "two", "three", "four", + "five", "six", "seven", "eight", + "nine", "colon", "semicolon", "less", + /* 0x020 */ + "equal", "greater", "question", "at", + "A", "B", "C", "D", + "E", "F", "G", "H", + "I", "J", "K", "L", + /* 0x030 */ + "M", "N", "O", "P", + "Q", "R", "S", "T", + "U", "V", "W", "X", + "Y", "Z", "bracketleft", "backslash", + /* 0x040 */ + "bracketright", "asciicircum", "underscore", "grave", + "a", "b", "c", "d", + "e", "f", "g", "h", + "i", "j", "k", "l", + /* 0x050 */ + "m", "n", "o", "p", + "q", "r", "s", "t", + "u", "v", "w", "x", + "y", "z", "braceleft", "bar", + /* 0x060 */ + "braceright", "asciitilde", "Adieresis", "Aring", + "Ccedilla", "Eacute", "Ntilde", "Odieresis", + "Udieresis", "aacute", "agrave", "acircumflex", + "adieresis", "atilde", "aring", "ccedilla", + /* 0x070 */ + "eacute", "egrave", "ecircumflex", "edieresis", + "iacute", "igrave", "icircumflex", "idieresis", + "ntilde", "oacute", "ograve", "ocircumflex", + "odieresis", "otilde", "uacute", "ugrave", + /* 0x080 */ + "ucircumflex", "udieresis", "dagger", "degree", + "cent", "sterling", "section", "bullet", + "paragraph", "germandbls", "registered", "copyright", + "trademark", "acute", "dieresis", "notequal", + /* 0x090 */ + "AE", "Oslash", "infinity", "plusminus", + "lessequal", "greaterequal", "yen", "mu", + "partialdiff", "summation", "product", "pi", + "integral", "ordfeminine", "ordmasculine", "Omega", + /* 0x0A0 */ + "ae", "oslash", "questiondown", "exclamdown", + "logicalnot", "radical", "florin", "approxequal", + "Delta", "guillemotleft", "guillemotright", "ellipsis", + "nonbreakingspace", "Agrave", "Atilde", "Otilde", + /* 0x0B0 */ + "OE", "oe", "endash", "emdash", + "quotedblleft", "quotedblright", "quoteleft", "quoteright", + "divide", "lozenge", "ydieresis", "Ydieresis", + "fraction", "currency", "guilsinglleft", "guilsinglright", + /* 0x0C0 */ + "fi", "fl", "daggerdbl", "periodcentered", + "quotesinglbase", "quotedblbase", "perthousand", "Acircumflex", + "Ecircumflex", "Aacute", "Edieresis", "Egrave", + "Iacute", "Icircumflex", "Idieresis", "Igrave", + /* 0x0D0 */ + "Oacute", "Ocircumflex", "apple", "Ograve", + "Uacute", "Ucircumflex", "Ugrave", "dotlessi", + "circumflex", "tilde", "macron", "breve", + "dotaccent", "ring", "cedilla", "hungarumlaut", + /* 0x0E0 */ + "ogonek", "caron", "Lslash", "lslash", + "Scaron", "scaron", "Zcaron", "zcaron", + "brokenbar", "Eth", "eth", "Yacute", + "yacute", "Thorn", "thorn", "minus", + /* 0x0F0 */ + "multiply", "onesuperior", "twosuperior", "threesuperior", + "onehalf", "onequarter", "threequarters", "franc", + "Gbreve", "gbreve", "Idotaccent", "Scedilla", + "scedilla", "Cacute", "cacute", "Ccaron", + /* 0x100 */ + "ccaron", "dcroat" + }; + + /** The FontFileReader used to read this TrueType font. */ + protected FontFileReader fontFile; + + /** Set to true to get even more debug output than with level DEBUG */ + public static final boolean TRACE_ENABLED = false; + + private static final String ENCODING = "WinAnsiEncoding"; // Default encoding + + private static final short FIRST_CHAR = 0; + + protected boolean useKerning = false; + private boolean isEmbeddable = true; + private boolean hasSerifs = true; + /** + * Table directory + */ + protected Map dirTabs; + + private Map> kerningTab; // for CIDs + private Map> ansiKerningTab; // For winAnsiEncoding + private List cmaps; + protected List unicodeMappings; + + private int upem; // unitsPerEm from "head" table + private int nhmtx; // Number of horizontal metrics + private PostScriptVersion postScriptVersion; + protected int locaFormat; + /** + * Offset to last loca + */ + protected long lastLoca = 0; + protected int numberOfGlyphs; // Number of glyphs in font (read from "maxp" table) + + /** + * Contains glyph data + */ + protected OFMtxEntry[] mtxTab; // Contains glyph data + + protected String postScriptName = ""; + protected String fullName = ""; + protected String notice = ""; + protected final Set familyNames = new HashSet(); + protected String subFamilyName = ""; + + private long italicAngle = 0; + private long isFixedPitch = 0; + private int fontBBox1 = 0; + private int fontBBox2 = 0; + private int fontBBox3 = 0; + private int fontBBox4 = 0; + private int capHeight = 0; + private int os2CapHeight = 0; + private int xHeight = 0; + private int os2xHeight = 0; + //Effective ascender/descender + private int ascender = 0; + private int descender = 0; + //Ascender/descender from hhea table + private int hheaAscender = 0; + private int hheaDescender = 0; + //Ascender/descender from OS/2 table + private int os2Ascender = 0; + private int os2Descender = 0; + private int usWeightClass = 0; + + private short lastChar = 0; + + private int[] ansiWidth; + private Map> ansiIndex; + + // internal mapping of glyph indexes to unicode indexes + // used for quick mappings in this class + private final Map glyphToUnicodeMap = new HashMap(); + private final Map unicodeToGlyphMap = new HashMap(); + + private boolean isCFF; + + // advanced typographic table support + protected boolean useAdvanced = false; + protected OTFAdvancedTypographicTableReader advancedTableReader; + + /** + * Version of the PostScript table (post) contained in this font. + */ + public static enum PostScriptVersion { + /** PostScript table version 1.0. */ + V1, + /** PostScript table version 2.0. */ + V2, + /** PostScript table version 3.0. */ + V3, + /** Unknown version of the PostScript table. */ + UNKNOWN; + } + + /** + * logging instance + */ + protected Log log = LogFactory.getLog(TTFFile.class); + + public OpenFont() { + this(true, false); + } + + /** + * Constructor + * @param useKerning true if kerning data should be loaded + * @param useAdvanced true if advanced typographic tables should be loaded + */ + public OpenFont(boolean useKerning, boolean useAdvanced) { + this.useKerning = useKerning; + this.useAdvanced = useAdvanced; + } + + /** + * Key-value helper class. + */ + final class UnicodeMapping implements Comparable { + + private final int unicodeIndex; + private final int glyphIndex; + + UnicodeMapping(int glyphIndex, int unicodeIndex) { + this.unicodeIndex = unicodeIndex; + this.glyphIndex = glyphIndex; + glyphToUnicodeMap.put(new Integer(glyphIndex), new Integer(unicodeIndex)); + unicodeToGlyphMap.put(new Integer(unicodeIndex), new Integer(glyphIndex)); + } + + /** + * Returns the glyphIndex. + * @return the glyph index + */ + public int getGlyphIndex() { + return glyphIndex; + } + + /** + * Returns the unicodeIndex. + * @return the Unicode index + */ + public int getUnicodeIndex() { + return unicodeIndex; + } + + + /** {@inheritDoc} */ + public int hashCode() { + int hc = unicodeIndex; + hc = 19 * hc + (hc ^ glyphIndex); + return hc; + } + + /** {@inheritDoc} */ + public boolean equals(Object o) { + if (o instanceof UnicodeMapping) { + UnicodeMapping m = (UnicodeMapping) o; + if (unicodeIndex != m.unicodeIndex) { + return false; + } else { + return (glyphIndex == m.glyphIndex); + } + } else { + return false; + } + } + + /** {@inheritDoc} */ + public int compareTo(Object o) { + if (o instanceof UnicodeMapping) { + UnicodeMapping m = (UnicodeMapping) o; + if (unicodeIndex > m.unicodeIndex) { + return 1; + } else if (unicodeIndex < m.unicodeIndex) { + return -1; + } else { + return 0; + } + } else { + return -1; + } + } + } + + /** + * Obtain directory table entry. + * @param name (tag) of entry + * @return a directory table entry or null if none found + */ + public OFDirTabEntry getDirectoryEntry(OFTableName name) { + return dirTabs.get(name); + } + + /** + * Position inputstream to position indicated + * in the dirtab offset + offset + * @param in font file reader + * @param tableName (tag) of table + * @param offset from start of table + * @return true if seek succeeded + * @throws IOException if I/O exception occurs during seek + */ + public boolean seekTab(FontFileReader in, OFTableName tableName, + long offset) throws IOException { + OFDirTabEntry dt = dirTabs.get(tableName); + if (dt == null) { + log.error("Dirtab " + tableName.getName() + " not found."); + return false; + } else { + in.seekSet(dt.getOffset() + offset); + } + return true; + } + + /** + * Convert from truetype unit to pdf unit based on the + * unitsPerEm field in the "head" table + * @param n truetype unit + * @return pdf unit + */ + public int convertTTFUnit2PDFUnit(int n) { + int ret; + if (n < 0) { + long rest1 = n % upem; + long storrest = 1000 * rest1; + long ledd2 = (storrest != 0 ? rest1 / storrest : 0); + ret = -((-1000 * n) / upem - (int)ledd2); + } else { + ret = (n / upem) * 1000 + ((n % upem) * 1000) / upem; + } + + return ret; + } + + /** + * Read the cmap table, + * return false if the table is not present or only unsupported + * tables are present. Currently only unicode cmaps are supported. + * Set the unicodeIndex in the TTFMtxEntries and fills in the + * cmaps vector. + */ + protected boolean readCMAP() throws IOException { + + unicodeMappings = new ArrayList(); + + seekTab(fontFile, OFTableName.CMAP, 2); + int numCMap = fontFile.readTTFUShort(); // Number of cmap subtables + long cmapUniOffset = 0; + long symbolMapOffset = 0; + + if (log.isDebugEnabled()) { + log.debug(numCMap + " cmap tables"); + } + + //Read offset for all tables. We are only interested in the unicode table + for (int i = 0; i < numCMap; i++) { + int cmapPID = fontFile.readTTFUShort(); + int cmapEID = fontFile.readTTFUShort(); + long cmapOffset = fontFile.readTTFLong(); + + if (log.isDebugEnabled()) { + log.debug("Platform ID: " + cmapPID + " Encoding: " + cmapEID); + } + + if (cmapPID == 3 && cmapEID == 1) { + cmapUniOffset = cmapOffset; + } + if (cmapPID == 3 && cmapEID == 0) { + symbolMapOffset = cmapOffset; + } + } + + if (cmapUniOffset > 0) { + return readUnicodeCmap(cmapUniOffset, 1); + } else if (symbolMapOffset > 0) { + return readUnicodeCmap(symbolMapOffset, 0); + } else { + log.fatal("Unsupported TrueType font: No Unicode or Symbol cmap table" + + " not present. Aborting"); + return false; + } + } + + private boolean readUnicodeCmap(long cmapUniOffset, int encodingID) + throws IOException { + //Read CMAP table and correct mtxTab.index + int mtxPtr = 0; + + // Read unicode cmap + seekTab(fontFile, OFTableName.CMAP, cmapUniOffset); + int cmapFormat = fontFile.readTTFUShort(); + /*int cmap_length =*/ fontFile.readTTFUShort(); //skip cmap length + + if (log.isDebugEnabled()) { + log.debug("CMAP format: " + cmapFormat); + } + + if (cmapFormat == 4) { + fontFile.skip(2); // Skip version number + int cmapSegCountX2 = fontFile.readTTFUShort(); + int cmapSearchRange = fontFile.readTTFUShort(); + int cmapEntrySelector = fontFile.readTTFUShort(); + int cmapRangeShift = fontFile.readTTFUShort(); + + if (log.isDebugEnabled()) { + log.debug("segCountX2 : " + cmapSegCountX2); + log.debug("searchRange : " + cmapSearchRange); + log.debug("entrySelector: " + cmapEntrySelector); + log.debug("rangeShift : " + cmapRangeShift); + } + + + int[] cmapEndCounts = new int[cmapSegCountX2 / 2]; + int[] cmapStartCounts = new int[cmapSegCountX2 / 2]; + int[] cmapDeltas = new int[cmapSegCountX2 / 2]; + int[] cmapRangeOffsets = new int[cmapSegCountX2 / 2]; + + for (int i = 0; i < (cmapSegCountX2 / 2); i++) { + cmapEndCounts[i] = fontFile.readTTFUShort(); + } + + fontFile.skip(2); // Skip reservedPad + + for (int i = 0; i < (cmapSegCountX2 / 2); i++) { + cmapStartCounts[i] = fontFile.readTTFUShort(); + } + + for (int i = 0; i < (cmapSegCountX2 / 2); i++) { + cmapDeltas[i] = fontFile.readTTFShort(); + } + + //int startRangeOffset = in.getCurrentPos(); + + for (int i = 0; i < (cmapSegCountX2 / 2); i++) { + cmapRangeOffsets[i] = fontFile.readTTFUShort(); + } + + int glyphIdArrayOffset = fontFile.getCurrentPos(); + + BitSet eightBitGlyphs = new BitSet(256); + + // Insert the unicode id for the glyphs in mtxTab + // and fill in the cmaps ArrayList + for (int i = 0; i < cmapStartCounts.length; i++) { + + if (log.isTraceEnabled()) { + log.trace(i + ": " + cmapStartCounts[i] + + " - " + cmapEndCounts[i]); + } + if (log.isDebugEnabled()) { + if (isInPrivateUseArea(cmapStartCounts[i], cmapEndCounts[i])) { + log.debug("Font contains glyphs in the Unicode private use area: " + + Integer.toHexString(cmapStartCounts[i]) + " - " + + Integer.toHexString(cmapEndCounts[i])); + } + } + + for (int j = cmapStartCounts[i]; j <= cmapEndCounts[i]; j++) { + + // Update lastChar + if (j < 256 && j > lastChar) { + lastChar = (short)j; + } + + if (j < 256) { + eightBitGlyphs.set(j); + } + + if (mtxPtr < mtxTab.length) { + int glyphIdx; + // the last character 65535 = .notdef + // may have a range offset + if (cmapRangeOffsets[i] != 0 && j != 65535) { + int glyphOffset = glyphIdArrayOffset + + ((cmapRangeOffsets[i] / 2) + + (j - cmapStartCounts[i]) + + (i) + - cmapSegCountX2 / 2) * 2; + fontFile.seekSet(glyphOffset); + glyphIdx = (fontFile.readTTFUShort() + cmapDeltas[i]) + & 0xffff; + //mtxTab[glyphIdx].setName(mtxTab[glyphIdx].getName() + " - "+(char)j); + unicodeMappings.add(new UnicodeMapping(glyphIdx, j)); + mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); + + if (encodingID == 0 && j >= 0xF020 && j <= 0xF0FF) { + //Experimental: Mapping 0xF020-0xF0FF to 0x0020-0x00FF + //Tested with Wingdings and Symbol TTF fonts which map their + //glyphs in the region 0xF020-0xF0FF. + int mapped = j - 0xF000; + if (!eightBitGlyphs.get(mapped)) { + //Only map if Unicode code point hasn't been mapped before + unicodeMappings.add(new UnicodeMapping(glyphIdx, mapped)); + mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(mapped)); + } + } + + // Also add winAnsiWidth + List v = ansiIndex.get(new Integer(j)); + if (v != null) { + for (Integer aIdx : v) { + ansiWidth[aIdx.intValue()] + = mtxTab[glyphIdx].getWx(); + + if (log.isTraceEnabled()) { + log.trace("Added width " + + mtxTab[glyphIdx].getWx() + + " uni: " + j + + " ansi: " + aIdx.intValue()); + } + } + } + + if (log.isTraceEnabled()) { + log.trace("Idx: " + + glyphIdx + + " Delta: " + cmapDeltas[i] + + " Unicode: " + j + + " name: " + mtxTab[glyphIdx].getName()); + } + } else { + glyphIdx = (j + cmapDeltas[i]) & 0xffff; + + if (glyphIdx < mtxTab.length) { + mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); + } else { + log.debug("Glyph " + glyphIdx + + " out of range: " + + mtxTab.length); + } + + unicodeMappings.add(new UnicodeMapping(glyphIdx, j)); + if (glyphIdx < mtxTab.length) { + mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); + } else { + log.debug("Glyph " + glyphIdx + + " out of range: " + + mtxTab.length); + } + + // Also add winAnsiWidth + List v = ansiIndex.get(new Integer(j)); + if (v != null) { + for (Integer aIdx : v) { + ansiWidth[aIdx.intValue()] = mtxTab[glyphIdx].getWx(); + } + } + + //getLogger().debug("IIdx: " + + // mtxPtr + + // " Delta: " + cmap_deltas[i] + + // " Unicode: " + j + + // " name: " + + // mtxTab[(j+cmap_deltas[i]) & 0xffff].name); + + } + if (glyphIdx < mtxTab.length) { + if (mtxTab[glyphIdx].getUnicodeIndex().size() < 2) { + mtxPtr++; + } + } + } + } + } + } else { + log.error("Cmap format not supported: " + cmapFormat); + return false; + } + return true; + } + + private boolean isInPrivateUseArea(int start, int end) { + return (isInPrivateUseArea(start) || isInPrivateUseArea(end)); + } + + private boolean isInPrivateUseArea(int unicode) { + return (unicode >= 0xE000 && unicode <= 0xF8FF); + } + + /** + * + * @return mmtx data + */ + public List getMtx() { + return Collections.unmodifiableList(Arrays.asList(mtxTab)); + } + + /** + * Print first char/last char + */ + private void printMaxMin() { + int min = 255; + int max = 0; + for (int i = 0; i < mtxTab.length; i++) { + if (mtxTab[i].getIndex() < min) { + min = mtxTab[i].getIndex(); + } + if (mtxTab[i].getIndex() > max) { + max = mtxTab[i].getIndex(); + } + } + log.info("Min: " + min); + log.info("Max: " + max); + } + + + /** + * Reads the font using a FontFileReader. + * + * @param in The FontFileReader to use + * @throws IOException In case of an I/O problem + */ + public void readFont(FontFileReader in, String header) throws IOException { + readFont(in, header, (String)null); + } + + /** + * initialize the ansiWidths array (for winAnsiEncoding) + * and fill with the missingwidth + */ + protected void initAnsiWidths() { + ansiWidth = new int[256]; + for (int i = 0; i < 256; i++) { + ansiWidth[i] = mtxTab[0].getWx(); + } + + // Create an index hash to the ansiWidth + // Can't just index the winAnsiEncoding when inserting widths + // same char (eg bullet) is repeated more than one place + ansiIndex = new HashMap>(); + for (int i = 32; i < Glyphs.WINANSI_ENCODING.length; i++) { + Integer ansi = new Integer(i); + Integer uni = new Integer(Glyphs.WINANSI_ENCODING[i]); + + List v = ansiIndex.get(uni); + if (v == null) { + v = new ArrayList(); + ansiIndex.put(uni, v); + } + v.add(ansi); + } + } + + /** + * Read the font data. + * If the fontfile is a TrueType Collection (.ttc file) + * the name of the font to read data for must be supplied, + * else the name is ignored. + * + * @param in The FontFileReader to use + * @param name The name of the font + * @return boolean Returns true if the font is valid + * @throws IOException In case of an I/O problem + */ + public boolean readFont(FontFileReader in, String header, String name) throws IOException { + initializeFont(in); + /* + * Check if TrueType collection, and that the name + * exists in the collection + */ + if (!checkTTC(header, name)) { + if (name == null) { + throw new IllegalArgumentException( + "For TrueType collection you must specify which font " + + "to select (-ttcname)"); + } else { + throw new IOException( + "Name does not exist in the TrueType collection: " + name); + } + } + + readDirTabs(); + readFontHeader(); + getNumGlyphs(); + if (log.isDebugEnabled()) { + log.debug("Number of glyphs in font: " + numberOfGlyphs); + } + readHorizontalHeader(); + readHorizontalMetrics(); + initAnsiWidths(); + readPostScript(); + readOS2(); + determineAscDesc(); + + readName(); + boolean pcltFound = readPCLT(); + // Read cmap table and fill in ansiwidths + boolean valid = readCMAP(); + if (!valid) { + return false; + } + + // Create cmaps for bfentries + createCMaps(); + updateBBoxAndOffset(); + + if (useKerning) { + readKerning(); + } + handleCharacterSpacing(in); + + guessVerticalMetricsFromGlyphBBox(); + return true; + } + + /** + * Reads a font. + * + * @param in FontFileReader to read from + * @param name Name to be checked for in the font file + * @param glyphs Map of glyphs (glyphs has old index as (Integer) key and + * new index as (Integer) value) + * @throws IOException in case of an I/O problem + */ + public void readFont(FontFileReader in, String header, MultiByteFont mbfont) throws IOException { + readFont(in, header, mbfont.getTTCName()); + } + + protected abstract void updateBBoxAndOffset() throws IOException; + + protected abstract void readName() throws IOException; + + protected abstract void initializeFont(FontFileReader in) throws IOException; + + protected void handleCharacterSpacing(FontFileReader in) throws IOException { + // Read advanced typographic tables. + if (useAdvanced) { + try { + OTFAdvancedTypographicTableReader atr + = new OTFAdvancedTypographicTableReader(this, in); + atr.readAll(); + this.advancedTableReader = atr; + } catch (AdvancedTypographicTableFormatException e) { + log.warn( + "Encountered format constraint violation in advanced (typographic) table (AT) " + + "in font '" + getFullName() + "', ignoring AT data: " + + e.getMessage() + ); + } + } + + } + + protected void createCMaps() { + cmaps = new ArrayList(); + int unicodeStart; + int glyphStart; + int unicodeEnd; + + Iterator e = unicodeMappings.iterator(); + UnicodeMapping um = e.next(); + UnicodeMapping lastMapping = um; + + unicodeStart = um.getUnicodeIndex(); + glyphStart = um.getGlyphIndex(); + + while (e.hasNext()) { + um = e.next(); + if (((lastMapping.getUnicodeIndex() + 1) != um.getUnicodeIndex()) + || ((lastMapping.getGlyphIndex() + 1) != um.getGlyphIndex())) { + unicodeEnd = lastMapping.getUnicodeIndex(); + cmaps.add(new CMapSegment(unicodeStart, unicodeEnd, glyphStart)); + unicodeStart = um.getUnicodeIndex(); + glyphStart = um.getGlyphIndex(); + } + lastMapping = um; + } + + unicodeEnd = lastMapping.getUnicodeIndex(); + cmaps.add(new CMapSegment(unicodeStart, unicodeEnd, glyphStart)); + } + + /** + * Returns the PostScript name of the font. + * @return String The PostScript name + */ + public String getPostScriptName() { + if (postScriptName.length() == 0) { + return FontUtil.stripWhiteSpace(getFullName()); + } else { + return postScriptName; + } + } + + PostScriptVersion getPostScriptVersion() { + return postScriptVersion; + } + + /** + * Returns the font family names of the font. + * @return Set The family names (a Set of Strings) + */ + public Set getFamilyNames() { + return familyNames; + } + + /** + * Returns the font sub family name of the font. + * @return String The sub family name + */ + public String getSubFamilyName() { + return subFamilyName; + } + + /** + * Returns the full name of the font. + * @return String The full name + */ + public String getFullName() { + return fullName; + } + + /** + * Returns the name of the character set used. + * @return String The caracter set + */ + public String getCharSetName() { + return ENCODING; + } + + /** + * Returns the CapHeight attribute of the font. + * @return int The CapHeight + */ + public int getCapHeight() { + return convertTTFUnit2PDFUnit(capHeight); + } + + /** + * Returns the XHeight attribute of the font. + * @return int The XHeight + */ + public int getXHeight() { + return convertTTFUnit2PDFUnit(xHeight); + } + + /** + * Returns the number of bytes necessary to pad the currentPosition so that a table begins + * on a 4-byte boundary. + * @param currentPosition the position to pad. + * @return int the number of bytes to pad. + */ + protected int getPadSize(int currentPosition) { + int padSize = 4 - (currentPosition % 4); + return padSize < 4 ? padSize : 0; + } + + /** + * Returns the Flags attribute of the font. + * @return int The Flags + */ + public int getFlags() { + int flags = 32; // Use Adobe Standard charset + if (italicAngle != 0) { + flags |= 64; + } + if (isFixedPitch != 0) { + flags |= 2; + } + if (hasSerifs) { + flags |= 1; + } + return flags; + } + + /** + * Returns the weight class of this font. Valid values are 100, 200....,800, 900. + * @return the weight class value (or 0 if there was no OS/2 table in the font) + */ + public int getWeightClass() { + return this.usWeightClass; + } + + /** + * Returns the StemV attribute of the font. + * @return String The StemV + */ + public String getStemV() { + return "0"; + } + + /** + * Returns the ItalicAngle attribute of the font. + * @return String The ItalicAngle + */ + public String getItalicAngle() { + String ia = Short.toString((short)(italicAngle / 0x10000)); + + // This is the correct italic angle, however only int italic + // angles are supported at the moment so this is commented out. + /* + * if ((italicAngle % 0x10000) > 0 ) + * ia=ia+(comma+Short.toString((short)((short)((italicAngle % 0x10000)*1000)/0x10000))); + */ + return ia; + } + + /** + * @return int[] The font bbox + */ + public int[] getFontBBox() { + final int[] fbb = new int[4]; + fbb[0] = convertTTFUnit2PDFUnit(fontBBox1); + fbb[1] = convertTTFUnit2PDFUnit(fontBBox2); + fbb[2] = convertTTFUnit2PDFUnit(fontBBox3); + fbb[3] = convertTTFUnit2PDFUnit(fontBBox4); + + return fbb; + } + + /** + * Returns the LowerCaseAscent attribute of the font. + * @return int The LowerCaseAscent + */ + public int getLowerCaseAscent() { + return convertTTFUnit2PDFUnit(ascender); + } + + /** + * Returns the LowerCaseDescent attribute of the font. + * @return int The LowerCaseDescent + */ + public int getLowerCaseDescent() { + return convertTTFUnit2PDFUnit(descender); + } + + /** + * Returns the index of the last character, but this is for WinAnsiEncoding + * only, so the last char is < 256. + * @return short Index of the last character (<256) + */ + public short getLastChar() { + return lastChar; + } + + /** + * Returns the index of the first character. + * @return short Index of the first character + */ + public short getFirstChar() { + return FIRST_CHAR; + } + + /** + * Returns an array of character widths. + * @return int[] The character widths + */ + public int[] getWidths() { + int[] wx = new int[mtxTab.length]; + for (int i = 0; i < wx.length; i++) { + wx[i] = convertTTFUnit2PDFUnit(mtxTab[i].getWx()); + } + + return wx; + } + + /** + * Returns an array (xMin, yMin, xMax, yMax) for a glyph. + * + * @param glyphIndex the index of the glyph + * @return int[] Array defining bounding box. + */ + public int[] getBBox(int glyphIndex) { + int[] bboxInTTFUnits = mtxTab[glyphIndex].getBoundingBox(); + int[] bbox = new int[4]; + for (int i = 0; i < 4; i++) { + bbox[i] = convertTTFUnit2PDFUnit(bboxInTTFUnits[i]); + } + return bbox; + } + + /** + * Returns the width of a given character. + * @param idx Index of the character + * @return int Standard width + */ + public int getCharWidth(int idx) { + return convertTTFUnit2PDFUnit(ansiWidth[idx]); + } + + /** + * Returns the kerning table. + * @return Map The kerning table + */ + public Map> getKerning() { + return kerningTab; + } + + /** + * Returns the ANSI kerning table. + * @return Map The ANSI kerning table + */ + public Map> getAnsiKerning() { + return ansiKerningTab; + } + + /** + * Indicates if the font may be embedded. + * @return boolean True if it may be embedded + */ + public boolean isEmbeddable() { + return isEmbeddable; + } + + /** + * Indicates whether or not the font is an OpenType + * CFF font (rather than a TrueType font). + * @return true if the font is in OpenType CFF format. + */ + public boolean isCFF() { + return this.isCFF; + } + + /** + * Read Table Directory from the current position in the + * FontFileReader and fill the global HashMap dirTabs + * with the table name (String) as key and a TTFDirTabEntry + * as value. + * @throws IOException in case of an I/O problem + */ + protected void readDirTabs() throws IOException { + int sfntVersion = fontFile.readTTFLong(); // TTF_FIXED_SIZE (4 bytes) + switch (sfntVersion) { + case 0x10000: + log.debug("sfnt version: OpenType 1.0"); + break; + case 0x4F54544F: //"OTTO" + this.isCFF = true; + log.debug("sfnt version: OpenType with CFF data"); + break; + case 0x74727565: //"true" + log.debug("sfnt version: Apple TrueType"); + break; + case 0x74797031: //"typ1" + log.debug("sfnt version: Apple Type 1 housed in sfnt wrapper"); + break; + default: + log.debug("Unknown sfnt version: " + Integer.toHexString(sfntVersion)); + break; + } + int ntabs = fontFile.readTTFUShort(); + fontFile.skip(6); // 3xTTF_USHORT_SIZE + + dirTabs = new HashMap(); + OFDirTabEntry[] pd = new OFDirTabEntry[ntabs]; + log.debug("Reading " + ntabs + " dir tables"); + + for (int i = 0; i < ntabs; i++) { + pd[i] = new OFDirTabEntry(); + String tableName = pd[i].read(fontFile); + dirTabs.put(OFTableName.getValue(tableName), pd[i]); + } + dirTabs.put(OFTableName.TABLE_DIRECTORY, + new OFDirTabEntry(0L, fontFile.getCurrentPos())); + log.debug("dir tables: " + dirTabs.keySet()); + } + + /** + * Read the "head" table, this reads the bounding box and + * sets the upem (unitsPerEM) variable + * @throws IOException in case of an I/O problem + */ + protected void readFontHeader() throws IOException { + seekTab(fontFile, OFTableName.HEAD, 2 * 4 + 2 * 4); + int flags = fontFile.readTTFUShort(); + if (log.isDebugEnabled()) { + log.debug("flags: " + flags + " - " + Integer.toString(flags, 2)); + } + upem = fontFile.readTTFUShort(); + if (log.isDebugEnabled()) { + log.debug("unit per em: " + upem); + } + + fontFile.skip(16); + + fontBBox1 = fontFile.readTTFShort(); + fontBBox2 = fontFile.readTTFShort(); + fontBBox3 = fontFile.readTTFShort(); + fontBBox4 = fontFile.readTTFShort(); + if (log.isDebugEnabled()) { + log.debug("font bbox: xMin=" + fontBBox1 + + " yMin=" + fontBBox2 + + " xMax=" + fontBBox3 + + " yMax=" + fontBBox4); + } + + fontFile.skip(2 + 2 + 2); + + locaFormat = fontFile.readTTFShort(); + } + + /** + * Read the number of glyphs from the "maxp" table + * @throws IOException in case of an I/O problem + */ + protected void getNumGlyphs() throws IOException { + seekTab(fontFile, OFTableName.MAXP, 4); + numberOfGlyphs = fontFile.readTTFUShort(); + } + + + /** + * Read the "hhea" table to find the ascender and descender and + * size of "hmtx" table, as a fixed size font might have only + * one width. + * @throws IOException in case of an I/O problem + */ + protected void readHorizontalHeader() + throws IOException { + seekTab(fontFile, OFTableName.HHEA, 4); + hheaAscender = fontFile.readTTFShort(); + hheaDescender = fontFile.readTTFShort(); + + fontFile.skip(2 + 2 + 3 * 2 + 8 * 2); + nhmtx = fontFile.readTTFUShort(); + + if (log.isDebugEnabled()) { + log.debug("hhea.Ascender: " + formatUnitsForDebug(hheaAscender)); + log.debug("hhea.Descender: " + formatUnitsForDebug(hheaDescender)); + log.debug("Number of horizontal metrics: " + nhmtx); + } + } + + /** + * Read "hmtx" table and put the horizontal metrics + * in the mtxTab array. If the number of metrics is less + * than the number of glyphs (eg fixed size fonts), extend + * the mtxTab array and fill in the missing widths + * @throws IOException in case of an I/O problem + */ + protected void readHorizontalMetrics() + throws IOException { + seekTab(fontFile, OFTableName.HMTX, 0); + + int mtxSize = Math.max(numberOfGlyphs, nhmtx); + mtxTab = new OFMtxEntry[mtxSize]; + + if (log.isTraceEnabled()) { + log.trace("*** Widths array: \n"); + } + for (int i = 0; i < mtxSize; i++) { + mtxTab[i] = new OFMtxEntry(); + } + for (int i = 0; i < nhmtx; i++) { + mtxTab[i].setWx(fontFile.readTTFUShort()); + mtxTab[i].setLsb(fontFile.readTTFUShort()); + + if (log.isTraceEnabled()) { + log.trace(" width[" + i + "] = " + + convertTTFUnit2PDFUnit(mtxTab[i].getWx()) + ";"); + } + } + + if (nhmtx < mtxSize) { + // Fill in the missing widths + int lastWidth = mtxTab[nhmtx - 1].getWx(); + for (int i = nhmtx; i < mtxSize; i++) { + mtxTab[i].setWx(lastWidth); + mtxTab[i].setLsb(fontFile.readTTFUShort()); + } + } + } + + + /** + * Read the "post" table + * containing the PostScript names of the glyphs. + */ + protected void readPostScript() throws IOException { + seekTab(fontFile, OFTableName.POST, 0); + int postFormat = fontFile.readTTFLong(); + italicAngle = fontFile.readTTFULong(); + //underlinePosition + fontFile.readTTFShort(); + //underlineThickness + fontFile.readTTFShort(); + isFixedPitch = fontFile.readTTFULong(); + + //Skip memory usage values + fontFile.skip(4 * 4); + + log.debug("PostScript format: 0x" + Integer.toHexString(postFormat)); + switch (postFormat) { + case 0x00010000: + log.debug("PostScript format 1"); + postScriptVersion = PostScriptVersion.V1; + for (int i = 0; i < MAC_GLYPH_ORDERING.length; i++) { + mtxTab[i].setName(MAC_GLYPH_ORDERING[i]); + } + break; + case 0x00020000: + log.debug("PostScript format 2"); + postScriptVersion = PostScriptVersion.V2; + int numGlyphStrings = 0; + + // Read Number of Glyphs + int l = fontFile.readTTFUShort(); + + // Read indexes + for (int i = 0; i < l; i++) { + mtxTab[i].setIndex(fontFile.readTTFUShort()); + + if (mtxTab[i].getIndex() > 257) { + //Index is not in the Macintosh standard set + numGlyphStrings++; + } + + if (log.isTraceEnabled()) { + log.trace("PostScript index: " + mtxTab[i].getIndexAsString()); + } + } + + // firstChar=minIndex; + String[] psGlyphsBuffer = new String[numGlyphStrings]; + if (log.isDebugEnabled()) { + log.debug("Reading " + numGlyphStrings + + " glyphnames, that are not in the standard Macintosh" + + " set. Total number of glyphs=" + l); + } + for (int i = 0; i < psGlyphsBuffer.length; i++) { + psGlyphsBuffer[i] = fontFile.readTTFString(fontFile.readTTFUByte()); + } + + //Set glyph names + for (int i = 0; i < l; i++) { + if (mtxTab[i].getIndex() < MAC_GLYPH_ORDERING.length) { + mtxTab[i].setName(MAC_GLYPH_ORDERING[mtxTab[i].getIndex()]); + } else { + if (!mtxTab[i].isIndexReserved()) { + int k = mtxTab[i].getIndex() - MAC_GLYPH_ORDERING.length; + + if (log.isTraceEnabled()) { + log.trace(k + " i=" + i + " mtx=" + mtxTab.length + + " ps=" + psGlyphsBuffer.length); + } + + mtxTab[i].setName(psGlyphsBuffer[k]); + } + } + } + + break; + case 0x00030000: + // PostScript format 3 contains no glyph names + log.debug("PostScript format 3"); + postScriptVersion = PostScriptVersion.V3; + break; + default: + log.error("Unknown PostScript format: " + postFormat); + postScriptVersion = PostScriptVersion.UNKNOWN; + } + } + + + /** + * Read the "OS/2" table + */ + protected void readOS2() throws IOException { + // Check if font is embeddable + OFDirTabEntry os2Entry = dirTabs.get(OFTableName.OS2); + if (os2Entry != null) { + seekTab(fontFile, OFTableName.OS2, 0); + int version = fontFile.readTTFUShort(); + if (log.isDebugEnabled()) { + log.debug("OS/2 table: version=" + version + + ", offset=" + os2Entry.getOffset() + ", len=" + os2Entry.getLength()); + } + fontFile.skip(2); //xAvgCharWidth + this.usWeightClass = fontFile.readTTFUShort(); + + // usWidthClass + fontFile.skip(2); + + int fsType = fontFile.readTTFUShort(); + if (fsType == 2) { + isEmbeddable = false; + } else { + isEmbeddable = true; + } + fontFile.skip(11 * 2); + fontFile.skip(10); //panose array + fontFile.skip(4 * 4); //unicode ranges + fontFile.skip(4); + fontFile.skip(3 * 2); + int v; + os2Ascender = fontFile.readTTFShort(); //sTypoAscender + os2Descender = fontFile.readTTFShort(); //sTypoDescender + if (log.isDebugEnabled()) { + log.debug("sTypoAscender: " + os2Ascender + + " -> internal " + convertTTFUnit2PDFUnit(os2Ascender)); + log.debug("sTypoDescender: " + os2Descender + + " -> internal " + convertTTFUnit2PDFUnit(os2Descender)); + } + v = fontFile.readTTFShort(); //sTypoLineGap + if (log.isDebugEnabled()) { + log.debug("sTypoLineGap: " + v); + } + v = fontFile.readTTFUShort(); //usWinAscent + if (log.isDebugEnabled()) { + log.debug("usWinAscent: " + formatUnitsForDebug(v)); + } + v = fontFile.readTTFUShort(); //usWinDescent + if (log.isDebugEnabled()) { + log.debug("usWinDescent: " + formatUnitsForDebug(v)); + } + + //version 1 OS/2 table might end here + if (os2Entry.getLength() >= 78 + (2 * 4) + (2 * 2)) { + fontFile.skip(2 * 4); + this.os2xHeight = fontFile.readTTFShort(); //sxHeight + this.os2CapHeight = fontFile.readTTFShort(); //sCapHeight + if (log.isDebugEnabled()) { + log.debug("sxHeight: " + this.os2xHeight); + log.debug("sCapHeight: " + this.os2CapHeight); + } + } + + } else { + isEmbeddable = true; + } + } + + /** + * Read the "PCLT" table to find xHeight and capHeight. + * @throws IOException In case of a I/O problem + */ + protected boolean readPCLT() throws IOException { + OFDirTabEntry dirTab = dirTabs.get(OFTableName.PCLT); + if (dirTab != null) { + fontFile.seekSet(dirTab.getOffset() + 4 + 4 + 2); + xHeight = fontFile.readTTFUShort(); + log.debug("xHeight from PCLT: " + formatUnitsForDebug(xHeight)); + fontFile.skip(2 * 2); + capHeight = fontFile.readTTFUShort(); + log.debug("capHeight from PCLT: " + formatUnitsForDebug(capHeight)); + fontFile.skip(2 + 16 + 8 + 6 + 1 + 1); + + int serifStyle = fontFile.readTTFUByte(); + serifStyle = serifStyle >> 6; + serifStyle = serifStyle & 3; + if (serifStyle == 1) { + hasSerifs = false; + } else { + hasSerifs = true; + } + return true; + } else { + return false; + } + } + + /** + * Determines the right source for the ascender and descender values. The problem here is + * that the interpretation of these values is not the same for every font. There doesn't seem + * to be a uniform definition of an ascender and a descender. In some fonts + * the hhea values are defined after the Apple interpretation, but not in every font. The + * same problem is in the OS/2 table. FOP needs the ascender and descender to determine the + * baseline so we need values which add up more or less to the "em box". However, due to + * accent modifiers a character can grow beyond the em box. + */ + protected void determineAscDesc() { + int hheaBoxHeight = hheaAscender - hheaDescender; + int os2BoxHeight = os2Ascender - os2Descender; + if (os2Ascender > 0 && os2BoxHeight <= upem) { + ascender = os2Ascender; + descender = os2Descender; + } else if (hheaAscender > 0 && hheaBoxHeight <= upem) { + ascender = hheaAscender; + descender = hheaDescender; + } else { + if (os2Ascender > 0) { + //Fall back to info from OS/2 if possible + ascender = os2Ascender; + descender = os2Descender; + } else { + ascender = hheaAscender; + descender = hheaDescender; + } + } + + if (log.isDebugEnabled()) { + log.debug("Font box height: " + (ascender - descender)); + if (ascender - descender > upem) { + log.debug("Ascender and descender together are larger than the em box."); + } + } + } + + protected void guessVerticalMetricsFromGlyphBBox() { + // Approximate capHeight from height of "H" + // It's most unlikely that a font misses the PCLT table + // This also assumes that postscriptnames exists ("H") + // Should look it up in the cmap (that wouldn't help + // for charsets without H anyway...) + // Same for xHeight with the letter "x" + int localCapHeight = 0; + int localXHeight = 0; + int localAscender = 0; + int localDescender = 0; + for (int i = 0; i < mtxTab.length; i++) { + if ("H".equals(mtxTab[i].getName())) { + localCapHeight = mtxTab[i].getBoundingBox()[3]; + } else if ("x".equals(mtxTab[i].getName())) { + localXHeight = mtxTab[i].getBoundingBox()[3]; + } else if ("d".equals(mtxTab[i].getName())) { + localAscender = mtxTab[i].getBoundingBox()[3]; + } else if ("p".equals(mtxTab[i].getName())) { + localDescender = mtxTab[i].getBoundingBox()[1]; + } else { + // OpenType Fonts with a version 3.0 "post" table don't have glyph names. + // Use Unicode indices instead. + List unicodeIndex = mtxTab[i].getUnicodeIndex(); + if (unicodeIndex.size() > 0) { + //Only the first index is used + char ch = (char)((Integer)unicodeIndex.get(0)).intValue(); + if (ch == 'H') { + localCapHeight = mtxTab[i].getBoundingBox()[3]; + } else if (ch == 'x') { + localXHeight = mtxTab[i].getBoundingBox()[3]; + } else if (ch == 'd') { + localAscender = mtxTab[i].getBoundingBox()[3]; + } else if (ch == 'p') { + localDescender = mtxTab[i].getBoundingBox()[1]; + } + } + } + } + if (log.isDebugEnabled()) { + log.debug("Ascender from glyph 'd': " + formatUnitsForDebug(localAscender)); + log.debug("Descender from glyph 'p': " + formatUnitsForDebug(localDescender)); + } + if (ascender - descender > upem) { + log.debug("Replacing specified ascender/descender with derived values to get values" + + " which fit in the em box."); + ascender = localAscender; + descender = localDescender; + } + + if (log.isDebugEnabled()) { + log.debug("xHeight from glyph 'x': " + formatUnitsForDebug(localXHeight)); + log.debug("CapHeight from glyph 'H': " + formatUnitsForDebug(localCapHeight)); + } + if (capHeight == 0) { + capHeight = localCapHeight; + if (capHeight == 0) { + capHeight = os2CapHeight; + } + if (capHeight == 0) { + log.debug("capHeight value could not be determined." + + " The font may not work as expected."); + } + } + if (xHeight == 0) { + xHeight = localXHeight; + if (xHeight == 0) { + xHeight = os2xHeight; + } + if (xHeight == 0) { + log.debug("xHeight value could not be determined." + + " The font may not work as expected."); + } + } + } + + /** + * Read the kerning table, create a table for both CIDs and + * winAnsiEncoding. + * @throws IOException In case of a I/O problem + */ + protected void readKerning() throws IOException { + // Read kerning + kerningTab = new HashMap>(); + ansiKerningTab = new HashMap>(); + OFDirTabEntry dirTab = dirTabs.get(OFTableName.KERN); + if (dirTab != null) { + seekTab(fontFile, OFTableName.KERN, 2); + for (int n = fontFile.readTTFUShort(); n > 0; n--) { + fontFile.skip(2 * 2); + int k = fontFile.readTTFUShort(); + if (!((k & 1) != 0) || (k & 2) != 0 || (k & 4) != 0) { + return; + } + if ((k >> 8) != 0) { + continue; + } + + k = fontFile.readTTFUShort(); + fontFile.skip(3 * 2); + while (k-- > 0) { + int i = fontFile.readTTFUShort(); + int j = fontFile.readTTFUShort(); + int kpx = fontFile.readTTFShort(); + if (kpx != 0) { + // CID kerning table entry, using unicode indexes + final Integer iObj = glyphToUnicode(i); + final Integer u2 = glyphToUnicode(j); + if (iObj == null) { + // happens for many fonts (Ubuntu font set), + // stray entries in the kerning table?? + log.debug("Ignoring kerning pair because no Unicode index was" + + " found for the first glyph " + i); + } else if (u2 == null) { + log.debug("Ignoring kerning pair because Unicode index was" + + " found for the second glyph " + i); + } else { + Map adjTab = kerningTab.get(iObj); + if (adjTab == null) { + adjTab = new HashMap(); + } + adjTab.put(u2, new Integer(convertTTFUnit2PDFUnit(kpx))); + kerningTab.put(iObj, adjTab); + } + } + } + } + + // Create winAnsiEncoded kerning table from kerningTab + // (could probably be simplified, for now we remap back to CID indexes and + // then to winAnsi) + for (Integer unicodeKey1 : kerningTab.keySet()) { + Integer cidKey1 = unicodeToGlyph(unicodeKey1.intValue()); + Map akpx = new HashMap(); + Map ckpx = kerningTab.get(unicodeKey1); + + for (Integer unicodeKey2 : ckpx.keySet()) { + Integer cidKey2 = unicodeToGlyph(unicodeKey2.intValue()); + Integer kern = ckpx.get(unicodeKey2); + + Iterator uniMap = mtxTab[cidKey2.intValue()].getUnicodeIndex().listIterator(); + while (uniMap.hasNext()) { + Integer unicodeKey = (Integer)uniMap.next(); + Integer[] ansiKeys = unicodeToWinAnsi(unicodeKey.intValue()); + for (int u = 0; u < ansiKeys.length; u++) { + akpx.put(ansiKeys[u], kern); + } + } + } + + if (akpx.size() > 0) { + Iterator uniMap = mtxTab[cidKey1.intValue()].getUnicodeIndex().listIterator(); + while (uniMap.hasNext()) { + Integer unicodeKey = (Integer)uniMap.next(); + Integer[] ansiKeys = unicodeToWinAnsi(unicodeKey.intValue()); + for (int u = 0; u < ansiKeys.length; u++) { + ansiKerningTab.put(ansiKeys[u], akpx); + } + } + } + } + } + } + + /** + * Streams a font. + * @param ttfOut The interface for streaming TrueType tables. + * @exception IOException file write error + */ + public void stream(TTFOutputStream ttfOut) throws IOException { + SortedSet> sortedDirTabs = sortDirTabMap(dirTabs); + byte[] file = fontFile.getAllBytes(); + TTFTableOutputStream tableOut = ttfOut.getTableOutputStream(); + TTFGlyphOutputStream glyphOut = ttfOut.getGlyphOutputStream(); + ttfOut.startFontStream(); + for (Map.Entry entry : sortedDirTabs) { + int offset = (int) entry.getValue().getOffset(); + int paddedLength = (int) entry.getValue().getLength(); + paddedLength += getPadSize(offset + paddedLength); + if (entry.getKey().equals(OFTableName.GLYF)) { + streamGlyf(glyphOut, file, offset, paddedLength); + } else { + tableOut.streamTable(file, offset, paddedLength); + } + } + ttfOut.endFontStream(); + } + + private void streamGlyf(TTFGlyphOutputStream glyphOut, byte[] fontFile, int tableOffset, + int tableLength) throws IOException { + //Stream all but the last glyph + int glyphStart = 0; + int glyphEnd = 0; + glyphOut.startGlyphStream(); + for (int i = 0; i < mtxTab.length - 1; i++) { + glyphStart = (int) mtxTab[i].getOffset() + tableOffset; + glyphEnd = (int) mtxTab[i + 1].getOffset() + tableOffset; + glyphOut.streamGlyph(fontFile, glyphStart, glyphEnd - glyphStart); + } + glyphOut.streamGlyph(fontFile, glyphEnd, (tableOffset + tableLength) - glyphEnd); + glyphOut.endGlyphStream(); + } + + /** + * Returns the order in which the tables in a TrueType font should be written to file. + * @param directoryTabs the map that is to be sorted. + * @return TTFTablesNames[] an array of table names sorted in the order they should appear in + * the TTF file. + */ + SortedSet> + sortDirTabMap(Map directoryTabs) { + SortedSet> sortedSet + = new TreeSet>( + new Comparator>() { + + public int compare(Entry o1, + Entry o2) { + return (int) (o1.getValue().getOffset() - o2.getValue().getOffset()); + } + }); + sortedSet.addAll(directoryTabs.entrySet()); + return sortedSet; + } + + /** + * Returns this font's character to glyph mapping. + * + * @return the font's cmap + */ + public List getCMaps() { + return cmaps; + } + + /** + * Check if this is a TrueType collection and that the given + * name exists in the collection. + * If it does, set offset in fontfile to the beginning of + * the Table Directory for that font. + * @param name The name to check + * @return True if not collection or font name present, false otherwise + * @throws IOException In case of an I/O problem + */ + protected final boolean checkTTC(String tag, String name) throws IOException { + if ("ttcf".equals(tag)) { + // This is a TrueType Collection + fontFile.skip(4); + + // Read directory offsets + int numDirectories = (int)fontFile.readTTFULong(); + // int numDirectories=in.readTTFUShort(); + long[] dirOffsets = new long[numDirectories]; + for (int i = 0; i < numDirectories; i++) { + dirOffsets[i] = fontFile.readTTFULong(); + } + + log.info("This is a TrueType collection file with " + + numDirectories + " fonts"); + log.info("Containing the following fonts: "); + // Read all the directories and name tables to check + // If the font exists - this is a bit ugly, but... + boolean found = false; + + // Iterate through all name tables even if font + // Is found, just to show all the names + long dirTabOffset = 0; + for (int i = 0; (i < numDirectories); i++) { + fontFile.seekSet(dirOffsets[i]); + readDirTabs(); + + readName(); + + if (fullName.equals(name)) { + found = true; + dirTabOffset = dirOffsets[i]; + log.info(fullName + " <-- selected"); + } else { + log.info(fullName); + } + + // Reset names + notice = ""; + fullName = ""; + familyNames.clear(); + postScriptName = ""; + subFamilyName = ""; + } + + fontFile.seekSet(dirTabOffset); + return found; + } else { + fontFile.seekSet(0); + return true; + } + } + + /** + * Return TTC font names + * @param in FontFileReader to read from + * @return True if not collection or font name present, false otherwise + * @throws IOException In case of an I/O problem + */ + public final List getTTCnames(FontFileReader in) throws IOException { + this.fontFile = in; + + List fontNames = new ArrayList(); + String tag = in.readTTFString(4); + + if ("ttcf".equals(tag)) { + // This is a TrueType Collection + in.skip(4); + + // Read directory offsets + int numDirectories = (int)in.readTTFULong(); + long[] dirOffsets = new long[numDirectories]; + for (int i = 0; i < numDirectories; i++) { + dirOffsets[i] = in.readTTFULong(); + } + + log.info("This is a TrueType collection file with " + + numDirectories + " fonts"); + log.info("Containing the following fonts: "); + + for (int i = 0; (i < numDirectories); i++) { + in.seekSet(dirOffsets[i]); + readDirTabs(); + + readName(); + + log.info(fullName); + fontNames.add(fullName); + + // Reset names + notice = ""; + fullName = ""; + familyNames.clear(); + postScriptName = ""; + subFamilyName = ""; + } + + in.seekSet(0); + return fontNames; + } else { + log.error("Not a TTC!"); + return null; + } + } + + /* + * Helper classes, they are not very efficient, but that really + * doesn't matter... + */ + private Integer[] unicodeToWinAnsi(int unicode) { + List ret = new ArrayList(); + for (int i = 32; i < Glyphs.WINANSI_ENCODING.length; i++) { + if (unicode == Glyphs.WINANSI_ENCODING[i]) { + ret.add(new Integer(i)); + } + } + return ret.toArray(new Integer[0]); + } + + /** + * Dumps a few informational values to System.out. + */ + public void printStuff() { + System.out.println("Font name: " + postScriptName); + System.out.println("Full name: " + fullName); + System.out.println("Family name: " + familyNames); + System.out.println("Subfamily name: " + subFamilyName); + System.out.println("Notice: " + notice); + System.out.println("xHeight: " + convertTTFUnit2PDFUnit(xHeight)); + System.out.println("capheight: " + convertTTFUnit2PDFUnit(capHeight)); + + int italic = (int)(italicAngle >> 16); + System.out.println("Italic: " + italic); + System.out.print("ItalicAngle: " + (short)(italicAngle / 0x10000)); + if ((italicAngle % 0x10000) > 0) { + System.out.print("." + + (short)((italicAngle % 0x10000) * 1000) + / 0x10000); + } + System.out.println(); + System.out.println("Ascender: " + convertTTFUnit2PDFUnit(ascender)); + System.out.println("Descender: " + convertTTFUnit2PDFUnit(descender)); + System.out.println("FontBBox: [" + convertTTFUnit2PDFUnit(fontBBox1) + + " " + convertTTFUnit2PDFUnit(fontBBox2) + " " + + convertTTFUnit2PDFUnit(fontBBox3) + " " + + convertTTFUnit2PDFUnit(fontBBox4) + "]"); + } + + private String formatUnitsForDebug(int units) { + return units + " -> " + convertTTFUnit2PDFUnit(units) + " internal units"; + } + + /** + * Map a glyph index to the corresponding unicode code point + * + * @param glyphIndex + * @return unicode code point + */ + private Integer glyphToUnicode(int glyphIndex) { + return glyphToUnicodeMap.get(new Integer(glyphIndex)); + } + + /** + * Map a unicode code point to the corresponding glyph index + * + * @param unicodeIndex unicode code point + * @return glyph index + */ + private Integer unicodeToGlyph(int unicodeIndex) throws IOException { + final Integer result + = unicodeToGlyphMap.get(new Integer(unicodeIndex)); + if (result == null) { + throw new IOException( + "Glyph index not found for unicode value " + unicodeIndex); + } + return result; + } + + String getGlyphName(int glyphIndex) { + return mtxTab[glyphIndex].getName(); + } + + /** + * Determine if advanced (typographic) table is present. + * @return true if advanced (typographic) table is present + */ + public boolean hasAdvancedTable() { + if (advancedTableReader != null) { + return advancedTableReader.hasAdvancedTable(); + } else { + return false; + } + } + + /** + * Returns the GDEF table or null if none present. + * @return the GDEF table + */ + public GlyphDefinitionTable getGDEF() { + if (advancedTableReader != null) { + return advancedTableReader.getGDEF(); + } else { + return null; + } + } + + /** + * Returns the GSUB table or null if none present. + * @return the GSUB table + */ + public GlyphSubstitutionTable getGSUB() { + if (advancedTableReader != null) { + return advancedTableReader.getGSUB(); + } else { + return null; + } + } + + /** + * Returns the GPOS table or null if none present. + * @return the GPOS table + */ + public GlyphPositioningTable getGPOS() { + if (advancedTableReader != null) { + return advancedTableReader.getGPOS(); + } else { + return null; + } + } + + /** + * Static main method to get info about a TrueType font. + * @param args The command line arguments + */ + public static void main(String[] args) { + InputStream stream = null; + try { + boolean useKerning = true; + boolean useAdvanced = true; + + stream = new FileInputStream(args[0]); + FontFileReader reader = new FontFileReader(stream); + + String name = null; + if (args.length >= 2) { + name = args[1]; + } + + String header = OFFontLoader.readHeader(reader); + boolean isCFF = header.equals("OTTO"); + OpenFont otfFile = (isCFF) ? new OTFFile() : new TTFFile(useKerning, useAdvanced); + otfFile.readFont(reader, header, name); + otfFile.printStuff(); + + } catch (IOException ioe) { + System.err.println("Problem reading font: " + ioe.toString()); + ioe.printStackTrace(System.err); + } finally { + IOUtils.closeQuietly(stream); + } + } +} diff --git a/src/java/org/apache/fop/fonts/truetype/TTFFile.java b/src/java/org/apache/fop/fonts/truetype/TTFFile.java index 2e78ef7f0..52df45ffb 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFFile.java +++ b/src/java/org/apache/fop/fonts/truetype/TTFFile.java @@ -19,1409 +19,34 @@ package org.apache.fop.fonts.truetype; -import java.io.FileInputStream; import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.BitSet; -import java.util.Comparator; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; -import org.apache.commons.io.IOUtils; -import org.apache.commons.logging.Log; -import org.apache.commons.logging.LogFactory; - -import org.apache.xmlgraphics.fonts.Glyphs; - -import org.apache.fop.complexscripts.fonts.AdvancedTypographicTableFormatException; -import org.apache.fop.complexscripts.fonts.GlyphDefinitionTable; -import org.apache.fop.complexscripts.fonts.GlyphPositioningTable; -import org.apache.fop.complexscripts.fonts.GlyphSubstitutionTable; -import org.apache.fop.complexscripts.fonts.OTFAdvancedTypographicTableReader; -import org.apache.fop.fonts.CMapSegment; -import org.apache.fop.fonts.FontUtil; - -/** - * Reads a TrueType file or a TrueType Collection. - * The TrueType spec can be found at the Microsoft. - * Typography site: http://www.microsoft.com/truetype/ - */ -public class TTFFile { - - static final byte NTABS = 24; - static final int MAX_CHAR_CODE = 255; - static final int ENC_BUF_SIZE = 1024; - - private static final String[] MAC_GLYPH_ORDERING = { - /* 0x000 */ - ".notdef", ".null", "nonmarkingreturn", "space", - "exclam", "quotedbl", "numbersign", "dollar", - "percent", "ampersand", "quotesingle", "parenleft", - "parenright", "asterisk", "plus", "comma", - /* 0x010 */ - "hyphen", "period", "slash", "zero", - "one", "two", "three", "four", - "five", "six", "seven", "eight", - "nine", "colon", "semicolon", "less", - /* 0x020 */ - "equal", "greater", "question", "at", - "A", "B", "C", "D", - "E", "F", "G", "H", - "I", "J", "K", "L", - /* 0x030 */ - "M", "N", "O", "P", - "Q", "R", "S", "T", - "U", "V", "W", "X", - "Y", "Z", "bracketleft", "backslash", - /* 0x040 */ - "bracketright", "asciicircum", "underscore", "grave", - "a", "b", "c", "d", - "e", "f", "g", "h", - "i", "j", "k", "l", - /* 0x050 */ - "m", "n", "o", "p", - "q", "r", "s", "t", - "u", "v", "w", "x", - "y", "z", "braceleft", "bar", - /* 0x060 */ - "braceright", "asciitilde", "Adieresis", "Aring", - "Ccedilla", "Eacute", "Ntilde", "Odieresis", - "Udieresis", "aacute", "agrave", "acircumflex", - "adieresis", "atilde", "aring", "ccedilla", - /* 0x070 */ - "eacute", "egrave", "ecircumflex", "edieresis", - "iacute", "igrave", "icircumflex", "idieresis", - "ntilde", "oacute", "ograve", "ocircumflex", - "odieresis", "otilde", "uacute", "ugrave", - /* 0x080 */ - "ucircumflex", "udieresis", "dagger", "degree", - "cent", "sterling", "section", "bullet", - "paragraph", "germandbls", "registered", "copyright", - "trademark", "acute", "dieresis", "notequal", - /* 0x090 */ - "AE", "Oslash", "infinity", "plusminus", - "lessequal", "greaterequal", "yen", "mu", - "partialdiff", "summation", "product", "pi", - "integral", "ordfeminine", "ordmasculine", "Omega", - /* 0x0A0 */ - "ae", "oslash", "questiondown", "exclamdown", - "logicalnot", "radical", "florin", "approxequal", - "Delta", "guillemotleft", "guillemotright", "ellipsis", - "nonbreakingspace", "Agrave", "Atilde", "Otilde", - /* 0x0B0 */ - "OE", "oe", "endash", "emdash", - "quotedblleft", "quotedblright", "quoteleft", "quoteright", - "divide", "lozenge", "ydieresis", "Ydieresis", - "fraction", "currency", "guilsinglleft", "guilsinglright", - /* 0x0C0 */ - "fi", "fl", "daggerdbl", "periodcentered", - "quotesinglbase", "quotedblbase", "perthousand", "Acircumflex", - "Ecircumflex", "Aacute", "Edieresis", "Egrave", - "Iacute", "Icircumflex", "Idieresis", "Igrave", - /* 0x0D0 */ - "Oacute", "Ocircumflex", "apple", "Ograve", - "Uacute", "Ucircumflex", "Ugrave", "dotlessi", - "circumflex", "tilde", "macron", "breve", - "dotaccent", "ring", "cedilla", "hungarumlaut", - /* 0x0E0 */ - "ogonek", "caron", "Lslash", "lslash", - "Scaron", "scaron", "Zcaron", "zcaron", - "brokenbar", "Eth", "eth", "Yacute", - "yacute", "Thorn", "thorn", "minus", - /* 0x0F0 */ - "multiply", "onesuperior", "twosuperior", "threesuperior", - "onehalf", "onequarter", "threequarters", "franc", - "Gbreve", "gbreve", "Idotaccent", "Scedilla", - "scedilla", "Cacute", "cacute", "Ccaron", - /* 0x100 */ - "ccaron", "dcroat" - }; - - /** The FontFileReader used to read this TrueType font. */ - protected FontFileReader fontFile; - - /** Set to true to get even more debug output than with level DEBUG */ - public static final boolean TRACE_ENABLED = false; - - private final String encoding = "WinAnsiEncoding"; // Default encoding - - private final short firstChar = 0; - - private boolean useKerning = false; - - private boolean isEmbeddable = true; - private boolean hasSerifs = true; - /** - * Table directory - */ - protected Map dirTabs; - private Map> kerningTab; // for CIDs - private Map> ansiKerningTab; // For winAnsiEncoding - private List cmaps; - private Set unicodeMappings; - - private int upem; // unitsPerEm from "head" table - private int nhmtx; // Number of horizontal metrics - private PostScriptVersion postScriptVersion; - private int locaFormat; - /** - * Offset to last loca - */ - protected long lastLoca = 0; - private int numberOfGlyphs; // Number of glyphs in font (read from "maxp" table) - - /** - * Contains glyph data - */ - protected TTFMtxEntry[] mtxTab; // Contains glyph data - - private String postScriptName = ""; - private String fullName = ""; - private String notice = ""; - private Set familyNames = new HashSet(); - private String subFamilyName = ""; - - private long italicAngle = 0; - private long isFixedPitch = 0; - private int fontBBox1 = 0; - private int fontBBox2 = 0; - private int fontBBox3 = 0; - private int fontBBox4 = 0; - private int capHeight = 0; - private int os2CapHeight = 0; - private int underlinePosition = 0; - private int underlineThickness = 0; - private int xHeight = 0; - private int os2xHeight = 0; - //Effective ascender/descender - private int ascender = 0; - private int descender = 0; - //Ascender/descender from hhea table - private int hheaAscender = 0; - private int hheaDescender = 0; - //Ascender/descender from OS/2 table - private int os2Ascender = 0; - private int os2Descender = 0; - private int usWeightClass = 0; - - private short lastChar = 0; - - private int[] ansiWidth; - private Map> ansiIndex; - - // internal mapping of glyph indexes to unicode indexes - // used for quick mappings in this class - private final Map glyphToUnicodeMap = new HashMap(); - private final Map unicodeToGlyphMap = new HashMap(); - - private TTFDirTabEntry currentDirTab; - - private boolean isCFF; - - // advanced typographic table support - private boolean useAdvanced = false; - private OTFAdvancedTypographicTableReader advancedTableReader; - - /** - * logging instance - */ - protected Log log = LogFactory.getLog(TTFFile.class); - - public TTFFile() { - this(true, false); - } - - /** - * Constructor - * @param useKerning true if kerning data should be loaded - * @param useAdvanced true if advanced typographic tables should be loaded - */ - public TTFFile(boolean useKerning, boolean useAdvanced) { - this.useKerning = useKerning; - this.useAdvanced = useAdvanced; - } - - /** - * Key-value helper class. - */ - final class UnicodeMapping implements Comparable { - - private final int unicodeIndex; - private final int glyphIndex; - - UnicodeMapping(int glyphIndex, int unicodeIndex) { - this.unicodeIndex = unicodeIndex; - this.glyphIndex = glyphIndex; - glyphToUnicodeMap.put(new Integer(glyphIndex), new Integer(unicodeIndex)); - unicodeToGlyphMap.put(new Integer(unicodeIndex), new Integer(glyphIndex)); - } - - /** - * Returns the glyphIndex. - * @return the glyph index - */ - public int getGlyphIndex() { - return glyphIndex; - } - - /** - * Returns the unicodeIndex. - * @return the Unicode index - */ - public int getUnicodeIndex() { - return unicodeIndex; - } - - - /** {@inheritDoc} */ - public int hashCode() { - int hc = unicodeIndex; - hc = 19 * hc + (hc ^ glyphIndex); - return hc; - } - - /** {@inheritDoc} */ - public boolean equals(Object o) { - if (o instanceof UnicodeMapping) { - UnicodeMapping m = (UnicodeMapping) o; - if (unicodeIndex != m.unicodeIndex) { - return false; - } else { - return (glyphIndex == m.glyphIndex); - } - } else { - return false; - } - } - - /** {@inheritDoc} */ - public int compareTo(Object o) { - if (o instanceof UnicodeMapping) { - UnicodeMapping m = (UnicodeMapping) o; - if (unicodeIndex > m.unicodeIndex) { - return 1; - } else if (unicodeIndex < m.unicodeIndex) { - return -1; - } else { - return 0; - } - } else { - return -1; - } - } - } - - /** - * Version of the PostScript table (post) contained in this font. - */ - public static enum PostScriptVersion { - /** PostScript table version 1.0. */ - V1, - /** PostScript table version 2.0. */ - V2, - /** PostScript table version 3.0. */ - V3, - /** Unknown version of the PostScript table. */ - UNKNOWN; - } - - /** - * Obtain directory table entry. - * @param name (tag) of entry - * @return a directory table entry or null if none found - */ - public TTFDirTabEntry getDirectoryEntry(TTFTableName name) { - return dirTabs.get(name); - } - - /** - * Position inputstream to position indicated - * in the dirtab offset + offset - * @param in font file reader - * @param tableName (tag) of table - * @param offset from start of table - * @return true if seek succeeded - * @throws IOException if I/O exception occurs during seek - */ - public boolean seekTab(FontFileReader in, TTFTableName tableName, - long offset) throws IOException { - TTFDirTabEntry dt = dirTabs.get(tableName); - if (dt == null) { - log.error("Dirtab " + tableName.getName() + " not found."); - return false; - } else { - in.seekSet(dt.getOffset() + offset); - this.currentDirTab = dt; - } - return true; - } - - /** - * Convert from truetype unit to pdf unit based on the - * unitsPerEm field in the "head" table - * @param n truetype unit - * @return pdf unit - */ - public int convertTTFUnit2PDFUnit(int n) { - int ret; - if (n < 0) { - long rest1 = n % upem; - long storrest = 1000 * rest1; - long ledd2 = (storrest != 0 ? rest1 / storrest : 0); - ret = -((-1000 * n) / upem - (int)ledd2); - } else { - ret = (n / upem) * 1000 + ((n % upem) * 1000) / upem; - } - - return ret; - } - - /** - * Read the cmap table, - * return false if the table is not present or only unsupported - * tables are present. Currently only unicode cmaps are supported. - * Set the unicodeIndex in the TTFMtxEntries and fills in the - * cmaps vector. - */ - private boolean readCMAP() throws IOException { - - unicodeMappings = new java.util.TreeSet(); - - seekTab(fontFile, TTFTableName.CMAP, 2); - int numCMap = fontFile.readTTFUShort(); // Number of cmap subtables - long cmapUniOffset = 0; - long symbolMapOffset = 0; - - if (log.isDebugEnabled()) { - log.debug(numCMap + " cmap tables"); - } - - //Read offset for all tables. We are only interested in the unicode table - for (int i = 0; i < numCMap; i++) { - int cmapPID = fontFile.readTTFUShort(); - int cmapEID = fontFile.readTTFUShort(); - long cmapOffset = fontFile.readTTFLong(); - - if (log.isDebugEnabled()) { - log.debug("Platform ID: " + cmapPID + " Encoding: " + cmapEID); - } - - if (cmapPID == 3 && cmapEID == 1) { - cmapUniOffset = cmapOffset; - } - if (cmapPID == 3 && cmapEID == 0) { - symbolMapOffset = cmapOffset; - } - } - - if (cmapUniOffset > 0) { - return readUnicodeCmap(cmapUniOffset, 1); - } else if (symbolMapOffset > 0) { - return readUnicodeCmap(symbolMapOffset, 0); - } else { - log.fatal("Unsupported TrueType font: No Unicode or Symbol cmap table" - + " not present. Aborting"); - return false; - } - } - - private boolean readUnicodeCmap( - long cmapUniOffset, int encodingID) - throws IOException { - //Read CMAP table and correct mtxTab.index - int mtxPtr = 0; - - // Read unicode cmap - seekTab(fontFile, TTFTableName.CMAP, cmapUniOffset); - int cmapFormat = fontFile.readTTFUShort(); - /*int cmap_length =*/ fontFile.readTTFUShort(); //skip cmap length - - if (log.isDebugEnabled()) { - log.debug("CMAP format: " + cmapFormat); - } - - if (cmapFormat == 4) { - fontFile.skip(2); // Skip version number - int cmapSegCountX2 = fontFile.readTTFUShort(); - int cmapSearchRange = fontFile.readTTFUShort(); - int cmapEntrySelector = fontFile.readTTFUShort(); - int cmapRangeShift = fontFile.readTTFUShort(); - - if (log.isDebugEnabled()) { - log.debug("segCountX2 : " + cmapSegCountX2); - log.debug("searchRange : " + cmapSearchRange); - log.debug("entrySelector: " + cmapEntrySelector); - log.debug("rangeShift : " + cmapRangeShift); - } - - - int[] cmapEndCounts = new int[cmapSegCountX2 / 2]; - int[] cmapStartCounts = new int[cmapSegCountX2 / 2]; - int[] cmapDeltas = new int[cmapSegCountX2 / 2]; - int[] cmapRangeOffsets = new int[cmapSegCountX2 / 2]; - - for (int i = 0; i < (cmapSegCountX2 / 2); i++) { - cmapEndCounts[i] = fontFile.readTTFUShort(); - } - - fontFile.skip(2); // Skip reservedPad - - for (int i = 0; i < (cmapSegCountX2 / 2); i++) { - cmapStartCounts[i] = fontFile.readTTFUShort(); - } - - for (int i = 0; i < (cmapSegCountX2 / 2); i++) { - cmapDeltas[i] = fontFile.readTTFShort(); - } - - //int startRangeOffset = in.getCurrentPos(); - - for (int i = 0; i < (cmapSegCountX2 / 2); i++) { - cmapRangeOffsets[i] = fontFile.readTTFUShort(); - } - - int glyphIdArrayOffset = fontFile.getCurrentPos(); - - BitSet eightBitGlyphs = new BitSet(256); - - // Insert the unicode id for the glyphs in mtxTab - // and fill in the cmaps ArrayList - - for (int i = 0; i < cmapStartCounts.length; i++) { - - if (log.isTraceEnabled()) { - log.trace(i + ": " + cmapStartCounts[i] - + " - " + cmapEndCounts[i]); - } - if (log.isDebugEnabled()) { - if (isInPrivateUseArea(cmapStartCounts[i], cmapEndCounts[i])) { - log.debug("Font contains glyphs in the Unicode private use area: " - + Integer.toHexString(cmapStartCounts[i]) + " - " - + Integer.toHexString(cmapEndCounts[i])); - } - } - - for (int j = cmapStartCounts[i]; j <= cmapEndCounts[i]; j++) { - - // Update lastChar - if (j < 256 && j > lastChar) { - lastChar = (short)j; - } - - if (j < 256) { - eightBitGlyphs.set(j); - } - - if (mtxPtr < mtxTab.length) { - int glyphIdx; - // the last character 65535 = .notdef - // may have a range offset - if (cmapRangeOffsets[i] != 0 && j != 65535) { - int glyphOffset = glyphIdArrayOffset - + ((cmapRangeOffsets[i] / 2) - + (j - cmapStartCounts[i]) - + (i) - - cmapSegCountX2 / 2) * 2; - fontFile.seekSet(glyphOffset); - glyphIdx = (fontFile.readTTFUShort() + cmapDeltas[i]) - & 0xffff; - - unicodeMappings.add(new UnicodeMapping(glyphIdx, j)); - mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); - - // Also add winAnsiWidth - List v = ansiIndex.get(new Integer(j)); - if (v != null) { - for (Integer aIdx : v) { - ansiWidth[aIdx.intValue()] - = mtxTab[glyphIdx].getWx(); - - if (log.isTraceEnabled()) { - log.trace("Added width " - + mtxTab[glyphIdx].getWx() - + " uni: " + j - + " ansi: " + aIdx.intValue()); - } - } - } - - if (log.isTraceEnabled()) { - log.trace("Idx: " - + glyphIdx - + " Delta: " + cmapDeltas[i] - + " Unicode: " + j - + " name: " + mtxTab[glyphIdx].getName()); - } - } else { - glyphIdx = (j + cmapDeltas[i]) & 0xffff; - - if (glyphIdx < mtxTab.length) { - mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); - } else { - log.debug("Glyph " + glyphIdx - + " out of range: " - + mtxTab.length); - } - - unicodeMappings.add(new UnicodeMapping(glyphIdx, j)); - if (glyphIdx < mtxTab.length) { - mtxTab[glyphIdx].getUnicodeIndex().add(new Integer(j)); - } else { - log.debug("Glyph " + glyphIdx - + " out of range: " - + mtxTab.length); - } - - // Also add winAnsiWidth - List v = ansiIndex.get(new Integer(j)); - if (v != null) { - for (Integer aIdx : v) { - ansiWidth[aIdx.intValue()] = mtxTab[glyphIdx].getWx(); - } - } - - //getLogger().debug("IIdx: " + - // mtxPtr + - // " Delta: " + cmap_deltas[i] + - // " Unicode: " + j + - // " name: " + - // mtxTab[(j+cmap_deltas[i]) & 0xffff].name); - - } - if (glyphIdx < mtxTab.length) { - if (mtxTab[glyphIdx].getUnicodeIndex().size() < 2) { - mtxPtr++; - } - } - } - } - } - } else { - log.error("Cmap format not supported: " + cmapFormat); - return false; - } - return true; - } - - private boolean isInPrivateUseArea(int start, int end) { - return (isInPrivateUseArea(start) || isInPrivateUseArea(end)); - } - - private boolean isInPrivateUseArea(int unicode) { - return (unicode >= 0xE000 && unicode <= 0xF8FF); - } - - /** - * Print first char/last char - */ - private void printMaxMin() { - int min = 255; - int max = 0; - for (int i = 0; i < mtxTab.length; i++) { - if (mtxTab[i].getIndex() < min) { - min = mtxTab[i].getIndex(); - } - if (mtxTab[i].getIndex() > max) { - max = mtxTab[i].getIndex(); - } - } - log.info("Min: " + min); - log.info("Max: " + max); - } - - - /** - * Reads the font using a FontFileReader. - * - * @param in The FontFileReader to use - * @throws IOException In case of an I/O problem - */ - public void readFont(FontFileReader in) throws IOException { - readFont(in, (String)null); - } - - /** - * initialize the ansiWidths array (for winAnsiEncoding) - * and fill with the missingwidth - */ - private void initAnsiWidths() { - ansiWidth = new int[256]; - for (int i = 0; i < 256; i++) { - ansiWidth[i] = mtxTab[0].getWx(); - } - - // Create an index hash to the ansiWidth - // Can't just index the winAnsiEncoding when inserting widths - // same char (eg bullet) is repeated more than one place - ansiIndex = new HashMap>(); - for (int i = 32; i < Glyphs.WINANSI_ENCODING.length; i++) { - Integer ansi = new Integer(i); - Integer uni = new Integer(Glyphs.WINANSI_ENCODING[i]); - - List v = ansiIndex.get(uni); - if (v == null) { - v = new ArrayList(); - ansiIndex.put(uni, v); - } - v.add(ansi); - } - } - - /** - * Read the font data. - * If the fontfile is a TrueType Collection (.ttc file) - * the name of the font to read data for must be supplied, - * else the name is ignored. - * - * @param in The FontFileReader to use - * @param name The name of the font - * @return boolean Returns true if the font is valid - * @throws IOException In case of an I/O problem - */ - public boolean readFont(FontFileReader in, String name) throws IOException { - fontFile = in; - /* - * Check if TrueType collection, and that the name - * exists in the collection - */ - if (!checkTTC(name)) { - if (name == null) { - throw new IllegalArgumentException( - "For TrueType collection you must specify which font " - + "to select (-ttcname)"); - } else { - throw new IOException( - "Name does not exist in the TrueType collection: " + name); - } - } - - readDirTabs(); - readFontHeader(); - getNumGlyphs(); - if (log.isDebugEnabled()) { - log.debug("Number of glyphs in font: " + numberOfGlyphs); - } - readHorizontalHeader(); - readHorizontalMetrics(); - initAnsiWidths(); - readPostScript(); - readOS2(); - determineAscDesc(); - if (!isCFF) { - readIndexToLocation(); - readGlyf(); - } - readName(); - boolean pcltFound = readPCLT(); - // Read cmap table and fill in ansiwidths - boolean valid = readCMAP(); - if (!valid) { - return false; - } - // Create cmaps for bfentries - createCMaps(); - - if (useKerning) { - readKerning(); - } - - // Read advanced typographic tables. - if (useAdvanced) { - try { - OTFAdvancedTypographicTableReader atr - = new OTFAdvancedTypographicTableReader(this, in); - atr.readAll(); - this.advancedTableReader = atr; - } catch (AdvancedTypographicTableFormatException e) { - log.warn( - "Encountered format constraint violation in advanced (typographic) table (AT) " - + "in font '" + getFullName() + "', ignoring AT data: " - + e.getMessage() - ); - } - } - - guessVerticalMetricsFromGlyphBBox(); - return true; - } - - /** - * Reads a font. - * - * @param in FontFileReader to read from - * @param name Name to be checked for in the font file - * @param glyphs Map of glyphs (glyphs has old index as (Integer) key and - * new index as (Integer) value) - * @throws IOException in case of an I/O problem - */ - public void readFont(FontFileReader in, String name, - Map glyphs) throws IOException { - readFont(in, name); - } - - private void createCMaps() { - cmaps = new ArrayList(); - int unicodeStart; - int glyphStart; - int unicodeEnd; - - Iterator e = unicodeMappings.iterator(); - UnicodeMapping um = e.next(); - UnicodeMapping lastMapping = um; - - unicodeStart = um.getUnicodeIndex(); - glyphStart = um.getGlyphIndex(); - - while (e.hasNext()) { - um = e.next(); - if (((lastMapping.getUnicodeIndex() + 1) != um.getUnicodeIndex()) - || ((lastMapping.getGlyphIndex() + 1) != um.getGlyphIndex())) { - unicodeEnd = lastMapping.getUnicodeIndex(); - cmaps.add(new CMapSegment(unicodeStart, unicodeEnd, glyphStart)); - unicodeStart = um.getUnicodeIndex(); - glyphStart = um.getGlyphIndex(); - } - lastMapping = um; - } - - unicodeEnd = lastMapping.getUnicodeIndex(); - cmaps.add(new CMapSegment(unicodeStart, unicodeEnd, glyphStart)); - } - - /** - * Returns the PostScript name of the font. - * @return String The PostScript name - */ - public String getPostScriptName() { - if (postScriptName.length() == 0) { - return FontUtil.stripWhiteSpace(getFullName()); - } else { - return postScriptName; - } - } - - PostScriptVersion getPostScriptVersion() { - return postScriptVersion; - } - - /** - * Returns the font family names of the font. - * @return Set The family names (a Set of Strings) - */ - public Set getFamilyNames() { - return familyNames; - } - - /** - * Returns the font sub family name of the font. - * @return String The sub family name - */ - public String getSubFamilyName() { - return subFamilyName; - } - - /** - * Returns the full name of the font. - * @return String The full name - */ - public String getFullName() { - return fullName; - } - - /** - * Returns the name of the character set used. - * @return String The caracter set - */ - public String getCharSetName() { - return encoding; - } - - /** - * Returns the CapHeight attribute of the font. - * @return int The CapHeight - */ - public int getCapHeight() { - return convertTTFUnit2PDFUnit(capHeight); - } - - /** - * Returns the XHeight attribute of the font. - * @return int The XHeight - */ - public int getXHeight() { - return convertTTFUnit2PDFUnit(xHeight); - } - - /** - * Returns the number of bytes necessary to pad the currentPosition so that a table begins - * on a 4-byte boundary. - * @param currentPosition the position to pad. - * @return int the number of bytes to pad. - */ - protected int getPadSize(int currentPosition) { - int padSize = 4 - (currentPosition % 4); - return padSize < 4 ? padSize : 0; - } - - /** - * Returns the Flags attribute of the font. - * @return int The Flags - */ - public int getFlags() { - int flags = 32; // Use Adobe Standard charset - if (italicAngle != 0) { - flags |= 64; - } - if (isFixedPitch != 0) { - flags |= 2; - } - if (hasSerifs) { - flags |= 1; - } - return flags; - } - - /** - * Returns the weight class of this font. Valid values are 100, 200....,800, 900. - * @return the weight class value (or 0 if there was no OS/2 table in the font) - */ - public int getWeightClass() { - return this.usWeightClass; - } - - /** - * Returns the StemV attribute of the font. - * @return String The StemV - */ - public String getStemV() { - return "0"; - } - - /** - * Returns the ItalicAngle attribute of the font. - * @return String The ItalicAngle - */ - public String getItalicAngle() { - String ia = Short.toString((short)(italicAngle / 0x10000)); - - // This is the correct italic angle, however only int italic - // angles are supported at the moment so this is commented out. - /* - * if ((italicAngle % 0x10000) > 0 ) - * ia=ia+(comma+Short.toString((short)((short)((italicAngle % 0x10000)*1000)/0x10000))); - */ - return ia; - } - - /** - * @return int[] The font bbox - */ - public int[] getFontBBox() { - final int[] fbb = new int[4]; - fbb[0] = convertTTFUnit2PDFUnit(fontBBox1); - fbb[1] = convertTTFUnit2PDFUnit(fontBBox2); - fbb[2] = convertTTFUnit2PDFUnit(fontBBox3); - fbb[3] = convertTTFUnit2PDFUnit(fontBBox4); - - return fbb; - } - - /** - * Returns the LowerCaseAscent attribute of the font. - * @return int The LowerCaseAscent - */ - public int getLowerCaseAscent() { - return convertTTFUnit2PDFUnit(ascender); - } - - /** - * Returns the LowerCaseDescent attribute of the font. - * @return int The LowerCaseDescent - */ - public int getLowerCaseDescent() { - return convertTTFUnit2PDFUnit(descender); - } - - /** - * Returns the index of the last character, but this is for WinAnsiEncoding - * only, so the last char is < 256. - * @return short Index of the last character (<256) - */ - public short getLastChar() { - return lastChar; - } - - /** - * Returns the index of the first character. - * @return short Index of the first character - */ - public short getFirstChar() { - return firstChar; - } - - /** - * Returns an array of character widths. - * @return int[] The character widths - */ - public int[] getWidths() { - int[] wx = new int[mtxTab.length]; - for (int i = 0; i < wx.length; i++) { - wx[i] = convertTTFUnit2PDFUnit(mtxTab[i].getWx()); - } - - return wx; - } - - /** - * Returns an array (xMin, yMin, xMax, yMax) for a glyph. - * - * @param glyphIndex the index of the glyph - * @return int[] Array defining bounding box. - */ - public int[] getBBox(int glyphIndex) { - int[] bboxInTTFUnits = mtxTab[glyphIndex].getBoundingBox(); - int[] bbox = new int[4]; - for (int i = 0; i < 4; i++) { - bbox[i] = convertTTFUnit2PDFUnit(bboxInTTFUnits[i]); - } - return bbox; - } - - /** - * Returns the width of a given character. - * @param idx Index of the character - * @return int Standard width - */ - public int getCharWidth(int idx) { - return convertTTFUnit2PDFUnit(ansiWidth[idx]); - } - - /** - * Returns the kerning table. - * @return Map The kerning table - */ - public Map> getKerning() { - return kerningTab; - } - - /** - * Returns the ANSI kerning table. - * @return Map The ANSI kerning table - */ - public Map> getAnsiKerning() { - return ansiKerningTab; - } - - /** - * Indicates if the font may be embedded. - * @return boolean True if it may be embedded - */ - public boolean isEmbeddable() { - return isEmbeddable; - } - - /** - * Indicates whether or not the font is an OpenType - * CFF font (rather than a TrueType font). - * @return true if the font is in OpenType CFF format. - */ - public boolean isCFF() { - return this.isCFF; - } - - /** - * Read Table Directory from the current position in the - * FontFileReader and fill the global HashMap dirTabs - * with the table name (String) as key and a TTFDirTabEntry - * as value. - * @throws IOException in case of an I/O problem - */ - protected void readDirTabs() throws IOException { - int sfntVersion = fontFile.readTTFLong(); // TTF_FIXED_SIZE (4 bytes) - switch (sfntVersion) { - case 0x10000: - log.debug("sfnt version: OpenType 1.0"); - break; - case 0x4F54544F: //"OTTO" - this.isCFF = true; - log.debug("sfnt version: OpenType with CFF data"); - break; - case 0x74727565: //"true" - log.debug("sfnt version: Apple TrueType"); - break; - case 0x74797031: //"typ1" - log.debug("sfnt version: Apple Type 1 housed in sfnt wrapper"); - break; - default: - log.debug("Unknown sfnt version: " + Integer.toHexString(sfntVersion)); - break; - } - int ntabs = fontFile.readTTFUShort(); - fontFile.skip(6); // 3xTTF_USHORT_SIZE - - dirTabs = new HashMap(); - TTFDirTabEntry[] pd = new TTFDirTabEntry[ntabs]; - log.debug("Reading " + ntabs + " dir tables"); - - for (int i = 0; i < ntabs; i++) { - pd[i] = new TTFDirTabEntry(); - String tableName = pd[i].read(fontFile); - dirTabs.put(TTFTableName.getValue(tableName), pd[i]); - } - dirTabs.put(TTFTableName.TABLE_DIRECTORY, - new TTFDirTabEntry(0L, fontFile.getCurrentPos())); - log.debug("dir tables: " + dirTabs.keySet()); - } - - /** - * Read the "head" table, this reads the bounding box and - * sets the upem (unitsPerEM) variable - * @throws IOException in case of an I/O problem - */ - protected void readFontHeader() throws IOException { - seekTab(fontFile, TTFTableName.HEAD, 2 * 4 + 2 * 4); - int flags = fontFile.readTTFUShort(); - if (log.isDebugEnabled()) { - log.debug("flags: " + flags + " - " + Integer.toString(flags, 2)); - } - upem = fontFile.readTTFUShort(); - if (log.isDebugEnabled()) { - log.debug("unit per em: " + upem); - } - - fontFile.skip(16); - - fontBBox1 = fontFile.readTTFShort(); - fontBBox2 = fontFile.readTTFShort(); - fontBBox3 = fontFile.readTTFShort(); - fontBBox4 = fontFile.readTTFShort(); - if (log.isDebugEnabled()) { - log.debug("font bbox: xMin=" + fontBBox1 - + " yMin=" + fontBBox2 - + " xMax=" + fontBBox3 - + " yMax=" + fontBBox4); - } - - fontFile.skip(2 + 2 + 2); - - locaFormat = fontFile.readTTFShort(); - } - - /** - * Read the number of glyphs from the "maxp" table - * @throws IOException in case of an I/O problem - */ - protected void getNumGlyphs() throws IOException { - seekTab(fontFile, TTFTableName.MAXP, 4); - numberOfGlyphs = fontFile.readTTFUShort(); - } - - - /** - * Read the "hhea" table to find the ascender and descender and - * size of "hmtx" table, as a fixed size font might have only - * one width. - * @throws IOException in case of an I/O problem - */ - protected void readHorizontalHeader() - throws IOException { - seekTab(fontFile, TTFTableName.HHEA, 4); - hheaAscender = fontFile.readTTFShort(); - hheaDescender = fontFile.readTTFShort(); - - fontFile.skip(2 + 2 + 3 * 2 + 8 * 2); - nhmtx = fontFile.readTTFUShort(); - - if (log.isDebugEnabled()) { - log.debug("hhea.Ascender: " + formatUnitsForDebug(hheaAscender)); - log.debug("hhea.Descender: " + formatUnitsForDebug(hheaDescender)); - log.debug("Number of horizontal metrics: " + nhmtx); - } - } - - /** - * Read "hmtx" table and put the horizontal metrics - * in the mtxTab array. If the number of metrics is less - * than the number of glyphs (eg fixed size fonts), extend - * the mtxTab array and fill in the missing widths - * @throws IOException in case of an I/O problem - */ - protected void readHorizontalMetrics() - throws IOException { - seekTab(fontFile, TTFTableName.HMTX, 0); - - int mtxSize = Math.max(numberOfGlyphs, nhmtx); - mtxTab = new TTFMtxEntry[mtxSize]; - - if (log.isTraceEnabled()) { - log.trace("*** Widths array: \n"); - } - for (int i = 0; i < mtxSize; i++) { - mtxTab[i] = new TTFMtxEntry(); - } - for (int i = 0; i < nhmtx; i++) { - mtxTab[i].setWx(fontFile.readTTFUShort()); - mtxTab[i].setLsb(fontFile.readTTFUShort()); - - if (log.isTraceEnabled()) { - log.trace(" width[" + i + "] = " - + convertTTFUnit2PDFUnit(mtxTab[i].getWx()) + ";"); - } - } - - if (nhmtx < mtxSize) { - // Fill in the missing widths - int lastWidth = mtxTab[nhmtx - 1].getWx(); - for (int i = nhmtx; i < mtxSize; i++) { - mtxTab[i].setWx(lastWidth); - mtxTab[i].setLsb(fontFile.readTTFUShort()); - } - } - } - - - /** - * Read the "post" table - * containing the PostScript names of the glyphs. - */ - private void readPostScript() throws IOException { - seekTab(fontFile, TTFTableName.POST, 0); - int postFormat = fontFile.readTTFLong(); - italicAngle = fontFile.readTTFULong(); - underlinePosition = fontFile.readTTFShort(); - underlineThickness = fontFile.readTTFShort(); - isFixedPitch = fontFile.readTTFULong(); - - //Skip memory usage values - fontFile.skip(4 * 4); - - log.debug("PostScript format: 0x" + Integer.toHexString(postFormat)); - switch (postFormat) { - case 0x00010000: - log.debug("PostScript format 1"); - postScriptVersion = PostScriptVersion.V1; - for (int i = 0; i < MAC_GLYPH_ORDERING.length; i++) { - mtxTab[i].setName(MAC_GLYPH_ORDERING[i]); - } - break; - case 0x00020000: - log.debug("PostScript format 2"); - postScriptVersion = PostScriptVersion.V2; - int numGlyphStrings = 0; - - // Read Number of Glyphs - int l = fontFile.readTTFUShort(); - - // Read indexes - for (int i = 0; i < l; i++) { - mtxTab[i].setIndex(fontFile.readTTFUShort()); - - if (mtxTab[i].getIndex() > 257) { - //Index is not in the Macintosh standard set - numGlyphStrings++; - } - - if (log.isTraceEnabled()) { - log.trace("PostScript index: " + mtxTab[i].getIndexAsString()); - } - } - - // firstChar=minIndex; - String[] psGlyphsBuffer = new String[numGlyphStrings]; - if (log.isDebugEnabled()) { - log.debug("Reading " + numGlyphStrings - + " glyphnames, that are not in the standard Macintosh" - + " set. Total number of glyphs=" + l); - } - for (int i = 0; i < psGlyphsBuffer.length; i++) { - psGlyphsBuffer[i] = fontFile.readTTFString(fontFile.readTTFUByte()); - } - - //Set glyph names - for (int i = 0; i < l; i++) { - if (mtxTab[i].getIndex() < MAC_GLYPH_ORDERING.length) { - mtxTab[i].setName(MAC_GLYPH_ORDERING[mtxTab[i].getIndex()]); - } else { - if (!mtxTab[i].isIndexReserved()) { - int k = mtxTab[i].getIndex() - MAC_GLYPH_ORDERING.length; - - if (log.isTraceEnabled()) { - log.trace(k + " i=" + i + " mtx=" + mtxTab.length - + " ps=" + psGlyphsBuffer.length); - } - - mtxTab[i].setName(psGlyphsBuffer[k]); - } - } - } - - break; - case 0x00030000: - // PostScript format 3 contains no glyph names - log.debug("PostScript format 3"); - postScriptVersion = PostScriptVersion.V3; - break; - default: - log.error("Unknown PostScript format: " + postFormat); - postScriptVersion = PostScriptVersion.UNKNOWN; - } - } - - - /** - * Read the "OS/2" table - */ - private void readOS2() throws IOException { - // Check if font is embeddable - TTFDirTabEntry os2Entry = dirTabs.get(TTFTableName.OS2); - if (os2Entry != null) { - seekTab(fontFile, TTFTableName.OS2, 0); - int version = fontFile.readTTFUShort(); - if (log.isDebugEnabled()) { - log.debug("OS/2 table: version=" + version - + ", offset=" + os2Entry.getOffset() + ", len=" + os2Entry.getLength()); - } - fontFile.skip(2); //xAvgCharWidth - this.usWeightClass = fontFile.readTTFUShort(); - - // usWidthClass - fontFile.skip(2); - - int fsType = fontFile.readTTFUShort(); - if (fsType == 2) { - isEmbeddable = false; - } else { - isEmbeddable = true; - } - fontFile.skip(11 * 2); - fontFile.skip(10); //panose array - fontFile.skip(4 * 4); //unicode ranges - fontFile.skip(4); - fontFile.skip(3 * 2); - int v; - os2Ascender = fontFile.readTTFShort(); //sTypoAscender - os2Descender = fontFile.readTTFShort(); //sTypoDescender - if (log.isDebugEnabled()) { - log.debug("sTypoAscender: " + os2Ascender - + " -> internal " + convertTTFUnit2PDFUnit(os2Ascender)); - log.debug("sTypoDescender: " + os2Descender - + " -> internal " + convertTTFUnit2PDFUnit(os2Descender)); - } - v = fontFile.readTTFShort(); //sTypoLineGap - if (log.isDebugEnabled()) { - log.debug("sTypoLineGap: " + v); - } - v = fontFile.readTTFUShort(); //usWinAscent - if (log.isDebugEnabled()) { - log.debug("usWinAscent: " + formatUnitsForDebug(v)); - } - v = fontFile.readTTFUShort(); //usWinDescent - if (log.isDebugEnabled()) { - log.debug("usWinDescent: " + formatUnitsForDebug(v)); - } - - //version 1 OS/2 table might end here - if (os2Entry.getLength() >= 78 + (2 * 4) + (2 * 2)) { - fontFile.skip(2 * 4); - this.os2xHeight = fontFile.readTTFShort(); //sxHeight - this.os2CapHeight = fontFile.readTTFShort(); //sCapHeight - if (log.isDebugEnabled()) { - log.debug("sxHeight: " + this.os2xHeight); - log.debug("sCapHeight: " + this.os2CapHeight); - } - } - - } else { - isEmbeddable = true; - } - } - - /** - * Read the "loca" table. - * @throws IOException In case of a I/O problem - */ - protected final void readIndexToLocation() - throws IOException { - if (!seekTab(fontFile, TTFTableName.LOCA, 0)) { - throw new IOException("'loca' table not found, happens when the font file doesn't" - + " contain TrueType outlines (trying to read an OpenType CFF font maybe?)"); - } - for (int i = 0; i < numberOfGlyphs; i++) { - mtxTab[i].setOffset(locaFormat == 1 ? fontFile.readTTFULong() - : (fontFile.readTTFUShort() << 1)); - } - lastLoca = (locaFormat == 1 ? fontFile.readTTFULong() - : (fontFile.readTTFUShort() << 1)); +/** + * Reads a TrueType file or a TrueType Collection. + * The TrueType spec can be found at the Microsoft. + * Typography site: http://www.microsoft.com/truetype/ + */ +public class TTFFile extends OpenFont { + + public TTFFile() { + this(true, false); } /** - * Read the "glyf" table to find the bounding boxes. - * @throws IOException In case of a I/O problem + * Constructor + * @param useKerning true if kerning data should be loaded + * @param useAdvanced true if advanced typographic tables should be loaded */ - private void readGlyf() throws IOException { - TTFDirTabEntry dirTab = dirTabs.get(TTFTableName.GLYF); - if (dirTab == null) { - throw new IOException("glyf table not found, cannot continue"); - } - for (int i = 0; i < (numberOfGlyphs - 1); i++) { - if (mtxTab[i].getOffset() != mtxTab[i + 1].getOffset()) { - fontFile.seekSet(dirTab.getOffset() + mtxTab[i].getOffset()); - fontFile.skip(2); - final int[] bbox = { - fontFile.readTTFShort(), - fontFile.readTTFShort(), - fontFile.readTTFShort(), - fontFile.readTTFShort()}; - mtxTab[i].setBoundingBox(bbox); - } else { - mtxTab[i].setBoundingBox(mtxTab[0].getBoundingBox()); - } - } - - - long n = (dirTabs.get(TTFTableName.GLYF)).getOffset(); - for (int i = 0; i < numberOfGlyphs; i++) { - if ((i + 1) >= mtxTab.length - || mtxTab[i].getOffset() != mtxTab[i + 1].getOffset()) { - fontFile.seekSet(n + mtxTab[i].getOffset()); - fontFile.skip(2); - final int[] bbox = { - fontFile.readTTFShort(), - fontFile.readTTFShort(), - fontFile.readTTFShort(), - fontFile.readTTFShort()}; - mtxTab[i].setBoundingBox(bbox); - } else { - /**@todo Verify that this is correct, looks like a copy/paste bug (jm)*/ - final int bbox0 = mtxTab[0].getBoundingBox()[0]; - final int[] bbox = {bbox0, bbox0, bbox0, bbox0}; - mtxTab[i].setBoundingBox(bbox); - /* Original code - mtxTab[i].bbox[0] = mtxTab[0].bbox[0]; - mtxTab[i].bbox[1] = mtxTab[0].bbox[0]; - mtxTab[i].bbox[2] = mtxTab[0].bbox[0]; - mtxTab[i].bbox[3] = mtxTab[0].bbox[0]; */ - } - if (log.isTraceEnabled()) { - log.trace(mtxTab[i].toString(this)); - } - } + public TTFFile(boolean useKerning, boolean useAdvanced) { + super(useKerning, useAdvanced); } /** * Read the "name" table. * @throws IOException In case of a I/O problem */ - private void readName() throws IOException { - seekTab(fontFile, TTFTableName.NAME, 2); + protected void readName() throws IOException { + seekTab(fontFile, OFTableName.NAME, 2); int i = fontFile.getCurrentPos(); int n = fontFile.readTTFUShort(); int j = fontFile.readTTFUShort() + i - 2; @@ -1487,572 +112,84 @@ public class TTFFile { } /** - * Read the "PCLT" table to find xHeight and capHeight. + * Read the "glyf" table to find the bounding boxes. * @throws IOException In case of a I/O problem */ - private boolean readPCLT() throws IOException { - TTFDirTabEntry dirTab = dirTabs.get(TTFTableName.PCLT); - if (dirTab != null) { - fontFile.seekSet(dirTab.getOffset() + 4 + 4 + 2); - xHeight = fontFile.readTTFUShort(); - log.debug("xHeight from PCLT: " + formatUnitsForDebug(xHeight)); - fontFile.skip(2 * 2); - capHeight = fontFile.readTTFUShort(); - log.debug("capHeight from PCLT: " + formatUnitsForDebug(capHeight)); - fontFile.skip(2 + 16 + 8 + 6 + 1 + 1); - - int serifStyle = fontFile.readTTFUByte(); - serifStyle = serifStyle >> 6; - serifStyle = serifStyle & 3; - if (serifStyle == 1) { - hasSerifs = false; - } else { - hasSerifs = true; - } - return true; - } else { - return false; - } - } - - /** - * Determines the right source for the ascender and descender values. The problem here is - * that the interpretation of these values is not the same for every font. There doesn't seem - * to be a uniform definition of an ascender and a descender. In some fonts - * the hhea values are defined after the Apple interpretation, but not in every font. The - * same problem is in the OS/2 table. FOP needs the ascender and descender to determine the - * baseline so we need values which add up more or less to the "em box". However, due to - * accent modifiers a character can grow beyond the em box. - */ - private void determineAscDesc() { - int hheaBoxHeight = hheaAscender - hheaDescender; - int os2BoxHeight = os2Ascender - os2Descender; - if (os2Ascender > 0 && os2BoxHeight <= upem) { - ascender = os2Ascender; - descender = os2Descender; - } else if (hheaAscender > 0 && hheaBoxHeight <= upem) { - ascender = hheaAscender; - descender = hheaDescender; - } else { - if (os2Ascender > 0) { - //Fall back to info from OS/2 if possible - ascender = os2Ascender; - descender = os2Descender; - } else { - ascender = hheaAscender; - descender = hheaDescender; - } - } - - if (log.isDebugEnabled()) { - log.debug("Font box height: " + (ascender - descender)); - if (ascender - descender > upem) { - log.debug("Ascender and descender together are larger than the em box."); - } + private void readGlyf() throws IOException { + OFDirTabEntry dirTab = dirTabs.get(OFTableName.GLYF); + if (dirTab == null) { + throw new IOException("glyf table not found, cannot continue"); } - } - - private void guessVerticalMetricsFromGlyphBBox() { - // Approximate capHeight from height of "H" - // It's most unlikely that a font misses the PCLT table - // This also assumes that postscriptnames exists ("H") - // Should look it up in the cmap (that wouldn't help - // for charsets without H anyway...) - // Same for xHeight with the letter "x" - int localCapHeight = 0; - int localXHeight = 0; - int localAscender = 0; - int localDescender = 0; - for (int i = 0; i < mtxTab.length; i++) { - if ("H".equals(mtxTab[i].getName())) { - localCapHeight = mtxTab[i].getBoundingBox()[3]; - } else if ("x".equals(mtxTab[i].getName())) { - localXHeight = mtxTab[i].getBoundingBox()[3]; - } else if ("d".equals(mtxTab[i].getName())) { - localAscender = mtxTab[i].getBoundingBox()[3]; - } else if ("p".equals(mtxTab[i].getName())) { - localDescender = mtxTab[i].getBoundingBox()[1]; + for (int i = 0; i < (numberOfGlyphs - 1); i++) { + if (mtxTab[i].getOffset() != mtxTab[i + 1].getOffset()) { + fontFile.seekSet(dirTab.getOffset() + mtxTab[i].getOffset()); + fontFile.skip(2); + final int[] bbox = { + fontFile.readTTFShort(), + fontFile.readTTFShort(), + fontFile.readTTFShort(), + fontFile.readTTFShort()}; + mtxTab[i].setBoundingBox(bbox); } else { - // OpenType Fonts with a version 3.0 "post" table don't have glyph names. - // Use Unicode indices instead. - List unicodeIndex = mtxTab[i].getUnicodeIndex(); - if (unicodeIndex.size() > 0) { - //Only the first index is used - char ch = (char)((Integer)unicodeIndex.get(0)).intValue(); - if (ch == 'H') { - localCapHeight = mtxTab[i].getBoundingBox()[3]; - } else if (ch == 'x') { - localXHeight = mtxTab[i].getBoundingBox()[3]; - } else if (ch == 'd') { - localAscender = mtxTab[i].getBoundingBox()[3]; - } else if (ch == 'p') { - localDescender = mtxTab[i].getBoundingBox()[1]; - } - } - } - } - if (log.isDebugEnabled()) { - log.debug("Ascender from glyph 'd': " + formatUnitsForDebug(localAscender)); - log.debug("Descender from glyph 'p': " + formatUnitsForDebug(localDescender)); - } - if (ascender - descender > upem) { - log.debug("Replacing specified ascender/descender with derived values to get values" - + " which fit in the em box."); - ascender = localAscender; - descender = localDescender; - } - - if (log.isDebugEnabled()) { - log.debug("xHeight from glyph 'x': " + formatUnitsForDebug(localXHeight)); - log.debug("CapHeight from glyph 'H': " + formatUnitsForDebug(localCapHeight)); - } - if (capHeight == 0) { - capHeight = localCapHeight; - if (capHeight == 0) { - capHeight = os2CapHeight; - } - if (capHeight == 0) { - log.debug("capHeight value could not be determined." - + " The font may not work as expected."); - } - } - if (xHeight == 0) { - xHeight = localXHeight; - if (xHeight == 0) { - xHeight = os2xHeight; - } - if (xHeight == 0) { - log.debug("xHeight value could not be determined." - + " The font may not work as expected."); - } - } - } - - /** - * Read the kerning table, create a table for both CIDs and - * winAnsiEncoding. - * @throws IOException In case of a I/O problem - */ - private void readKerning() throws IOException { - // Read kerning - kerningTab = new HashMap>(); - ansiKerningTab = new HashMap>(); - TTFDirTabEntry dirTab = dirTabs.get(TTFTableName.KERN); - if (dirTab != null) { - seekTab(fontFile, TTFTableName.KERN, 2); - for (int n = fontFile.readTTFUShort(); n > 0; n--) { - fontFile.skip(2 * 2); - int k = fontFile.readTTFUShort(); - if (!((k & 1) != 0) || (k & 2) != 0 || (k & 4) != 0) { - return; - } - if ((k >> 8) != 0) { - continue; - } - - k = fontFile.readTTFUShort(); - fontFile.skip(3 * 2); - while (k-- > 0) { - int i = fontFile.readTTFUShort(); - int j = fontFile.readTTFUShort(); - int kpx = fontFile.readTTFShort(); - if (kpx != 0) { - // CID kerning table entry, using unicode indexes - final Integer iObj = glyphToUnicode(i); - final Integer u2 = glyphToUnicode(j); - if (iObj == null) { - // happens for many fonts (Ubuntu font set), - // stray entries in the kerning table?? - log.debug("Ignoring kerning pair because no Unicode index was" - + " found for the first glyph " + i); - } else if (u2 == null) { - log.debug("Ignoring kerning pair because Unicode index was" - + " found for the second glyph " + i); - } else { - Map adjTab = kerningTab.get(iObj); - if (adjTab == null) { - adjTab = new HashMap(); - } - adjTab.put(u2, new Integer(convertTTFUnit2PDFUnit(kpx))); - kerningTab.put(iObj, adjTab); - } - } - } - } - - // Create winAnsiEncoded kerning table from kerningTab - // (could probably be simplified, for now we remap back to CID indexes and - // then to winAnsi) - for (Integer unicodeKey1 : kerningTab.keySet()) { - Integer cidKey1 = unicodeToGlyph(unicodeKey1.intValue()); - Map akpx = new HashMap(); - Map ckpx = kerningTab.get(unicodeKey1); - - for (Integer unicodeKey2 : ckpx.keySet()) { - Integer cidKey2 = unicodeToGlyph(unicodeKey2.intValue()); - Integer kern = ckpx.get(unicodeKey2); - - Iterator uniMap = mtxTab[cidKey2.intValue()].getUnicodeIndex().listIterator(); - while (uniMap.hasNext()) { - Integer unicodeKey = (Integer)uniMap.next(); - Integer[] ansiKeys = unicodeToWinAnsi(unicodeKey.intValue()); - for (int u = 0; u < ansiKeys.length; u++) { - akpx.put(ansiKeys[u], kern); - } - } - } - - if (akpx.size() > 0) { - Iterator uniMap = mtxTab[cidKey1.intValue()].getUnicodeIndex().listIterator(); - while (uniMap.hasNext()) { - Integer unicodeKey = (Integer)uniMap.next(); - Integer[] ansiKeys = unicodeToWinAnsi(unicodeKey.intValue()); - for (int u = 0; u < ansiKeys.length; u++) { - ansiKerningTab.put(ansiKeys[u], akpx); - } - } - } + mtxTab[i].setBoundingBox(mtxTab[0].getBoundingBox()); } } - } - /** - * Streams a font. - * @param ttfOut The interface for streaming TrueType tables. - * @exception IOException file write error - */ - public void stream(TTFOutputStream ttfOut) throws IOException { - SortedSet> sortedDirTabs = sortDirTabMap(dirTabs); - byte[] file = fontFile.getAllBytes(); - TTFTableOutputStream tableOut = ttfOut.getTableOutputStream(); - TTFGlyphOutputStream glyphOut = ttfOut.getGlyphOutputStream(); - ttfOut.startFontStream(); - for (Map.Entry entry : sortedDirTabs) { - int offset = (int) entry.getValue().getOffset(); - int paddedLength = (int) entry.getValue().getLength(); - paddedLength += getPadSize(offset + paddedLength); - if (entry.getKey().equals(TTFTableName.GLYF)) { - streamGlyf(glyphOut, file, offset, paddedLength); + long n = (dirTabs.get(OFTableName.GLYF)).getOffset(); + for (int i = 0; i < numberOfGlyphs; i++) { + if ((i + 1) >= mtxTab.length + || mtxTab[i].getOffset() != mtxTab[i + 1].getOffset()) { + fontFile.seekSet(n + mtxTab[i].getOffset()); + fontFile.skip(2); + final int[] bbox = { + fontFile.readTTFShort(), + fontFile.readTTFShort(), + fontFile.readTTFShort(), + fontFile.readTTFShort()}; + mtxTab[i].setBoundingBox(bbox); } else { - tableOut.streamTable(file, offset, paddedLength); - } - } - ttfOut.endFontStream(); - } - - private void streamGlyf(TTFGlyphOutputStream glyphOut, byte[] fontFile, int tableOffset, - int tableLength) throws IOException { - //Stream all but the last glyph - int glyphStart = 0; - int glyphEnd = 0; - glyphOut.startGlyphStream(); - for (int i = 0; i < mtxTab.length - 1; i++) { - glyphStart = (int) mtxTab[i].getOffset() + tableOffset; - glyphEnd = (int) mtxTab[i + 1].getOffset() + tableOffset; - glyphOut.streamGlyph(fontFile, glyphStart, glyphEnd - glyphStart); - } - glyphOut.streamGlyph(fontFile, glyphEnd, (tableOffset + tableLength) - glyphEnd); - glyphOut.endGlyphStream(); - } - - /** - * Returns the order in which the tables in a TrueType font should be written to file. - * @param directoryTabs the map that is to be sorted. - * @return TTFTablesNames[] an array of table names sorted in the order they should appear in - * the TTF file. - */ - SortedSet> - sortDirTabMap(Map directoryTabs) { - SortedSet> sortedSet - = new TreeSet>( - new Comparator>() { - - public int compare(Entry o1, - Entry o2) { - return (int) (o1.getValue().getOffset() - o2.getValue().getOffset()); - } - }); - sortedSet.addAll(directoryTabs.entrySet()); - return sortedSet; - } - - /** - * Returns this font's character to glyph mapping. - * - * @return the font's cmap - */ - public List getCMaps() { - return cmaps; - } - - /** - * Check if this is a TrueType collection and that the given - * name exists in the collection. - * If it does, set offset in fontfile to the beginning of - * the Table Directory for that font. - * @param name The name to check - * @return True if not collection or font name present, false otherwise - * @throws IOException In case of an I/O problem - */ - protected final boolean checkTTC(String name) throws IOException { - String tag = fontFile.readTTFString(4); - - if ("ttcf".equals(tag)) { - // This is a TrueType Collection - fontFile.skip(4); - - // Read directory offsets - int numDirectories = (int)fontFile.readTTFULong(); - // int numDirectories=in.readTTFUShort(); - long[] dirOffsets = new long[numDirectories]; - for (int i = 0; i < numDirectories; i++) { - dirOffsets[i] = fontFile.readTTFULong(); - } - - log.info("This is a TrueType collection file with " - + numDirectories + " fonts"); - log.info("Containing the following fonts: "); - // Read all the directories and name tables to check - // If the font exists - this is a bit ugly, but... - boolean found = false; - - // Iterate through all name tables even if font - // Is found, just to show all the names - long dirTabOffset = 0; - for (int i = 0; (i < numDirectories); i++) { - fontFile.seekSet(dirOffsets[i]); - readDirTabs(); - - readName(); - - if (fullName.equals(name)) { - found = true; - dirTabOffset = dirOffsets[i]; - log.info(fullName + " <-- selected"); - } else { - log.info(fullName); - } - - // Reset names - notice = ""; - fullName = ""; - familyNames.clear(); - postScriptName = ""; - subFamilyName = ""; - } - - fontFile.seekSet(dirTabOffset); - return found; - } else { - fontFile.seekSet(0); - return true; - } - } - - /** - * Return TTC font names - * @param in FontFileReader to read from - * @return True if not collection or font name present, false otherwise - * @throws IOException In case of an I/O problem - */ - public final List getTTCnames(FontFileReader in) throws IOException { - this.fontFile = in; - - List fontNames = new ArrayList(); - String tag = in.readTTFString(4); - - if ("ttcf".equals(tag)) { - // This is a TrueType Collection - in.skip(4); - - // Read directory offsets - int numDirectories = (int)in.readTTFULong(); - long[] dirOffsets = new long[numDirectories]; - for (int i = 0; i < numDirectories; i++) { - dirOffsets[i] = in.readTTFULong(); - } - - log.info("This is a TrueType collection file with " - + numDirectories + " fonts"); - log.info("Containing the following fonts: "); - - for (int i = 0; (i < numDirectories); i++) { - in.seekSet(dirOffsets[i]); - readDirTabs(); - - readName(); - - log.info(fullName); - fontNames.add(fullName); - - // Reset names - notice = ""; - fullName = ""; - familyNames.clear(); - postScriptName = ""; - subFamilyName = ""; + /**@todo Verify that this is correct, looks like a copy/paste bug (jm)*/ + final int bbox0 = mtxTab[0].getBoundingBox()[0]; + final int[] bbox = {bbox0, bbox0, bbox0, bbox0}; + mtxTab[i].setBoundingBox(bbox); + /* Original code + mtxTab[i].bbox[0] = mtxTab[0].bbox[0]; + mtxTab[i].bbox[1] = mtxTab[0].bbox[0]; + mtxTab[i].bbox[2] = mtxTab[0].bbox[0]; + mtxTab[i].bbox[3] = mtxTab[0].bbox[0]; */ } - - in.seekSet(0); - return fontNames; - } else { - log.error("Not a TTC!"); - return null; - } - } - - /* - * Helper classes, they are not very efficient, but that really - * doesn't matter... - */ - private Integer[] unicodeToWinAnsi(int unicode) { - List ret = new ArrayList(); - for (int i = 32; i < Glyphs.WINANSI_ENCODING.length; i++) { - if (unicode == Glyphs.WINANSI_ENCODING[i]) { - ret.add(new Integer(i)); + if (log.isTraceEnabled()) { + log.trace(mtxTab[i].toString(this)); } } - return ret.toArray(new Integer[0]); - } - - /** - * Dumps a few informational values to System.out. - */ - public void printStuff() { - System.out.println("Font name: " + postScriptName); - System.out.println("Full name: " + fullName); - System.out.println("Family name: " + familyNames); - System.out.println("Subfamily name: " + subFamilyName); - System.out.println("Notice: " + notice); - System.out.println("xHeight: " + convertTTFUnit2PDFUnit(xHeight)); - System.out.println("capheight: " + convertTTFUnit2PDFUnit(capHeight)); - - int italic = (int)(italicAngle >> 16); - System.out.println("Italic: " + italic); - System.out.print("ItalicAngle: " + (short)(italicAngle / 0x10000)); - if ((italicAngle % 0x10000) > 0) { - System.out.print("." - + (short)((italicAngle % 0x10000) * 1000) - / 0x10000); - } - System.out.println(); - System.out.println("Ascender: " + convertTTFUnit2PDFUnit(ascender)); - System.out.println("Descender: " + convertTTFUnit2PDFUnit(descender)); - System.out.println("FontBBox: [" + convertTTFUnit2PDFUnit(fontBBox1) - + " " + convertTTFUnit2PDFUnit(fontBBox2) + " " - + convertTTFUnit2PDFUnit(fontBBox3) + " " - + convertTTFUnit2PDFUnit(fontBBox4) + "]"); - } - - private String formatUnitsForDebug(int units) { - return units + " -> " + convertTTFUnit2PDFUnit(units) + " internal units"; - } - - /** - * Map a glyph index to the corresponding unicode code point - * - * @param glyphIndex - * @return unicode code point - */ - private Integer glyphToUnicode(int glyphIndex) { - return glyphToUnicodeMap.get(new Integer(glyphIndex)); - } - - /** - * Map a unicode code point to the corresponding glyph index - * - * @param unicodeIndex unicode code point - * @return glyph index - */ - private Integer unicodeToGlyph(int unicodeIndex) throws IOException { - final Integer result - = unicodeToGlyphMap.get(new Integer(unicodeIndex)); - if (result == null) { - throw new IOException( - "Glyph index not found for unicode value " + unicodeIndex); - } - return result; - } - - String getGlyphName(int glyphIndex) { - return mtxTab[glyphIndex].getName(); - } - - /** - * Determine if advanced (typographic) table is present. - * @return true if advanced (typographic) table is present - */ - public boolean hasAdvancedTable() { - if (advancedTableReader != null) { - return advancedTableReader.hasAdvancedTable(); - } else { - return false; - } } - /** - * Returns the GDEF table or null if none present. - * @return the GDEF table - */ - public GlyphDefinitionTable getGDEF() { - if (advancedTableReader != null) { - return advancedTableReader.getGDEF(); - } else { - return null; - } + @Override + protected void updateBBoxAndOffset() throws IOException { + readIndexToLocation(); + readGlyf(); } /** - * Returns the GSUB table or null if none present. - * @return the GSUB table + * Read the "loca" table. + * @throws IOException In case of a I/O problem */ - public GlyphSubstitutionTable getGSUB() { - if (advancedTableReader != null) { - return advancedTableReader.getGSUB(); - } else { - return null; + protected final void readIndexToLocation() + throws IOException { + if (!seekTab(fontFile, OFTableName.LOCA, 0)) { + throw new IOException("'loca' table not found, happens when the font file doesn't" + + " contain TrueType outlines (trying to read an OpenType CFF font maybe?)"); } - } - - /** - * Returns the GPOS table or null if none present. - * @return the GPOS table - */ - public GlyphPositioningTable getGPOS() { - if (advancedTableReader != null) { - return advancedTableReader.getGPOS(); - } else { - return null; + for (int i = 0; i < numberOfGlyphs; i++) { + mtxTab[i].setOffset(locaFormat == 1 ? fontFile.readTTFULong() + : (fontFile.readTTFUShort() << 1)); } + lastLoca = (locaFormat == 1 ? fontFile.readTTFULong() + : (fontFile.readTTFUShort() << 1)); } - /** - * Static main method to get info about a TrueType font. - * @param args The command line arguments - */ - public static void main(String[] args) { - InputStream stream = null; - try { - boolean useKerning = true; - boolean useAdvanced = true; - TTFFile ttfFile = new TTFFile(useKerning, useAdvanced); - - stream = new FileInputStream(args[0]); - FontFileReader reader = new FontFileReader(stream); - - String name = null; - if (args.length >= 2) { - name = args[1]; - } - - ttfFile.readFont(reader, name); - ttfFile.printStuff(); - - } catch (IOException ioe) { - System.err.println("Problem reading font: " + ioe.toString()); - ioe.printStackTrace(System.err); - } finally { - IOUtils.closeQuietly(stream); - } + @Override + protected void initializeFont(FontFileReader in) throws IOException { + fontFile = in; } } diff --git a/src/java/org/apache/fop/fonts/truetype/TTFSubSetFile.java b/src/java/org/apache/fop/fonts/truetype/TTFSubSetFile.java index c9a0e6c8e..ff46af1c7 100644 --- a/src/java/org/apache/fop/fonts/truetype/TTFSubSetFile.java +++ b/src/java/org/apache/fop/fonts/truetype/TTFSubSetFile.java @@ -43,7 +43,7 @@ public class TTFSubSetFile extends TTFFile { * Offsets in name table to be filled out by table. * The offsets are to the checkSum field */ - private Map offsets = new HashMap(); + private Map offsets = new HashMap(); private int checkSumAdjustmentOffset = 0; private int locaOffset = 0; @@ -67,8 +67,8 @@ public class TTFSubSetFile extends TTFFile { } /** The dir tab entries in the new subset font. */ - private Map newDirTabs - = new HashMap(); + private Map newDirTabs + = new HashMap(); private int determineTableCount() { int numTables = 4; //4 req'd tables: head,hhea,hmtx,maxp @@ -117,29 +117,29 @@ public class TTFSubSetFile extends TTFFile { writeUShort((numTables * 16) - searchRange); realSize += 2; // Create space for the table entries (these must be in ASCII alphabetical order[A-Z] then[a-z]) - writeTableName(TTFTableName.OS2); + writeTableName(OFTableName.OS2); if (hasCvt()) { - writeTableName(TTFTableName.CVT); + writeTableName(OFTableName.CVT); } if (hasFpgm()) { - writeTableName(TTFTableName.FPGM); + writeTableName(OFTableName.FPGM); } - writeTableName(TTFTableName.GLYF); - writeTableName(TTFTableName.HEAD); - writeTableName(TTFTableName.HHEA); - writeTableName(TTFTableName.HMTX); - writeTableName(TTFTableName.LOCA); - writeTableName(TTFTableName.MAXP); - writeTableName(TTFTableName.NAME); - writeTableName(TTFTableName.POST); + writeTableName(OFTableName.GLYF); + writeTableName(OFTableName.HEAD); + writeTableName(OFTableName.HHEA); + writeTableName(OFTableName.HMTX); + writeTableName(OFTableName.LOCA); + writeTableName(OFTableName.MAXP); + writeTableName(OFTableName.NAME); + writeTableName(OFTableName.POST); if (hasPrep()) { - writeTableName(TTFTableName.PREP); + writeTableName(OFTableName.PREP); } - newDirTabs.put(TTFTableName.TABLE_DIRECTORY, new TTFDirTabEntry(0, currentPos)); + newDirTabs.put(OFTableName.TABLE_DIRECTORY, new OFDirTabEntry(0, currentPos)); } - private void writeTableName(TTFTableName tableName) { + private void writeTableName(OFTableName tableName) { writeString(tableName.getName()); offsets.put(tableName, currentPos); currentPos += 12; @@ -148,15 +148,15 @@ public class TTFSubSetFile extends TTFFile { private boolean hasCvt() { - return dirTabs.containsKey(TTFTableName.CVT); + return dirTabs.containsKey(OFTableName.CVT); } private boolean hasFpgm() { - return dirTabs.containsKey(TTFTableName.FPGM); + return dirTabs.containsKey(OFTableName.FPGM); } private boolean hasPrep() { - return dirTabs.containsKey(TTFTableName.PREP); + return dirTabs.containsKey(OFTableName.PREP); } /** @@ -165,15 +165,15 @@ public class TTFSubSetFile extends TTFFile { private void createLoca(int size) throws IOException { pad4(); locaOffset = currentPos; - int dirTableOffset = offsets.get(TTFTableName.LOCA); + int dirTableOffset = offsets.get(OFTableName.LOCA); writeULong(dirTableOffset + 4, currentPos); writeULong(dirTableOffset + 8, size * 4 + 4); currentPos += size * 4 + 4; realSize += size * 4 + 4; } - private boolean copyTable(FontFileReader in, TTFTableName tableName) throws IOException { - TTFDirTabEntry entry = dirTabs.get(tableName); + private boolean copyTable(FontFileReader in, OFTableName tableName) throws IOException { + OFDirTabEntry entry = dirTabs.get(tableName); if (entry != null) { pad4(); seekTab(in, tableName, 0); @@ -193,28 +193,28 @@ public class TTFSubSetFile extends TTFFile { * Copy the cvt table as is from original font to subset font */ private boolean createCvt(FontFileReader in) throws IOException { - return copyTable(in, TTFTableName.CVT); + return copyTable(in, OFTableName.CVT); } /** * Copy the fpgm table as is from original font to subset font */ private boolean createFpgm(FontFileReader in) throws IOException { - return copyTable(in, TTFTableName.FPGM); + return copyTable(in, OFTableName.FPGM); } /** * Copy the name table as is from the original. */ private boolean createName(FontFileReader in) throws IOException { - return copyTable(in, TTFTableName.NAME); + return copyTable(in, OFTableName.NAME); } /** * Copy the OS/2 table as is from the original. */ private boolean createOS2(FontFileReader in) throws IOException { - return copyTable(in, TTFTableName.OS2); + return copyTable(in, OFTableName.OS2); } /** @@ -222,8 +222,8 @@ public class TTFSubSetFile extends TTFFile { * and set num glyphs to size */ private void createMaxp(FontFileReader in, int size) throws IOException { - TTFTableName maxp = TTFTableName.MAXP; - TTFDirTabEntry entry = dirTabs.get(maxp); + OFTableName maxp = OFTableName.MAXP; + OFDirTabEntry entry = dirTabs.get(maxp); if (entry != null) { pad4(); seekTab(in, maxp, 0); @@ -240,8 +240,8 @@ public class TTFSubSetFile extends TTFFile { } private void createPost(FontFileReader in) throws IOException { - TTFTableName post = TTFTableName.POST; - TTFDirTabEntry entry = dirTabs.get(post); + OFTableName post = OFTableName.POST; + OFDirTabEntry entry = dirTabs.get(post); if (entry != null) { pad4(); seekTab(in, post, 0); @@ -266,7 +266,7 @@ public class TTFSubSetFile extends TTFFile { * Copy the prep table as is from original font to subset font */ private boolean createPrep(FontFileReader in) throws IOException { - return copyTable(in, TTFTableName.PREP); + return copyTable(in, OFTableName.PREP); } @@ -275,15 +275,15 @@ public class TTFSubSetFile extends TTFFile { * and fill in size of hmtx table */ private void createHhea(FontFileReader in, int size) throws IOException { - TTFDirTabEntry entry = dirTabs.get(TTFTableName.HHEA); + OFDirTabEntry entry = dirTabs.get(OFTableName.HHEA); if (entry != null) { pad4(); - seekTab(in, TTFTableName.HHEA, 0); + seekTab(in, OFTableName.HHEA, 0); System.arraycopy(in.getBytes((int) entry.getOffset(), (int) entry.getLength()), 0, output, currentPos, (int) entry.getLength()); writeUShort((int) entry.getLength() + currentPos - 2, size); - updateCheckSum(currentPos, (int) entry.getLength(), TTFTableName.HHEA); + updateCheckSum(currentPos, (int) entry.getLength(), OFTableName.HHEA); currentPos += (int) entry.getLength(); realSize += (int) entry.getLength(); } else { @@ -299,8 +299,8 @@ public class TTFSubSetFile extends TTFFile { * in checkSumAdjustmentOffset */ private void createHead(FontFileReader in) throws IOException { - TTFTableName head = TTFTableName.HEAD; - TTFDirTabEntry entry = dirTabs.get(head); + OFTableName head = OFTableName.HEAD; + OFDirTabEntry entry = dirTabs.get(head); if (entry != null) { pad4(); seekTab(in, head, 0); @@ -329,8 +329,8 @@ public class TTFSubSetFile extends TTFFile { */ private void createGlyf(FontFileReader in, Map glyphs) throws IOException { - TTFTableName glyf = TTFTableName.GLYF; - TTFDirTabEntry entry = dirTabs.get(glyf); + OFTableName glyf = OFTableName.GLYF; + OFDirTabEntry entry = dirTabs.get(glyf); int size = 0; int startPos = 0; int endOffset = 0; // Store this as the last loca @@ -393,10 +393,10 @@ public class TTFSubSetFile extends TTFFile { writeULong(locaOffset + glyphs.size() * 4, endOffset); int locaSize = glyphs.size() * 4 + 4; int checksum = getCheckSum(output, locaOffset, locaSize); - writeULong(offsets.get(TTFTableName.LOCA), checksum); + writeULong(offsets.get(OFTableName.LOCA), checksum); int padSize = (locaOffset + locaSize) % 4; - newDirTabs.put(TTFTableName.LOCA, - new TTFDirTabEntry(locaOffset, locaSize + padSize)); + newDirTabs.put(OFTableName.LOCA, + new OFDirTabEntry(locaOffset, locaSize + padSize)); } else { throw new IOException("Can't find glyf table"); } @@ -420,8 +420,8 @@ public class TTFSubSetFile extends TTFFile { */ private void createHmtx(FontFileReader in, Map glyphs) throws IOException { - TTFTableName hmtx = TTFTableName.HMTX; - TTFDirTabEntry entry = dirTabs.get(hmtx); + OFTableName hmtx = OFTableName.HMTX; + OFDirTabEntry entry = dirTabs.get(hmtx); int longHorMetricSize = glyphs.size() * 2; int leftSideBearingSize = glyphs.size() * 2; @@ -457,11 +457,11 @@ public class TTFSubSetFile extends TTFFile { * new index as (Integer) value) * @throws IOException in case of an I/O problem */ - public void readFont(FontFileReader in, String name, + public void readFont(FontFileReader in, String name, String header, Map glyphs) throws IOException { fontFile = in; //Check if TrueType collection, and that the name exists in the collection - if (!checkTTC(name)) { + if (!checkTTC(header, name)) { throw new IOException("Failed to read font"); } @@ -533,7 +533,7 @@ public class TTFSubSetFile extends TTFFile { glyphOffsets[i + 1] - glyphOffsets[i]); } // Stream the last glyph - TTFDirTabEntry glyf = newDirTabs.get(TTFTableName.GLYF); + OFDirTabEntry glyf = newDirTabs.get(OFTableName.GLYF); long lastGlyphLength = glyf.getLength() - (glyphOffsets[glyphOffsets.length - 1] - glyf.getOffset()); glyphOut.streamGlyph(output, glyphOffsets[glyphOffsets.length - 1], @@ -543,14 +543,14 @@ public class TTFSubSetFile extends TTFFile { @Override public void stream(TTFOutputStream ttfOut) throws IOException { - SortedSet> sortedDirTabs + SortedSet> sortedDirTabs = sortDirTabMap(newDirTabs); TTFTableOutputStream tableOut = ttfOut.getTableOutputStream(); TTFGlyphOutputStream glyphOut = ttfOut.getGlyphOutputStream(); ttfOut.startFontStream(); - for (Map.Entry entry : sortedDirTabs) { - if (entry.getKey().equals(TTFTableName.GLYF)) { + for (Map.Entry entry : sortedDirTabs) { + if (entry.getKey().equals(OFTableName.GLYF)) { handleGlyphSubset(glyphOut); } else { tableOut.streamTable(output, (int) entry.getValue().getOffset(), @@ -562,7 +562,7 @@ public class TTFSubSetFile extends TTFFile { private void scanGlyphs(FontFileReader in, Map subsetGlyphs) throws IOException { - TTFDirTabEntry glyfTableInfo = dirTabs.get(TTFTableName.GLYF); + OFDirTabEntry glyfTableInfo = dirTabs.get(OFTableName.GLYF); if (glyfTableInfo == null) { throw new IOException("Glyf table could not be found"); } @@ -663,11 +663,11 @@ public class TTFSubSetFile extends TTFFile { } - private void updateCheckSum(int tableStart, int tableSize, TTFTableName tableName) { + private void updateCheckSum(int tableStart, int tableSize, OFTableName tableName) { int checksum = getCheckSum(output, tableStart, tableSize); int offset = offsets.get(tableName); int padSize = getPadSize(tableStart + tableSize); - newDirTabs.put(tableName, new TTFDirTabEntry(tableStart, tableSize + padSize)); + newDirTabs.put(tableName, new OFDirTabEntry(tableStart, tableSize + padSize)); writeULong(offset, checksum); writeULong(offset + 4, tableStart); writeULong(offset + 8, tableSize); diff --git a/src/java/org/apache/fop/pdf/PDFCFFStreamType0C.java b/src/java/org/apache/fop/pdf/PDFCFFStreamType0C.java new file mode 100644 index 000000000..53f0b36b4 --- /dev/null +++ b/src/java/org/apache/fop/pdf/PDFCFFStreamType0C.java @@ -0,0 +1,74 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.pdf; + +import java.io.IOException; +import java.io.OutputStream; + +/** + * PDFStream for embeddable OpenType CFF fonts. + */ +public class PDFCFFStreamType0C extends AbstractPDFFontStream { + + private byte[] cffData; + private boolean fullEmbed; + + /** + * Main constructor + * @param fullEmbed Determines whether the font is fully embedded + */ + public PDFCFFStreamType0C(boolean fullEmbed) { + super(); + this.fullEmbed = fullEmbed; + } + + protected int getSizeHint() throws IOException { + if (this.cffData != null) { + return cffData.length; + } else { + return 0; //no hint available + } + } + + /** {@inheritDoc} */ + protected void outputRawStreamData(OutputStream out) throws IOException { + out.write(this.cffData); + } + + /** {@inheritDoc} */ + protected void populateStreamDict(Object lengthEntry) { + String type = (fullEmbed) ? "OpenType" : "CIDFontType0C"; + put("Subtype", new PDFName(type)); + super.populateStreamDict(lengthEntry); + } + + /** + * Sets the CFF font data. + * @param data the font payload + * @param size size of the payload + * @throws IOException in case of an I/O problem + */ + public void setData(byte[] data, int size) throws IOException { + this.cffData = new byte[size]; + System.arraycopy(data, 0, this.cffData, 0, size); + } + +} + diff --git a/src/java/org/apache/fop/pdf/PDFEncryptionJCE.java b/src/java/org/apache/fop/pdf/PDFEncryptionJCE.java index 2fe9f29e0..8fd8d3444 100644 --- a/src/java/org/apache/fop/pdf/PDFEncryptionJCE.java +++ b/src/java/org/apache/fop/pdf/PDFEncryptionJCE.java @@ -449,14 +449,13 @@ public final class PDFEncryptionJCE extends PDFObject implements PDFEncryption { private class Rev5Engine extends InitializationEngine { - // private SecureRandom random = new SecureRandom(); - private byte[] userValidationSalt = new byte[8]; - private byte[] userKeySalt = new byte[8]; - private byte[] ownerValidationSalt = new byte[8]; - private byte[] ownerKeySalt = new byte[8]; - private byte[] ueValue; - private byte[] oeValue; - private final boolean encryptMetadata; + protected byte[] userValidationSalt = new byte[8]; + protected byte[] userKeySalt = new byte[8]; + protected byte[] ownerValidationSalt = new byte[8]; + protected byte[] ownerKeySalt = new byte[8]; + protected byte[] ueValue; + protected byte[] oeValue; + protected final boolean encryptMetadata; Rev5Engine(EncryptionSettings encryptionSettings) { super(encryptionSettings); @@ -563,7 +562,7 @@ public final class PDFEncryptionJCE extends PDFObject implements PDFEncryption { /** * Algorithm 3.8-2 (page 20, Adobe Supplement to the ISO 32000, BaseVersion: 1.7, ExtensionLevel: 3) */ - private void computeUEValue() { + protected void computeUEValue() { digest.reset(); byte[] prepared = preparedUserPassword; byte[] concatenated = new byte[prepared.length + 8]; @@ -577,7 +576,7 @@ public final class PDFEncryptionJCE extends PDFObject implements PDFEncryption { /** * Algorithm 3.9-2 (page 20, Adobe Supplement to the ISO 32000, BaseVersion: 1.7, ExtensionLevel: 3) */ - private void computeOEValue() { + protected void computeOEValue() { digest.reset(); byte[] prepared = preparedOwnerPassword; byte[] concatenated = new byte[prepared.length + 56]; @@ -615,6 +614,86 @@ public final class PDFEncryptionJCE extends PDFObject implements PDFEncryption { } } + private class Rev6Engine extends Rev5Engine { + + private MessageDigest digest384; + private MessageDigest digest512; + + Rev6Engine(EncryptionSettings encryptionSettings) { + super(encryptionSettings); + try { + digest384 = MessageDigest.getInstance("SHA-384"); + digest512 = MessageDigest.getInstance("SHA-512"); + } catch (NoSuchAlgorithmException e) { + throw new UnsupportedOperationException(e.getMessage()); + } + } + + @Override + protected void computeUValue() { + byte[] userBytes = new byte[16]; + random.nextBytes(userBytes); + System.arraycopy(userBytes, 0, userValidationSalt, 0, 8); + System.arraycopy(userBytes, 8, userKeySalt, 0, 8); + digest.reset(); + byte[] prepared = preparedUserPassword; + byte[] concatenated = new byte[prepared.length + 8]; + System.arraycopy(prepared, 0, concatenated, 0, prepared.length); + System.arraycopy(userValidationSalt, 0, concatenated, prepared.length, 8); + digest.update(concatenated); + byte[] block = digest.digest(); + int blockSize = 32; + byte[] key = new byte[16]; + byte[] iv = new byte[16]; + int length = prepared.length + blockSize; + byte[] data = new byte[length * 64]; + for (int i = 0; i < 64 || i < data[length * 64 - 1] + 32; i++) { + System.arraycopy(block, 0, key, 0, 16); + System.arraycopy(block, 16, iv, 0, 16); + for (int j = 0; j < 64; j++) { + System.arraycopy(prepared, 0, data, j * length, prepared.length); + System.arraycopy(block, 0, data, j * length + prepared.length, blockSize); + } + try { + final Cipher cipher = PDFEncryptionJCE.initCipher(key, false, iv); + data = cipher.doFinal(data); + } catch (IllegalBlockSizeException e) { + throw new IllegalStateException(e.getMessage()); + } catch (BadPaddingException e) { + throw new IllegalStateException(e.getMessage()); + } + int sum = 0; + for (int k = 0; k < 16; k++) { + sum += data[k]; + } + blockSize = 32 + (sum % 3) * 16; + switch (blockSize) { + case 32: + digest.reset(); + digest.update(data); + block = digest.digest(); + break; + case 48: + digest384.reset(); + digest384.update(data); + block = digest384.digest(); + break; + case 64: + digest512.reset(); + digest512.update(data); + block = digest512.digest(); + break; + default: + // not possible + break; + } + length = prepared.length + blockSize; + data = new byte[length * 64]; + } + } + + } + private class EncryptionFilter extends PDFFilter { private int streamNumber; diff --git a/src/java/org/apache/fop/pdf/PDFFactory.java b/src/java/org/apache/fop/pdf/PDFFactory.java index 1756f1d56..631499af1 100644 --- a/src/java/org/apache/fop/pdf/PDFFactory.java +++ b/src/java/org/apache/fop/pdf/PDFFactory.java @@ -56,6 +56,8 @@ import org.apache.fop.fonts.SingleByteEncoding; import org.apache.fop.fonts.SingleByteFont; import org.apache.fop.fonts.Typeface; import org.apache.fop.fonts.truetype.FontFileReader; +import org.apache.fop.fonts.truetype.OFFontLoader; +import org.apache.fop.fonts.truetype.OTFSubSetFile; import org.apache.fop.fonts.truetype.TTFSubSetFile; import org.apache.fop.fonts.type1.PFBData; import org.apache.fop.fonts.type1.PFBParser; @@ -1387,15 +1389,15 @@ public class PDFFactory { int firstChar = singleByteFont.getFirstChar(); int lastChar = singleByteFont.getLastChar(); nonBase14.setWidthMetrics(firstChar, - lastChar, - new PDFArray(null, metrics.getWidths())); + lastChar, + new PDFArray(null, metrics.getWidths())); //Handle encoding SingleByteEncoding mapping = singleByteFont.getEncoding(); if (singleByteFont.isSymbolicFont()) { //no encoding, use the font's encoding if (forceToUnicode) { - generateToUnicodeCmap(nonBase14, mapping); + generateToUnicodeCmap(nonBase14, mapping); } } else if (PDFEncoding.isPredefinedEncoding(mapping.getName())) { font.setEncoding(mapping.getName()); @@ -1403,7 +1405,7 @@ public class PDFFactory { //believed. } else { Object pdfEncoding = createPDFEncoding(mapping, - singleByteFont.getFontName()); + singleByteFont.getFontName()); if (pdfEncoding instanceof PDFEncoding) { font.setEncoding((PDFEncoding)pdfEncoding); } else { @@ -1518,7 +1520,8 @@ public class PDFFactory { // Check if the font is embeddable if (desc.isEmbeddable()) { - AbstractPDFStream stream = makeFontFile(desc); + AbstractPDFStream stream = makeFontFile(desc, fontPrefix); + if (stream != null) { descriptor.setFontFile(desc.getFontType(), stream); getDocument().registerObject(stream); @@ -1564,7 +1567,7 @@ public class PDFFactory { * @param desc FontDescriptor of the font. * @return PDFStream The embedded font file */ - public AbstractPDFStream makeFontFile(FontDescriptor desc) { + public AbstractPDFStream makeFontFile(FontDescriptor desc, String fontPrefix) { if (desc.getFontType() == FontType.OTHER) { throw new IllegalArgumentException("Trying to embed unsupported font type: " + desc.getFontType()); @@ -1578,20 +1581,24 @@ public class PDFFactory { if (in == null) { return null; } else { - AbstractPDFStream embeddedFont; + AbstractPDFStream embeddedFont = null; if (desc.getFontType() == FontType.TYPE0) { MultiByteFont mbfont = (MultiByteFont) font; FontFileReader reader = new FontFileReader(in); byte[] fontBytes; + String header = OFFontLoader.readHeader(reader); + boolean isCFF = mbfont.isOTFFile(); if (font.getEmbeddingMode() == EmbeddingMode.FULL) { fontBytes = reader.getAllBytes(); + if (isCFF) { + //Ensure version 1.6 for full OTF CFF embedding + document.setPDFVersion(Version.V1_6); + } } else { - TTFSubSetFile ttfFile = new TTFSubSetFile(); - ttfFile.readFont(reader, mbfont.getTTCName(), mbfont.getUsedGlyphs()); - fontBytes = ttfFile.getFontSubset(); + fontBytes = getFontSubsetBytes(reader, mbfont, header, fontPrefix, desc, + isCFF); } - embeddedFont = new PDFTTFStream(fontBytes.length); - ((PDFTTFStream) embeddedFont).setData(fontBytes, fontBytes.length); + embeddedFont = getFontStream(font, fontBytes, isCFF); } else if (desc.getFontType() == FontType.TYPE1) { PFBParser parser = new PFBParser(); PFBData pfb = parser.parsePFB(in); @@ -1621,6 +1628,32 @@ public class PDFFactory { } } + private byte[] getFontSubsetBytes(FontFileReader reader, MultiByteFont mbfont, String header, + String fontPrefix, FontDescriptor desc, boolean isCFF) throws IOException { + if (isCFF) { + OTFSubSetFile otfFile = new OTFSubSetFile(); + otfFile.readFont(reader, fontPrefix + desc.getEmbedFontName(), header, mbfont); + return otfFile.getFontSubset(); + } else { + TTFSubSetFile otfFile = new TTFSubSetFile(); + otfFile.readFont(reader, mbfont.getTTCName(), header, mbfont.getUsedGlyphs()); + return otfFile.getFontSubset(); + } + } + + private AbstractPDFStream getFontStream(CustomFont font, byte[] fontBytes, boolean isCFF) + throws IOException { + AbstractPDFStream embeddedFont; + if (isCFF) { + embeddedFont = new PDFCFFStreamType0C(font.getEmbeddingMode() == EmbeddingMode.FULL); + ((PDFCFFStreamType0C) embeddedFont).setData(fontBytes, fontBytes.length); + } else { + embeddedFont = new PDFTTFStream(fontBytes.length); + ((PDFTTFStream) embeddedFont).setData(fontBytes, fontBytes.length); + } + return embeddedFont; + } + private CustomFont getCustomFont(FontDescriptor desc) { Typeface tempFont; if (desc instanceof LazyFont) { diff --git a/src/java/org/apache/fop/pdf/PDFFontDescriptor.java b/src/java/org/apache/fop/pdf/PDFFontDescriptor.java index ec4e99101..73dbebc3f 100644 --- a/src/java/org/apache/fop/pdf/PDFFontDescriptor.java +++ b/src/java/org/apache/fop/pdf/PDFFontDescriptor.java @@ -102,6 +102,8 @@ public class PDFFontDescriptor extends PDFDictionary { public void setFontFile(FontType subtype, AbstractPDFStream fontfile) { if (subtype == FontType.TYPE1) { put("FontFile", fontfile); + } else if (fontfile instanceof PDFCFFStreamType0C) { + put("FontFile3", fontfile); } else { put("FontFile2", fontfile); } diff --git a/src/java/org/apache/fop/render/ps/PSFontUtils.java b/src/java/org/apache/fop/render/ps/PSFontUtils.java index e57567b88..c22a3ba28 100644 --- a/src/java/org/apache/fop/render/ps/PSFontUtils.java +++ b/src/java/org/apache/fop/render/ps/PSFontUtils.java @@ -29,6 +29,7 @@ import java.util.Set; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; +import org.apache.fontbox.cff.CFFStandardString; import org.apache.xmlgraphics.fonts.Glyphs; import org.apache.xmlgraphics.ps.DSCConstants; @@ -50,9 +51,14 @@ import org.apache.fop.fonts.MultiByteFont; import org.apache.fop.fonts.SingleByteEncoding; import org.apache.fop.fonts.SingleByteFont; import org.apache.fop.fonts.Typeface; +import org.apache.fop.fonts.cff.CFFDataReader; +import org.apache.fop.fonts.cff.CFFDataReader.DICTEntry; import org.apache.fop.fonts.truetype.FontFileReader; +import org.apache.fop.fonts.truetype.OFFontLoader; +import org.apache.fop.fonts.truetype.OTFFile; +import org.apache.fop.fonts.truetype.OTFSubSetFile; +import org.apache.fop.fonts.truetype.OpenFont.PostScriptVersion; import org.apache.fop.fonts.truetype.TTFFile; -import org.apache.fop.fonts.truetype.TTFFile.PostScriptVersion; import org.apache.fop.fonts.truetype.TTFOutputStream; import org.apache.fop.fonts.truetype.TTFSubSetFile; import org.apache.fop.render.ps.fonts.PSTTFOutputStream; @@ -221,6 +227,7 @@ public class PSFontUtils extends org.apache.xmlgraphics.ps.PSFontUtils { private static PSFontResource embedFont(PSGenerator gen, Typeface tf, PSResource fontRes, PSEventProducer eventProducer) throws IOException { + boolean embeddedFont = false; FontType fontType = tf.getFontType(); PSFontResource fontResource = null; if (!(fontType == FontType.TYPE1 || fontType == FontType.TRUETYPE @@ -232,52 +239,63 @@ public class PSFontUtils extends org.apache.xmlgraphics.ps.PSFontUtils { CustomFont cf = (CustomFont)tf; if (isEmbeddable(cf)) { InputStream in = getInputStreamOnFont(gen, cf); - if (in == null) { + if (in != null) { + if (fontType == FontType.TYPE0) { + if (((MultiByteFont)tf).isOTFFile()) { + checkPostScriptLevel3(gen, eventProducer, "OpenType CFF"); + embedType2CFF(gen, (MultiByteFont) tf, in); + } else { + if (gen.embedIdentityH()) { + checkPostScriptLevel3(gen, eventProducer, "TrueType"); + /* + * First CID-keyed font to be embedded; add + * %%IncludeResource: comment for ProcSet CIDInit. + */ + gen.includeProcsetCIDInitResource(); + } + PSResource cidFontResource; + cidFontResource = embedType2CIDFont(gen, + (MultiByteFont) tf, in); + fontResource = PSFontResource.createFontResource(fontRes, + gen.getProcsetCIDInitResource(), gen.getIdentityHCMapResource(), + cidFontResource); + } + } + gen.writeDSCComment(DSCConstants.BEGIN_RESOURCE, fontRes); + if (fontType == FontType.TYPE1) { + embedType1Font(gen, in); + fontResource = PSFontResource.createFontResource(fontRes); + } else if (fontType == FontType.TRUETYPE) { + embedTrueTypeFont(gen, (SingleByteFont) tf, in); + fontResource = PSFontResource.createFontResource(fontRes); + } else { + composeType0Font(gen, (MultiByteFont) tf, in); + } + gen.writeDSCComment(DSCConstants.END_RESOURCE); + gen.getResourceTracker().registerSuppliedResource(fontRes); + embeddedFont = true; + } else { gen.commentln("%WARNING: Could not embed font: " + cf.getEmbedFontName()); log.warn("Font " + cf.getEmbedFontName() + " is marked as supplied in the" + " PostScript file but could not be embedded!"); - gen.writeDSCComment(DSCConstants.INCLUDE_RESOURCE, fontRes); - fontResource = PSFontResource.createFontResource(fontRes); - return fontResource; - } - if (fontType == FontType.TYPE0) { - if (gen.embedIdentityH()) { - checkPostScriptLevel3(gen, eventProducer); - /* - * First CID-keyed font to be embedded; add - * %%IncludeResource: comment for ProcSet CIDInit. - */ - gen.includeProcsetCIDInitResource(); - } - PSResource cidFontResource = embedType2CIDFont(gen, - (MultiByteFont) tf, in); - fontResource = PSFontResource.createFontResource(fontRes, - gen.getProcsetCIDInitResource(), gen.getIdentityHCMapResource(), - cidFontResource); } - gen.writeDSCComment(DSCConstants.BEGIN_RESOURCE, fontRes); - if (fontType == FontType.TYPE1) { - embedType1Font(gen, in); - fontResource = PSFontResource.createFontResource(fontRes); - } else if (fontType == FontType.TRUETYPE) { - embedTrueTypeFont(gen, (SingleByteFont) tf, in); - fontResource = PSFontResource.createFontResource(fontRes); - } else { - composeType0Font(gen, (MultiByteFont) tf, in); - } - gen.writeDSCComment(DSCConstants.END_RESOURCE); - gen.getResourceTracker().registerSuppliedResource(fontRes); + } + if (!embeddedFont) { + gen.writeDSCComment(DSCConstants.INCLUDE_RESOURCE, fontRes); + fontResource = PSFontResource.createFontResource(fontRes); + return fontResource; } return fontResource; } - private static void checkPostScriptLevel3(PSGenerator gen, PSEventProducer eventProducer) { + private static void checkPostScriptLevel3(PSGenerator gen, PSEventProducer eventProducer, + String fontType) { if (gen.getPSLevel() < 3) { if (eventProducer != null) { eventProducer.postscriptLevel3Needed(gen); } else { throw new IllegalStateException("PostScript Level 3 is" - + " required to use TrueType fonts," + + " required to use " + fontType + " fonts," + " configured level is " + gen.getPSLevel()); } @@ -415,6 +433,96 @@ public class PSFontUtils extends org.apache.xmlgraphics.ps.PSFontUtils { gen.writeln("] composefont pop"); } + private static void embedType2CFF(PSGenerator gen, + MultiByteFont font, InputStream fontStream) throws IOException { + FontFileReader reader = new FontFileReader(fontStream); + String header = OFFontLoader.readHeader(reader); + String psName; + CFFDataReader cffReader = new CFFDataReader(reader); + if (cffReader.getFDSelect() != null) { + throw new UnsupportedOperationException("CID-Keyed OTF CFF fonts are not supported" + + " for PostScript output."); + } + + byte[] bytes; + if (font.getEmbeddingMode() == EmbeddingMode.FULL) { + font.setFontName(new String(cffReader.getNameIndex().getValue(0))); + psName = font.getEmbedFontName(); + Map topDICT = cffReader.getTopDictEntries(); + int charsetOffset = topDICT.get("charset").getOperands().get(0).intValue(); + for (int gid = 0; gid < cffReader.getCharStringIndex().getNumObjects(); gid++) { + int sid = cffReader.getSIDFromGID(charsetOffset, gid); + + //Check whether the SID falls into the standard string set + if (sid < 391) { + font.mapUsedGlyphName(gid, + CFFStandardString.getName(sid)); + } else { + int index = sid - 391; + if (index < cffReader.getStringIndex().getNumObjects()) { + font.mapUsedGlyphName(gid, + new String(cffReader.getStringIndex().getValue(index))); + } else { + font.mapUsedGlyphName(gid, ".notdef"); + } + } + } + bytes = OTFFile.getCFFData(reader); + } else { + psName = font.getEmbedFontName(); + OTFSubSetFile otfFile = new OTFSubSetFile(); + otfFile.readFont(reader, psName, header, font); + bytes = otfFile.getFontSubset(); + } + + gen.writeln("%!PS-Adobe-3.0 Resource-FontSet"); + gen.writeln("%%DocumentNeedResources:ProcSet(FontSetInit)"); + gen.writeln("%%Title:(FontSet/" + psName + ")"); + gen.writeln("%%Version: 1.000"); + gen.writeln("%%EndComments"); + gen.writeln("%%IncludeResource:ProcSet(FontSetInit)"); + gen.writeln("%%BeginResource: FontSet (" + psName + ")"); + gen.writeln("/FontSetInit /ProcSet findresource begin"); + //Next line + 1 + String fontDeclaration = "/" + psName + " " + bytes.length + " StartData"; + gen.writeln("%%BeginData: " + (fontDeclaration.length() + 1 + bytes.length) + " Binary Bytes"); + gen.writeln(fontDeclaration); + gen.writeByteArr(bytes); + gen.writeln("%%EndData"); + gen.writeln("%%EndResource"); + + gen.writeln("/" + psName + ".0.enc [ "); + int lengthCount = 0; + int charCount = 1; + int encodingCount = 0; + String line = ""; + for (int gid : font.getUsedGlyphNames().keySet()) { + line += "/" + font.getUsedGlyphNames().get(gid) + " "; + lengthCount++; + charCount++; + if (lengthCount == 8) { + gen.writeln(line); + line = ""; + lengthCount = 0; + } + if (charCount > 256) { + encodingCount++; + charCount = 1; + gen.writeln(line); + line = ""; + lengthCount = 0; + gen.writeln("] def"); + gen.writeln(String.format("/%s.%d %s.%d.enc /%s RE", psName, + encodingCount - 1, psName, encodingCount - 1, psName)); + gen.writeln("/" + psName + "." + encodingCount + ".enc [ "); + } + } + gen.writeln(line); + gen.writeln("] def"); + gen.writeln(String.format("/%s.%d %s.%d.enc /%s RE", psName, encodingCount, + psName, encodingCount, psName)); + } + private static PSResource embedType2CIDFont(PSGenerator gen, MultiByteFont font, InputStream fontStream) throws IOException { assert font.getCIDType() == CIDFontType.CIDTYPE2; @@ -502,17 +610,18 @@ public class PSFontUtils extends org.apache.xmlgraphics.ps.PSFontUtils { } gen.writeln(">] def"); FontFileReader reader = new FontFileReader(fontStream); + String header = OFFontLoader.readHeader(reader); TTFFile ttfFile; if (font.getEmbeddingMode() != EmbeddingMode.FULL) { ttfFile = new TTFSubSetFile(); - ttfFile.readFont(reader, font.getTTCName(), font.getUsedGlyphs()); + //Change the TTFFile to have the abstract method for TTFSubSetFile + ((TTFSubSetFile)ttfFile).readFont(reader, font.getTTCName(), header, font.getUsedGlyphs()); } else { ttfFile = new TTFFile(); ttfFile.readFont(reader, font.getTTCName()); } - createType42DictionaryEntries(gen, font, new CMapSegment[0], ttfFile); gen.writeln("CIDFontName currentdict end /CIDFont defineresource pop"); gen.writeln("end"); @@ -670,7 +779,7 @@ public class PSFontUtils extends org.apache.xmlgraphics.ps.PSFontUtils { private static PSResource defineDerivedTrueTypeFont(PSGenerator gen, PSEventProducer eventProducer, String baseFontName, String fontName, SingleByteEncoding encoding, CMapSegment[] cmap) throws IOException { - checkPostScriptLevel3(gen, eventProducer); + checkPostScriptLevel3(gen, eventProducer, "TrueType"); PSResource res = new PSResource(PSResource.TYPE_FONT, fontName); gen.writeDSCComment(DSCConstants.BEGIN_RESOURCE, res); gen.commentln("%XGCDependencies: font " + baseFontName); diff --git a/src/java/org/apache/fop/render/ps/PSPainter.java b/src/java/org/apache/fop/render/ps/PSPainter.java index b0b370c79..3d1887f2d 100644 --- a/src/java/org/apache/fop/render/ps/PSPainter.java +++ b/src/java/org/apache/fop/render/ps/PSPainter.java @@ -40,6 +40,7 @@ import org.apache.xmlgraphics.image.loader.ImageSessionContext; import org.apache.xmlgraphics.ps.PSGenerator; import org.apache.xmlgraphics.ps.PSResource; +import org.apache.fop.fonts.EmbeddingMode; import org.apache.fop.fonts.Font; import org.apache.fop.fonts.FontTriplet; import org.apache.fop.fonts.LazyFont; @@ -375,7 +376,13 @@ public class PSPainter extends AbstractIFPainter { } Font font = getFontInfo().getFontInstance(triplet, sizeMillipoints); - useFont(fontKey, sizeMillipoints); + PSFontResource res = getDocumentHandler().getPSResourceForFontKey(fontKey); + if (tf instanceof MultiByteFont && ((MultiByteFont)tf).isOTFFile()) { + generator.writeln("/" + res.getName() + ".0 " + + generator.formatDouble(sizeMillipoints / 1000f) + " F"); + } else { + useFont(fontKey, sizeMillipoints); + } if (dp != null && dp[0] != null) { x += dp[0][0]; @@ -408,7 +415,30 @@ public class PSPainter extends AbstractIFPainter { } } } else { - useFont(fontKey, sizeMillipoints); + if (tf instanceof MultiByteFont && ((MultiByteFont)tf).isOTFFile()) { + //Analyze string and split up in order to paint in different sub-fonts/encodings + int curEncoding = 0; + for (int i = start; i < textLen; i++) { + char orgChar = text.charAt(i); + + MultiByteFont mbFont = (MultiByteFont)tf; + int origGlyphIdx = mbFont.findGlyphIndex(orgChar); + int newGlyphIdx = mbFont.getUsedGlyphs().get(origGlyphIdx); + int encoding = newGlyphIdx / 256; + if (encoding != curEncoding) { + if (i != 0) { + writeText(text, start, i - start, letterSpacing, wordSpacing, dp, font, tf, + true); + start = i; + } + generator.writeln("/" + res.getName() + "." + encoding + " " + + generator.formatDouble(sizeMillipoints / 1000f) + " F"); + curEncoding = encoding; + } + } + } else { + useFont(fontKey, sizeMillipoints); + } } writeText(text, start, textLen - start, letterSpacing, wordSpacing, dp, font, tf, tf instanceof MultiByteFont); @@ -431,12 +461,14 @@ public class PSPainter extends AbstractIFPainter { int lineStart = 0; StringBuffer accText = new StringBuffer(initialSize); StringBuffer sb = new StringBuffer(initialSize); + boolean isOTF = multiByte && ((MultiByteFont)tf).isOTFFile(); for (int i = start; i < end; i++) { char orgChar = text.charAt(i); char ch; int cw; int xGlyphAdjust = 0; int yGlyphAdjust = 0; + if (CharUtilities.isFixedWidthSpace(orgChar)) { //Fixed width space are rendered as spaces so copy/paste works in a reader ch = font.mapChar(CharUtilities.SPACE); @@ -460,11 +492,16 @@ public class PSPainter extends AbstractIFPainter { xGlyphAdjust -= dp[i + 1][0]; yGlyphAdjust += dp[i + 1][1]; } - if (multiByte) { - accText.append(HexEncoder.encode(ch)); - } else { + if (!multiByte || isOTF) { char codepoint = (char)(ch % 256); - PSGenerator.escapeChar(codepoint, accText); //add character to accumulated text + if (isOTF) { + codepoint -= (((MultiByteFont)tf).getEmbeddingMode() == EmbeddingMode.FULL) ? 0 : 1; + accText.append(HexEncoder.encode(codepoint, 2)); + } else { + PSGenerator.escapeChar(codepoint, accText); //add character to accumulated text + } + } else { + accText.append(HexEncoder.encode(ch)); } if (xGlyphAdjust != 0 || yGlyphAdjust != 0) { needTJ = true; diff --git a/test/java/org/apache/fop/fonts/cff/CFFDataReaderTestCase.java b/test/java/org/apache/fop/fonts/cff/CFFDataReaderTestCase.java new file mode 100644 index 000000000..64c7642eb --- /dev/null +++ b/test/java/org/apache/fop/fonts/cff/CFFDataReaderTestCase.java @@ -0,0 +1,154 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.cff; + +import java.io.IOException; +import java.util.Map; +import java.util.Random; + +import org.junit.Before; +import org.junit.Test; + +import org.apache.fontbox.cff.CFFDataInput; + +import org.apache.fop.fonts.cff.CFFDataReader.CFFIndexData; +import org.apache.fop.fonts.cff.CFFDataReader.DICTEntry; +import org.apache.fop.fonts.truetype.OTFSubSetFile; + +import static org.junit.Assert.assertEquals; + +public class CFFDataReaderTestCase { + private CFFDataReader cffReader; + + /** + * Initializes the CFFDataReader for testing purposes + */ + @Before + public void setUp() { + cffReader = new CFFDataReader(); + } + + /** + * Parses a test dictionary to verify whether the stored data is read correctly. + * @throws IOException + */ + @Test + public void parseDictData() throws IOException { + byte[] testDictData = prepareDictData(); + Map testTopDict = cffReader.parseDictData(testDictData); + validateDictData(testTopDict); + } + + private byte[] prepareDictData() { + byte[] testDictData = new byte[0]; + //Version + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 392, new int[] { 0 }, -1)); + //Notice + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 393, new int[] { 1 }, -1)); + //Copyright + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 394, new int[] { 12, 0 }, -1)); + //FullName + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 395, new int[] { 2 }, -1)); + //FamilyName + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 396, new int[] { 3 }, -1)); + //Weight + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 397, new int[] { 4 }, -1)); + //isFixedPitch (boolean = false) + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 0, new int[] { 12, 1 }, -1)); + //FontBBox + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + -50, new int[0], -1)); + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + -40, new int[0], -1)); + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 100, new int[0], -1)); + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 120, new int[] { 5 }, -1)); + //charset + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 1234, new int[] { 15 }, -1)); + //CharStrings + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 3654, new int[] { 17 }, -1)); + //Private + testDictData = OTFSubSetFile.concatArray(testDictData, OTFSubSetFile.createNewRef( + 11454, new int[] { 18 }, -1)); + return testDictData; + } + + private void validateDictData(Map dictMap) { + //SID Values (numbers) + assertEquals(dictMap.get("version").getOperands().get(0).intValue(), 392); + assertEquals(dictMap.get("Notice").getOperands().get(0).intValue(), 393); + assertEquals(dictMap.get("Copyright").getOperands().get(0).intValue(), 394); + assertEquals(dictMap.get("FullName").getOperands().get(0).intValue(), 395); + assertEquals(dictMap.get("FamilyName").getOperands().get(0).intValue(), 396); + assertEquals(dictMap.get("Weight").getOperands().get(0).intValue(), 397); + //Boolean comparison + assertEquals(dictMap.get("isFixedPitch").getOperands().get(0).intValue(), 0); + //Array comparison + int[] fontBBox = { -50, -40, 100, 120 }; + DICTEntry fontBBoxEntry = dictMap.get("FontBBox"); + for (int i = 0;i < fontBBoxEntry.getOperands().size();i++) { + assertEquals(fontBBoxEntry.getOperands().get(i).intValue(), fontBBox[i]); + } + //Multi-byte offset (number) + assertEquals(dictMap.get("charset").getOperands().get(0).intValue(), 1234); + assertEquals(dictMap.get("CharStrings").getOperands().get(0).intValue(), 3654); + //Larger offset + assertEquals(dictMap.get("Private").getOperands().get(0).intValue(), 11454); + } + + /** + * Tests the parsing of an example byte data index structure + * @throws IOException + */ + @Test + public void testIndexParsing() throws IOException { + byte[] testIndex = { + 0, 5, //Number of objects + 1, //Offset size + 1, //Offsets... + 5, + 12, + 24, + 27, + 32 + }; + Random randGen = new Random(); + byte[] data = new byte[31]; + for (int i = 0;i < data.length;i++) { + data[i] = (byte)randGen.nextInt(255); + } + testIndex = OTFSubSetFile.concatArray(testIndex, data); + CFFIndexData indexData = cffReader.readIndex(new CFFDataInput(testIndex)); + assertEquals(indexData.getNumObjects(), 5); + assertEquals(indexData.getOffSize(), 1); + assertEquals(indexData.getOffsets().length, 6); + assertEquals(indexData.getOffsets()[5], 32); + } +} diff --git a/test/java/org/apache/fop/fonts/truetype/GlyfTableTestCase.java b/test/java/org/apache/fop/fonts/truetype/GlyfTableTestCase.java index 204803a32..e794ab1a8 100644 --- a/test/java/org/apache/fop/fonts/truetype/GlyfTableTestCase.java +++ b/test/java/org/apache/fop/fonts/truetype/GlyfTableTestCase.java @@ -148,14 +148,15 @@ public class GlyfTableTestCase { private void setupSubsetReader(Map glyphs) throws IOException { TTFSubSetFile fontFile = new TTFSubSetFile(); - fontFile.readFont(originalFontReader, "Deja", glyphs); + String header = OFFontLoader.readHeader(subsetReader); + fontFile.readFont(originalFontReader, "Deja", header, glyphs); byte[] subsetFont = fontFile.getFontSubset(); InputStream intputStream = new ByteArrayInputStream(subsetFont); subsetReader = new FontFileReader(intputStream); } private void readLoca() throws IOException { - DirData loca = getTableData("loca"); + DirData loca = getTableData(OFTableName.LOCA.getName()); int numberOfGlyphs = (int) (loca.length - 4) / 4; glyphOffsets = new long[numberOfGlyphs]; subsetReader.seekSet(loca.offset); @@ -166,7 +167,7 @@ public class GlyfTableTestCase { } private int[] retrieveIndicesOfComposedGlyphs() throws IOException { - DirData glyf = getTableData("glyf"); + DirData glyf = getTableData(OFTableName.GLYF.getName()); int[] composedGlyphIndices = new int[glyphOffsets.length]; for (int i = 0; i < glyphOffsets.length; i++) { diff --git a/test/java/org/apache/fop/fonts/truetype/OTFFileTestCase.java b/test/java/org/apache/fop/fonts/truetype/OTFFileTestCase.java new file mode 100644 index 000000000..737c2e05e --- /dev/null +++ b/test/java/org/apache/fop/fonts/truetype/OTFFileTestCase.java @@ -0,0 +1,86 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.truetype; + +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStream; + +import org.junit.Before; +import org.junit.Test; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; + +public class OTFFileTestCase { + protected OTFFile sourceSansProBold; + protected FontFileReader sourceSansReader = null; + protected OTFFile alexBrush; + protected FontFileReader alexBrushReader = null; + + /** + * Initializes fonts used for the testing of reading OTF CFF + * @throws IOException + */ + @Before + public void setUp() throws Exception { + sourceSansProBold = new OTFFile(); + InputStream sourceSansStream = new FileInputStream("test/resources/fonts/otf/SourceSansProBold.otf"); + sourceSansReader = new FontFileReader(sourceSansStream); + String sourceSansHeader = OFFontLoader.readHeader(sourceSansReader); + sourceSansProBold.readFont(sourceSansReader, sourceSansHeader); + sourceSansStream.close(); + + InputStream alexBrushStream = new FileInputStream("test/resources/fonts/otf/AlexBrushRegular.otf"); + alexBrush = new OTFFile(); + alexBrushReader = new FontFileReader(alexBrushStream); + String carolynaHeader = OFFontLoader.readHeader(alexBrushReader); + alexBrush.readFont(alexBrushReader, carolynaHeader); + alexBrushStream.close(); + } + + /** + * Tests the font names being read from the file + */ + @Test + public void testFontNames() { + assertTrue(sourceSansProBold.getFamilyNames().contains("Source Sans Pro")); + assertTrue(alexBrush.getFamilyNames().contains("Alex Brush")); + } + + /** + * Tests the number of glyphs and a select number of widths from each font + */ + @Test + public void testGlyphNumberAndWidths() { + assertEquals(824, sourceSansProBold.numberOfGlyphs); + assertEquals(256, alexBrush.numberOfGlyphs); + + int[] gids = {32, 42, 44, 47}; + int[] sourceSansWidths = {516, 555, 572, 383}; + for (int i = 0;i < gids.length;i++) { + assertEquals(sourceSansWidths[i], sourceSansProBold.getWidths()[gids[i]]); + } + int[] carolynaWidths = {842, 822, 658, 784}; + for (int i = 0;i < gids.length;i++) { + assertEquals(carolynaWidths[i], alexBrush.getWidths()[gids[i]]); + } + } +} diff --git a/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java b/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java new file mode 100644 index 000000000..604cca3a8 --- /dev/null +++ b/test/java/org/apache/fop/fonts/truetype/OTFSubSetFileTestCase.java @@ -0,0 +1,148 @@ +/* + * 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. + */ + +/* $Id$ */ + +package org.apache.fop.fonts.truetype; + +import java.io.IOException; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import org.junit.Before; +import org.junit.Test; + +import org.apache.fontbox.cff.CFFDataInput; +import org.apache.fontbox.cff.CFFFont; +import org.apache.fontbox.cff.CFFParser; +import org.apache.fontbox.cff.IndexData; +import org.apache.fontbox.cff.Type2CharStringParser; + +import org.apache.fop.fonts.cff.CFFDataReader; +import org.apache.fop.fonts.cff.CFFDataReader.CFFIndexData; +import org.apache.fop.fonts.cff.CFFDataReader.DICTEntry; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertTrue; + +public class OTFSubSetFileTestCase extends OTFFileTestCase { + + CFFDataReader cffReaderSourceSans; + private OTFSubSetFile sourceSansSubset; + private byte[] sourceSansData; + CFFDataReader cffReaderHeitiStd; + + public OTFSubSetFileTestCase() throws IOException { + super(); + } + + /** + * Initialises the test by creating the font subset. A CFFDataReader is + * also created based on the subset data for use in the tests. + * @throws IOException + */ + @Before + public void setUp() throws Exception { + super.setUp(); + + Map glyphs = new HashMap(); + for (int i = 0; i < 256; i++) { + glyphs.put(i, i); + } + + sourceSansSubset = new OTFSubSetFile(); + String sourceSansHeader = OFFontLoader.readHeader(sourceSansReader); + sourceSansSubset.readFont(sourceSansReader, "SourceSansProBold", sourceSansHeader, glyphs); + sourceSansData = sourceSansSubset.getFontSubset(); + cffReaderSourceSans = new CFFDataReader(sourceSansData); + } + + /** + * Validates the CharString data against the original font + * @throws IOException + */ + @Test + public void testCharStringIndex() throws IOException { + assertEquals(256, cffReaderSourceSans.getCharStringIndex().getNumObjects()); + assertTrue(checkCorrectOffsets(cffReaderSourceSans.getCharStringIndex())); + validateCharStrings(cffReaderSourceSans); + } + + private boolean checkCorrectOffsets(CFFIndexData indexData) { + int last = 0; + for (int i = 0;i < indexData.getOffsets().length;i++) { + if (indexData.getOffsets()[i] < last) { + return false; + } + last = indexData.getOffsets()[i]; + } + return true; + } + + private void validateCharStrings(CFFDataReader cffReader) throws IOException { + CFFFont sourceSansOriginal = sourceSansProBold.fileFont; + Map origCharStringData = sourceSansOriginal.getCharStringsDict(); + IndexData origGlobalIndex = sourceSansOriginal.getGlobalSubrIndex(); + IndexData origLocalIndex = sourceSansOriginal.getLocalSubrIndex(); + + CFFDataInput globalSubrs = new CFFDataInput(cffReader.getGlobalIndexSubr().getByteData()); + CFFDataInput localSubrs = new CFFDataInput(cffReader.getLocalIndexSubr().getByteData()); + + IndexData globalIndexData = CFFParser.readIndexData(globalSubrs); + IndexData localIndexData = CFFParser.readIndexData(localSubrs); + + CFFIndexData charStrings = cffReader.getCharStringIndex(); + for (int i = 0;i < charStrings.getNumObjects();i++) { + byte[] charData = charStrings.getValue(i); + Type2CharStringParser parser = new Type2CharStringParser(); + + byte[] origCharData = origCharStringData.get(origCharStringData.keySet().toArray( + new String[0])[i]); + List origSeq = parser.parse(origCharData, origGlobalIndex, origLocalIndex); + + List subsetSeq = parser.parse(charData, globalIndexData, localIndexData); + + //Validates the subset glyph render routines against the originals + assertEquals(origSeq, subsetSeq); + } + } + + /** + * Validates the String index data and size + * @throws IOException + */ + @Test + public void testStringIndex() throws IOException { + assertEquals(164, cffReaderSourceSans.getStringIndex().getNumObjects()); + assertTrue(checkCorrectOffsets(cffReaderSourceSans.getStringIndex())); + assertEquals("Amacron", new String(cffReaderSourceSans.getStringIndex().getValue(5))); + assertEquals("Edotaccent", new String(cffReaderSourceSans.getStringIndex().getValue(32))); + assertEquals("uni0122", new String(cffReaderSourceSans.getStringIndex().getValue(45))); + } + + /** + * Validates the Top Dict data + * @throws IOException + */ + @Test + public void testTopDictData() throws IOException { + Map topDictEntries = cffReaderSourceSans.parseDictData( + cffReaderSourceSans.getTopDictIndex().getData()); + assertEquals(10, topDictEntries.size()); + } +} diff --git a/test/java/org/apache/fop/fonts/truetype/TTFFileTestCase.java b/test/java/org/apache/fop/fonts/truetype/TTFFileTestCase.java index e04347032..a390bef0f 100644 --- a/test/java/org/apache/fop/fonts/truetype/TTFFileTestCase.java +++ b/test/java/org/apache/fop/fonts/truetype/TTFFileTestCase.java @@ -26,7 +26,7 @@ import java.util.Map; import org.junit.Test; -import org.apache.fop.fonts.truetype.TTFFile.PostScriptVersion; +import org.apache.fop.fonts.truetype.OpenFont.PostScriptVersion; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; @@ -55,14 +55,16 @@ public class TTFFileTestCase { dejavuTTFFile = new TTFFile(); InputStream dejaStream = new FileInputStream("test/resources/fonts/ttf/DejaVuLGCSerif.ttf"); dejavuReader = new FontFileReader(dejaStream); - dejavuTTFFile.readFont(dejavuReader); + String dejavuHeader = OFFontLoader.readHeader(dejavuReader); + dejavuTTFFile.readFont(dejavuReader, dejavuHeader); dejaStream.close(); InputStream droidStream = new FileInputStream("test/resources/fonts/ttf/DroidSansMono.ttf"); droidmonoTTFFile = new TTFFile(); droidmonoReader = new FontFileReader(droidStream); - droidmonoTTFFile.readFont(droidmonoReader); + String droidmonoHeader = OFFontLoader.readHeader(droidmonoReader); + droidmonoTTFFile.readFont(droidmonoReader, droidmonoHeader); droidStream.close(); } @@ -93,8 +95,10 @@ public class TTFFileTestCase { @Test public void testCheckTTC() throws IOException { // DejaVu is not a TTC, thus this returns true - assertTrue(dejavuTTFFile.checkTTC("")); - assertTrue(droidmonoTTFFile.checkTTC("")); + String dejavuHeader = OFFontLoader.readHeader(dejavuReader); + assertTrue(dejavuTTFFile.checkTTC(dejavuHeader, "")); + String droidmonoHeader = OFFontLoader.readHeader(droidmonoReader); + assertTrue(droidmonoTTFFile.checkTTC(droidmonoHeader, "")); /* * Cannot reasonably test the rest of this method without an actual truetype collection * because all methods in FontFileReader are "final" and thus mocking isn't possible. diff --git a/test/java/org/apache/fop/fonts/truetype/TTFFontLoaderTestCase.java b/test/java/org/apache/fop/fonts/truetype/TTFFontLoaderTestCase.java index 063d8c781..f50b116ac 100644 --- a/test/java/org/apache/fop/fonts/truetype/TTFFontLoaderTestCase.java +++ b/test/java/org/apache/fop/fonts/truetype/TTFFontLoaderTestCase.java @@ -34,7 +34,7 @@ import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; /** - * Test case for {@link TTFFontLoader}. + * Test case for {@link OFFontLoader}. */ public class TTFFontLoaderTestCase { @@ -49,12 +49,12 @@ public class TTFFontLoaderTestCase { boolean embedded = false; boolean useKerning = true; - TTFFontLoader fontLoader = new TTFFontLoader(absoluteFilePath, fontName, embedded, + OFFontLoader fontLoader = new OFFontLoader(absoluteFilePath, fontName, embedded, EmbeddingMode.AUTO, EncodingMode.AUTO, useKerning, useComplexScriptFeatures, resourceResolver); assertTrue(fontLoader.getFont().hasKerningInfo()); useKerning = false; - fontLoader = new TTFFontLoader(absoluteFilePath, fontName, embedded, EmbeddingMode.AUTO, + fontLoader = new OFFontLoader(absoluteFilePath, fontName, embedded, EmbeddingMode.AUTO, EncodingMode.AUTO, useKerning, useComplexScriptFeatures, resourceResolver); assertFalse(fontLoader.getFont().hasKerningInfo()); } diff --git a/test/java/org/apache/fop/fonts/truetype/TTFSubSetFileTestCase.java b/test/java/org/apache/fop/fonts/truetype/TTFSubSetFileTestCase.java index 16bedad8d..ef0dff5d5 100644 --- a/test/java/org/apache/fop/fonts/truetype/TTFSubSetFileTestCase.java +++ b/test/java/org/apache/fop/fonts/truetype/TTFSubSetFileTestCase.java @@ -55,7 +55,8 @@ public class TTFSubSetFileTestCase extends TTFFileTestCase { for (int i = 0; i < 255; i++) { glyphs.put(i, i); } - ttfSubset.readFont(dejavuReader, "DejaVu", glyphs); + String header = OFFontLoader.readHeader(dejavuReader); + ttfSubset.readFont(dejavuReader, "DejaVu", header, glyphs); subset = ttfSubset.getFontSubset(); } /** @@ -68,7 +69,9 @@ public class TTFSubSetFileTestCase extends TTFFileTestCase { public void testReadFont3Args() throws IOException { ByteArrayInputStream byteArray = new ByteArrayInputStream(subset); - dejavuTTFFile.readFont(new FontFileReader(byteArray)); + FontFileReader reader = new FontFileReader(byteArray); + String header = OFFontLoader.readHeader(reader); + dejavuTTFFile.readFont(reader, header); // Test a couple arbitrary values assertEquals(dejavuTTFFile.convertTTFUnit2PDFUnit(-1576), dejavuTTFFile.getFontBBox()[0]); assertEquals(dejavuTTFFile.getFullName(), "DejaVu LGC Serif"); diff --git a/test/java/org/apache/fop/fonts/truetype/TTFTableNameTestCase.java b/test/java/org/apache/fop/fonts/truetype/TTFTableNameTestCase.java index b9066dc2d..ac5ab3ddc 100644 --- a/test/java/org/apache/fop/fonts/truetype/TTFTableNameTestCase.java +++ b/test/java/org/apache/fop/fonts/truetype/TTFTableNameTestCase.java @@ -37,37 +37,37 @@ public class TTFTableNameTestCase { */ @Test public void testGetName() throws IllegalAccessException { - assertEquals("tableDirectory", TTFTableName.TABLE_DIRECTORY.getName()); - assertEquals("EBDT", TTFTableName.EBDT.getName()); - assertEquals("EBLC", TTFTableName.EBLC.getName()); - assertEquals("EBSC", TTFTableName.EBSC.getName()); - assertEquals("FFTM", TTFTableName.FFTM.getName()); - assertEquals("GDEF", TTFTableName.GDEF.getName()); - assertEquals("GPOS", TTFTableName.GPOS.getName()); - assertEquals("GSUB", TTFTableName.GSUB.getName()); - assertEquals("LTSH", TTFTableName.LTSH.getName()); - assertEquals("OS/2", TTFTableName.OS2.getName()); - assertEquals("PCLT", TTFTableName.PCLT.getName()); - assertEquals("VDMX", TTFTableName.VDMX.getName()); - assertEquals("cmap", TTFTableName.CMAP.getName()); - assertEquals("cvt ", TTFTableName.CVT.getName()); - assertEquals("fpgm", TTFTableName.FPGM.getName()); - assertEquals("gasp", TTFTableName.GASP.getName()); - assertEquals("glyf", TTFTableName.GLYF.getName()); - assertEquals("hdmx", TTFTableName.HDMX.getName()); - assertEquals("head", TTFTableName.HEAD.getName()); - assertEquals("hhea", TTFTableName.HHEA.getName()); - assertEquals("hmtx", TTFTableName.HMTX.getName()); - assertEquals("kern", TTFTableName.KERN.getName()); - assertEquals("loca", TTFTableName.LOCA.getName()); - assertEquals("maxp", TTFTableName.MAXP.getName()); - assertEquals("name", TTFTableName.NAME.getName()); - assertEquals("post", TTFTableName.POST.getName()); - assertEquals("prep", TTFTableName.PREP.getName()); - assertEquals("vhea", TTFTableName.VHEA.getName()); - assertEquals("vmtx", TTFTableName.VMTX.getName()); + assertEquals("tableDirectory", OFTableName.TABLE_DIRECTORY.getName()); + assertEquals("EBDT", OFTableName.EBDT.getName()); + assertEquals("EBLC", OFTableName.EBLC.getName()); + assertEquals("EBSC", OFTableName.EBSC.getName()); + assertEquals("FFTM", OFTableName.FFTM.getName()); + assertEquals("GDEF", OFTableName.GDEF.getName()); + assertEquals("GPOS", OFTableName.GPOS.getName()); + assertEquals("GSUB", OFTableName.GSUB.getName()); + assertEquals("LTSH", OFTableName.LTSH.getName()); + assertEquals("OS/2", OFTableName.OS2.getName()); + assertEquals("PCLT", OFTableName.PCLT.getName()); + assertEquals("VDMX", OFTableName.VDMX.getName()); + assertEquals("cmap", OFTableName.CMAP.getName()); + assertEquals("cvt ", OFTableName.CVT.getName()); + assertEquals("fpgm", OFTableName.FPGM.getName()); + assertEquals("gasp", OFTableName.GASP.getName()); + assertEquals("glyf", OFTableName.GLYF.getName()); + assertEquals("hdmx", OFTableName.HDMX.getName()); + assertEquals("head", OFTableName.HEAD.getName()); + assertEquals("hhea", OFTableName.HHEA.getName()); + assertEquals("hmtx", OFTableName.HMTX.getName()); + assertEquals("kern", OFTableName.KERN.getName()); + assertEquals("loca", OFTableName.LOCA.getName()); + assertEquals("maxp", OFTableName.MAXP.getName()); + assertEquals("name", OFTableName.NAME.getName()); + assertEquals("post", OFTableName.POST.getName()); + assertEquals("prep", OFTableName.PREP.getName()); + assertEquals("vhea", OFTableName.VHEA.getName()); + assertEquals("vmtx", OFTableName.VMTX.getName()); // make sure it works with other table names - TTFTableName test = TTFTableName.getValue("test"); + OFTableName test = OFTableName.getValue("test"); assertEquals("test", test.getName()); } @@ -78,34 +78,34 @@ public class TTFTableNameTestCase { */ @Test public void testGetValue() throws IllegalAccessException { - assertEquals(TTFTableName.EBDT, TTFTableName.getValue("EBDT")); - assertEquals(TTFTableName.EBLC, TTFTableName.getValue("EBLC")); - assertEquals(TTFTableName.EBSC, TTFTableName.getValue("EBSC")); - assertEquals(TTFTableName.FFTM, TTFTableName.getValue("FFTM")); - assertEquals(TTFTableName.LTSH, TTFTableName.getValue("LTSH")); - assertEquals(TTFTableName.OS2, TTFTableName.getValue("OS/2")); - assertEquals(TTFTableName.PCLT, TTFTableName.getValue("PCLT")); - assertEquals(TTFTableName.VDMX, TTFTableName.getValue("VDMX")); - assertEquals(TTFTableName.CMAP, TTFTableName.getValue("cmap")); - assertEquals(TTFTableName.CVT, TTFTableName.getValue("cvt ")); - assertEquals(TTFTableName.FPGM, TTFTableName.getValue("fpgm")); - assertEquals(TTFTableName.GASP, TTFTableName.getValue("gasp")); - assertEquals(TTFTableName.GLYF, TTFTableName.getValue("glyf")); - assertEquals(TTFTableName.HDMX, TTFTableName.getValue("hdmx")); - assertEquals(TTFTableName.HEAD, TTFTableName.getValue("head")); - assertEquals(TTFTableName.HHEA, TTFTableName.getValue("hhea")); - assertEquals(TTFTableName.HMTX, TTFTableName.getValue("hmtx")); - assertEquals(TTFTableName.KERN, TTFTableName.getValue("kern")); - assertEquals(TTFTableName.LOCA, TTFTableName.getValue("loca")); - assertEquals(TTFTableName.MAXP, TTFTableName.getValue("maxp")); - assertEquals(TTFTableName.NAME, TTFTableName.getValue("name")); - assertEquals(TTFTableName.POST, TTFTableName.getValue("post")); - assertEquals(TTFTableName.PREP, TTFTableName.getValue("prep")); - assertEquals(TTFTableName.VHEA, TTFTableName.getValue("vhea")); - assertEquals(TTFTableName.VMTX, TTFTableName.getValue("vmtx")); + assertEquals(OFTableName.EBDT, OFTableName.getValue("EBDT")); + assertEquals(OFTableName.EBLC, OFTableName.getValue("EBLC")); + assertEquals(OFTableName.EBSC, OFTableName.getValue("EBSC")); + assertEquals(OFTableName.FFTM, OFTableName.getValue("FFTM")); + assertEquals(OFTableName.LTSH, OFTableName.getValue("LTSH")); + assertEquals(OFTableName.OS2, OFTableName.getValue("OS/2")); + assertEquals(OFTableName.PCLT, OFTableName.getValue("PCLT")); + assertEquals(OFTableName.VDMX, OFTableName.getValue("VDMX")); + assertEquals(OFTableName.CMAP, OFTableName.getValue("cmap")); + assertEquals(OFTableName.CVT, OFTableName.getValue("cvt ")); + assertEquals(OFTableName.FPGM, OFTableName.getValue("fpgm")); + assertEquals(OFTableName.GASP, OFTableName.getValue("gasp")); + assertEquals(OFTableName.GLYF, OFTableName.getValue("glyf")); + assertEquals(OFTableName.HDMX, OFTableName.getValue("hdmx")); + assertEquals(OFTableName.HEAD, OFTableName.getValue("head")); + assertEquals(OFTableName.HHEA, OFTableName.getValue("hhea")); + assertEquals(OFTableName.HMTX, OFTableName.getValue("hmtx")); + assertEquals(OFTableName.KERN, OFTableName.getValue("kern")); + assertEquals(OFTableName.LOCA, OFTableName.getValue("loca")); + assertEquals(OFTableName.MAXP, OFTableName.getValue("maxp")); + assertEquals(OFTableName.NAME, OFTableName.getValue("name")); + assertEquals(OFTableName.POST, OFTableName.getValue("post")); + assertEquals(OFTableName.PREP, OFTableName.getValue("prep")); + assertEquals(OFTableName.VHEA, OFTableName.getValue("vhea")); + assertEquals(OFTableName.VMTX, OFTableName.getValue("vmtx")); // Test that we can store a random table name and it will not fail or throw an error. - TTFTableName test = TTFTableName.getValue("random"); - assertTrue(test instanceof TTFTableName); + OFTableName test = OFTableName.getValue("random"); + assertTrue(test instanceof OFTableName); } /** @@ -115,10 +115,10 @@ public class TTFTableNameTestCase { */ @Test public void testHashCode() throws IllegalAccessException { - TTFTableName a = TTFTableName.getValue("testObject"); - TTFTableName b = TTFTableName.getValue("testObject"); + OFTableName a = OFTableName.getValue("testObject"); + OFTableName b = OFTableName.getValue("testObject"); assertTrue(a.hashCode() == b.hashCode()); - TTFTableName c = TTFTableName.getValue("fail"); + OFTableName c = OFTableName.getValue("fail"); assertFalse(a.hashCode() == c.hashCode()); } @@ -134,15 +134,15 @@ public class TTFTableNameTestCase { @Test public void testEquals() throws IllegalAccessException { // Reflexivity - TTFTableName a = TTFTableName.getValue("test"); + OFTableName a = OFTableName.getValue("test"); assertTrue(a.equals(a)); // Symmetry - TTFTableName b = TTFTableName.getValue("test"); + OFTableName b = OFTableName.getValue("test"); assertTrue(a.equals(b)); assertTrue(b.equals(a)); // Transitivity (tested with symmetry) // Consistency (test that a == b is true and that a == c fails) - TTFTableName c = TTFTableName.getValue("fail"); + OFTableName c = OFTableName.getValue("fail"); for (int i = 0; i < 100; i++) { assertTrue(a.equals(b)); assertFalse(a.equals(c)); diff --git a/test/resources/fonts/otf/AlexBrushRegular.otf b/test/resources/fonts/otf/AlexBrushRegular.otf new file mode 100644 index 0000000000000000000000000000000000000000..2d48ec13d3b95492091bf067e33f45198a351b29 GIT binary patch literal 39796 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

!JK6s4z3xL;ji=Z(96tOan-+Htr?F9v9o6qb5C zY9AIH>U!s0LjMf_e&m!~@z9Tgw2r&M_8o6McY&azXe@F(gKYi&wToAVV}Ry|?heni z!3#_Wj(&>XZTaZjNBHUYZ(RE1IDF#MdkuH6caN84G=sgsIHV^b#cDAg?%2iBeZ~Yn zB;|35OSAV11@K$j_UGkcl?tmzODGSwpSpP!zI^>mdq3u|Y7{0SYHUMZ8GWspCI$5T zC&3O|mK@Lp$JjweP3P72(DAo#j70n#8A@c?g2p=F9#+(!(1h0~t#>ZQ!jqm7X1+wE z2s3&4TsS$Me;@_jA1LaV<3J79lfc(UX;xccnM)0<98^nfXJ3EMp}v-ZTDb4yuWSE_ zT^*5?^%8^py4)00s1YdmxFn~rIHeq}%*jw5z$zs=os^*RJR(dYQ_B?u`2#>gaCG`I1#jf$!O@1>q@i1qTl13rY+B7S}Eldxe-%sU_t^shr0x z+6!}bijylb^(hCK^c&|5T3Asn(twE18j1J$xb^7nv zm^W}>K@$-bn!TZmz7V8;0Gpp#0s6DU5o5X##%gGDb_%wZSbnE_qI4*Sq-1g%w!^`-#Qj z$$Qt76~lWbQH2%NBqkM<%SnJSQ$(=GXgf~q+_-OZ>bCtGO46wcSV37dF3j&SIb1}u zC(>iF0BA?A(JApNg^DtvuExV7@8W%Dx`tYNj6luy>0qa~nyMwJATTmvjV_bTq%c$f zOqdesI67FDE7WPQFKFb{yS^r{DWSqM1oY%a+WubR>D;d2Af448Egl_{H^=-%`tve+ zlx53aZVFGt!f`LF<>|yW3Aa*&N*(Gtt95+i6!X5+WjJa6+yYzfA2<3iZffez4ZB}X zn(<1~Qtn%d2PT+GEF8J?{8t|yyZ`l9#Lai^j(ph#x7@nnxsDBXs3dhnyU<(8Lkr7_ zGK%qonVFI-Y!|=jw1sFfXxvp;l}ePaBR1&T@-JXVkNUcXh@r0f?q0O1vc5QgH|8e0 zwqh$6m**@b7UnKLuz438est#MSx=#1#>Xq^*0nEB7j;buJF2u_7 z^`<0Zn>p2ZP)Dz)+u|DfoZW3`Z+UBO0O$JhZCSeTu@wgA?Y0|$FF z-H{jM;V~zQgB_Ivn8TsdJBS`rSA9o6+;P}hpKIYuRNKKlXntjS@g96- zI4WUY`sVfe{i@>1gOYp|dPiP~)QXuv@LL$S`@8 zS_&K_Uk=ADUbAUy%AOh7se%%K5*tk&!T#>6t>@}bz%_?#t-wBB)1{e+c3yX1;-y2>*1}s!mexRkZ+`86z{oo^4!%^@YQ>FJ3qiqv{e?n!0`uz zNQmw$4KNcQ9)AF*2*B|NJK_A}_=Cav@c2XDrL!O0{>xYN#CxB-djYNqcx`sfVpK~j zRb|p*qG0*%XI6(FOL{G58$SoulE6a>RhTu7hJd%thj*O2{RKUhM!x#;?yYx5RZJr= zw-qvDei=VHQ3sArykiGL^|$4Mv32!~8_bBg?5OQtHgI4a1`e#^|KY$IHC7ac8tIPu z-oVGLbY@*?fAm1lKTgoI2gW!8a^p~@gP)pf?5|GNME;As1IabKw4t31btuN8OZr2)XKAe`PoPppd)r( z#|B#Jn%pW^m5Y!%ReE6UB=u_Cq|^i1AuN@aCC?lFCXC_to9`TZ{~G)hbLFDtn|7>A zTUjh}#3gp+)K%Ev+H4L`U5mkZi3nMxyh0&_#dXT&&exg0Z2l#Sl`KtGr|5HaMfOsk zy*@5r_c`jZ_EY@i+eB0!Gdit#EOa)e`88&YGo2l?^;PiP3bg;lbIy)MH8XB9Bjy1~ z@Yx#znmc&Eo?hByIaSe2&*+P;>5ZX(?hJLZ{4N_%ftq+tQWvPZ1~~TE6h^rW0BFFk z5*La2at@ZVs_w}1M0nE3#^y=`?Ae-NO~k^J=M-#ML2O9KU%vv~(vUpN!PDO=T}!Q| zw%Jqt#c*NWA@KNeadh0})`AX`jFd$S55<_Cn5Z9n zn&t7y$6IZ*)yQq-IwGbR80D&!SYDQtpGNQ{*}Oej3F*&1366d(3lrftmdqDPVIX#N zCe+vd;brT4H&6!p_XM;G(3;y}QwsO?ysp zaY;jyvI!eFi3XCrXj?pLpx}_R-smzsdi}^VJAg3x96NwCF z5h1XayTt)m*eGl3K?mK(TTbI0myeye&R8dtS2biXU&`lP5JPHq{Q|pupG_`z3?ixI0!IoE-z6rm)Xl3d) zaBcxiXJVVreCHkdsS%nn`qjnTuuUZ~39(8ksa6nKyn=(pyj^=TvWj@y_pDpDY!SS6 zb3vXK)3x^9y+FMC&AE>UZ@`y+Xummtb{+KXIKeW9EbQ9;+_iN+WOh&|jb(CW?XJ*oS?+_9o^b&f<7-PV_ zTb69~-mKm%$?BGExmRpsj4_0kP(lkSq>y^jL-OWi#2LPmyJa|Ux!=8at-J2J(E?)4 zXf&RA<|%vs|G&MzAp+C8NOO}didaD2j_G7dVI9e>WXdyb%z_s%^j+Dq)Fds2M;8+LKt90rd{c30Y;*m|1kR}c=&;L_-Ba`LR z+f9(lQ(46pLTahe7RV|T8w*}pwRrQQb&FOZwq7%=AwI4c+w3DO{8}Rqn>(*`^?Y*9 z@?Ebhp3|1uIX>_^c|*!(Xie^x7Sd(|^`Zf(ufL8P^$GY=;;1q z;9uZ4I(*DxFkHEM2mrumWSAm#UnB9?!+t z@1&!{7O{9voH+mXhwo5~A3hlc`EGhI8n56bdj?V-fNuHO$GAU#uxmITY&Sg*{c;1p z`No{~2ulDrzDrI^jaKtnYoq_ z>{j!!t(Ae^lRZCPrr0DHrjCC#@lJDlFz9t47Q5dVYaGxtVirri0Wyt_dUHKHovL|& z8{^(M%IoE2#8u5qclV7YEQQh_bBVvX?aX;ZR4&3Spdc~$@^t~M+qG&nWDEHG=#5un z$#G48O2o_(bt%ua9JIP%y)yFt?_W@}k!dAR6~ueAsw% zZQh#v$KIgX-`dZ&QM}VrG-_7aaM5P|MGjY!1kqT}G zQ+lIoGb^BzJNVfDs!fxsRAQ1jzt$>q5lm^c!(bdBjboh#FJ_@OQ0t7;8Z7-j>OC%m z2B-zp@%4Bsp8N(XY81SN50Gy!#_y#cN_}bB=7nf_zdm+3Ox=K7`WUt9-IO>^5u-Rn zZY}zYI2cHDY7GgFKB*8Bh@2rQsr0Dbx(1Wm3@^kIHu>G`fXXQ~5``9i%{DgA$hQay zWd*M=VYJ>`$SK9-3X4lkYV0~N0kk(A96LvJkB&^dbqX1qXlmB88|z$x+|}#pw7JCV zbjsd&Iqc2;itgS%e@{Qr+Zh`OjUqdOiQr@;)DR7k={e#cwV9flOnphc#&X!|E%FOE z2;Irbf`S52qvUMbRa1zSaGTmKq$O$%*j)X`GTr`gur1OVZ3dY$@&m3{E9An2uUD#M zOC4&T&*Shp2)oDZ^|70Hf#R*`P@wnlVQBjIs-skIZ*tro-_9~wjAk?2U2d0Xh%))M zHB0C_G;S?est~6#(Kp|6brqZ2s|K)8o3E>v{P^S4ZCuN%=P=86XvEy@InX`S+0_pc z2D8NozDJO?sPu$duZI7SM_*dGcNezReJR#J`u6vqI{Rt=*Z{l`dOiITYr!LXw<#6K z++|sN%eJF$b^d2yt`YqS1)uEP9JKIxbTHu)|4E3xOz&=sZ#h7f@sgM0=^z|!qZUS} zfu7_zgX&^6m_=T`6t(|1H`?M!H(Esp7U+x|I7nW3f7>HPt4p?*lclUub9lNY0J z9Up|DrLBMP{KU`hra)Koh(G4^8*Io{FY9(=+P#m1@9#Kz>0RW^`NS!@?Fl1Y`rq;R zGvIzGM9+QEeaPt5_>@+uwn(~R$y}P5w|4tWtLbEfi>5y;2~%I3P8Rl2&p=|oA6!HImU!rNGBpR@(#NOO;j8a&$NAO5IzwrX~6w6{U+sqeGBV_2Las@Ge#q#VTtX$I2WFjF7Ff#HMGITW5YGAwh z4T6g7>g}rteO}3eHwmN7)7m_WG>^EW3B`|7Sh;E6yxGL&?YVo(iY@+7fA=Y*>zJ<{ zqDM-rSS(e`l*EpuMcD>iSfHqpv6;_E+?;^f+t}Gm^c?8uYl)2>8XG*+S(9C}i<`~K z67E*!AP5AAwRzGq4Hroy<5g^?Wp{)-5^nd# z28g~`dwWM8lKw#ee%A~tcbJ(&-3MW&yj`1D8gMyRQ6N?0d)UlSiJQ}N=!ZYL+6b%7 z-k9hPOj@m=28=7!6_w>Bl}JTVwHRm*^?paVp{uEntc77qD_0Wf**XwLKZvJ~*SAvo zRy!}_;l6n0IOHGhqPVOmUZWDJluF1VL{$w^jYh9m6Xo)4>lWUFSaE-kH{x>mc#V=q zwGyqdNgZysx4C=bC^0tP7IRx6jSxYtv^p3sJ(T=$dkM8Uh5Cl7Wr0h}WMmsJ;wD1k zNbQ*F(#owuEPD+vcL7<#FR3gkKnil}3d`7g19g2SB4X_D_P6Z3CzHQNQBcC(>Z|PT z?rIuqCt8O*eI0DC#v}I-eyPw=i`7Z>VB`u6caM%8LR$XL0>>dcb=`*SvLdWjX@{hU zV`O0T@+h+Z%%M;xW;g3J2J%(<1j|q(FX8V+c5*qKYUly24JuOY&^aK_YH#!Q6P_-2 zi#rt7do?z-Q)v+yxJdfD>ZbVJ&{kPX(ezH;Y3e&(@-jTVOxc|hf0X)wCDRwzZ`7~R z?=$cXNJmd&*ul1{tx_u?wJMEjJxIR9bsPy_A`lCZb!m`t1JMmA5uj^Clxhtm6nTDS zw~eSRsLQX*N2;?Vc~$JyouZ=_qR%|+9*rH0_4jo21B1lkIEU&$9we6&yR&!Y6>%dt!&1hspNwaJ$=OHjLW7Za_YA_S>y&u>Ga~EN!R8AQZiadW;1#l6-W> zLcCzFLV+w;v`=1+_fB;5MI$_%C*$!6aHqeNs#0jx6DX(x!9v&86>F|%7i{Nco63+v zlb7FuwVY_8rhG@j;S4{;wyI}q7 zCB%~T+l$KNI*)gx^L?cA17E+9?b8dqLKw~<6A9@m&W@tzi(U|JGe{A!p|jSFje1WE zUOtO__WtPk3HG7F=6#ScpYDi=xzvZe3~Js%YHKHRB)*Xnvi#~^rHcs4rA7q?NqLQl zv`H*=hALyeaA)}zWNmR_8ORaR%0;35P4*U$uQ>hQaIgjOh3#$=8x#{l-tN5lD~JS( zq%c?S@%Q(fL3+>lJB@6II4Izi?0jlBvG+yZRz6#4RW>LIX06iY(AY3#w{+~BH-rlLHM;=tr{#b^E&P_;W*nvE0l>b~;0x4y=73 zIB<~c?~Jx}4Dq_5H%z>Ys{@)|=J_u`e0bE|zdwA@ z(Q9o1@7hE|uP1=SLOq^w%xy`vYBeSerb}CI$dQzDIJJUOS#AwIJyV_|EaUKNg+=n6 zYN;UeqQ0kM3%gpCFUca9*Cbi0f@*fYy9(@&a(}D34>MbhW(O&^uV_fEwaWv5v9WZ! zMu9Qm8nt#eu}5m!b~O^|_srqm04X%Z=ubKPAj@vIy6mJc;{Q2FEkyj(a}Fx`6#JMs zRv}e^Ji{n6NeEk6s=30rXDge|kkZT=`Y#0ce$iGn`%B34rvLm1_l6D**W2sfpAvt9 z(zD#YViU(Iw9VqVWR2h#at!##iNImUKr6dl7%X!VR(_?aAd$sWo{*>dRSsblyF#&# zzm4E;Q|zr^=QdT2Nr*gYQC)cjhg+K`*t(Za&#cWZuFlq0Xh9^XMN}rU){Gg_&L0l; zcaou~f4}#n@14dWZ>YI@zwa1W#X0d8&!dUV_FAejzJ(=}f-~#3ZIhXE%eX1lf^oB) zFA~c@Q>+)EuA`_gVOnNd-a=goyPwrTHVg6i1N44w{Muyts{Qb9`>A=8DJ-g%F8CUc z${NAwZSgo7h#vW%cEqwCy_MEN9=>nez4x&n8Crg=h~V=ToN~63kLRIQHS z_s&lJ5ZBctHewH>zCTzXJ2en08{b_XnzYj-xvvk4l4sFzv2Cb^)%|`8QC=3BQK-lkY6X3%2L)$ls2f zide5-mA`oL;w8li_u+p*31FG91b;5EWKe6gYD}Z^*)-&^rGI3YU9FR&mV`mhatO_# z8@N>P)|6Zk^X*T$N-s|si+ErxYD(P1=7vbnNf^Kkh3Rk4tN;I*wO62J9&U@6D3$OF z@@_W@8QO?aPw`-m%!}W_M?a-^Jc_5oTYrJKp2M4ef*Y(e68qZAB3ut*QK^mnXyV~i zSv2I~;#7XyS@`@vCingFOP1DB6a|A{<1CF)gHNEAaAW)Ts4OTBiNS{kE44P|e;k@6 z_0whCZQqG1HHo(PN}??$$S@$^O6;-_c9|Q$lVyY~je$_w_@0X3r#PIhNo`S+R<%!> zXpXT)g-MGh_J0iaFQsn6X%|PU6TU?4DHP5+)Y#EaKr}`gyyc*?W0O$WKFokiIJg}7KaDPeU-PZPK{TxnZ4OT z&Vaw!+tx|Mnp@hMyAc)j){_71OTa69+c?~uu%5C_7jbCxF!hY*K8Q!D*ZJt=59=Sq z55NO9d6(gexhq1S;{Sn9UNDQsCyh;BFgaYX#3yGz2+uF|^5lIs-nzlJpW?|W?f3=Q zPEfjkKdxZ@h36J>O%Mv1bX&^V)sx3r0Q)^eDOe)t8~HnNk!niQ+(qCD7}d)UVtaMpq=>z6;*YJZqMYVrLc*lIFt9>NaVGbMz~(YtWLC3 z4YX6W8Tui(@v%C%@n_M*!QOZPT|)_-_;IpnPB|anmEbDZFbx~;BWL{uEY@eD=_OSy~b%s=h zzFMqgFV(NnZXuTFx9EyA;6%Ymg()O-V0w?i*hXG8YgQ{?1X9T?<sZ(2UH<-l{Ij-eJtFL zBv1_owgr^%5Y^CX2#r=)QHXur0gyR_0-)LSI+N z9`S<8cO>fdyMvh5rjn9sl~~Qzo`8I=&23Kv9h_FSMQ72Pz}9kjU6T!(*z^cB44$fv zlpBBcvzjZ~OT&ao3*9=V(Zh7!s%Vgq4HBDJ#4h4g?i3P|qC8a&mb=5|-AJzSWCuzD z%}uf4_S2r$&{*suLcN?8aM~LIIHV@&`Duecx19@iA#b%G`SC0kX%ZFf;_u5ZA|-Mq z#L*B5fDe^$hxBH%*czC(^z>cN?A(A{0+L)$E>`^w1jo<8v)Hgd4B^Dwyv^t;TwFR{;l4}MSH zJSb&xOY>!b+o*JeDoIXA+!SNO^wS>dme!6Dhj`t5zX%=>iH)Hw>^0S~a;xP|U5W&My`h+KN1D4_AI; zIc+}eJJ<0}jGA(}=8_h|i;@Q9?|qj(yvU~hLXQ`4sW}AX&CTo|sO2XvnTf;30g-gA zmX|39?vfP)cT2C)X&=!Xep!vsk1OeA_tGhBzFA-s63^zXSTv7KXHts=pKm07S@Ha9 z3rgYl%^&0@QsHp{C1ai7j_2$rhIVfat;N=C<>us&yLWT9u4S(YZQY+k>>e8Dp2SX! zhxYF$hlWDqCn1bcML)y6aTbK#sW+yx92%*akCl~)$}32dOl%Nf5|A}llltm9y#!mc zws!AYaz#$@w)O1gaGa&Rx@>=FFDTXZiHt($HWp^BsRGN zsq@RjQ5Z$wR@KWv?_()%$O-Zg>f3lX>-Y8k*Dm1?-Mp_0HG6_lh|L@H8Wo&10c77A zHORMTty3N@dN)3eTKLaR)JE)3XTj2)Ia}A)k#F)=?^($%h?NdWK!8$_+AVK{oZITB zx9qGVM8$>5d`uuTn#82UrEXL=>aEJ4x(5m9lujvD!LO(mo5eN}X%pM!4rPNhq-fP3 zg5a?#H)aDV1ppVwI?JZ8+=}QL!fH461GVrpb%%{KL}ZbQpuoj*JQzZDx~l^%?D3<4 zeh=|+%i+!|aQn{0LR3DrMDjf^m@(KB|7-L}AM?{H^p)(_o?S>(8#q30w=gPcm3Isn z`fNR3WHitOdF>W{sK`w?tII9L*e1Ygt|iZ$ztnjdyLNo_OXOS+Yx}xl`c45MH!0Op zkcB`R!-_ddJSBm$ro5(_s0!J;X>;w?Oz*DE%av8&AzQ1F>;2Ex)685?>h+}SleaxB#1gl->hD*PhcpQv*m zPyQZ9y5i}5%s>^osBr0$WyG>2ONtg9N3V2Wyl|d4fALb+m0M@J@Cd6#;4WIVs%-5F zV%h4V)vMWD2j4FxWZr-}g0=QL17qZ|aBDd7Jq{0Dm2hi0!YnJ>oFgj2N(2C?iXA)t zHu=u+qwR;WNQ0!tK(^ruU7baf*f|XS>adJR6N=cVivnBVS)2g>T3QkL~gQcJdFdEMl9gas?-{h zfbCs67o>LR)MkO*Ye*;Tyzo`A~f;_yJO1rb{;9FH({OJ0dw=5PyC){(qIK zpfO6AfG*sks>TiXqv^XeR7rJHhPxHwm|uO(`T+&w3QR_`a`#m4#dtDT*lBDqyUBnp z?2Uwx<|cQ@$8J>GMRf_X8{w9VY_*tNmXL8)$bcc8i&W%_AWp~()jH(9SZC+iUP4!E z;F)<=xm9KX9g58bIjg1?XP}L24TOU35MnSU<`r|kVu326j!y`M0)TUw-3}jYW9CE~ z8{7`)6tpVxMI%d6Dk$L&D6cEbWv@C~OikI}?+W)2LoH1`<`E>lgx<`J z&xA1jdaA)>y(xuCQc+uyy$RB=x!cOi5G^PO zfTm(qyTE?}kVG36=pFp{2zlh=_IK=X^kq_R{5nX(AP&lokK8h?yF}Is?y3d!qxTW_ z&`)f7ESFtt;#&knrNb)@!8{9GiXiefkX06mH_F~W{Mnb(OybHv-uwH-50G>ZJrqr* z*@M*ZU<&m`{1p~xI;{|G5WD#rqDZ-E=YkjBczNY>8=gc~-B5MK3rE@gvJP0?#yCZuU0ArgV_j zwf+OR8R(FS3qux4<1M=?dr9wAA_CW7h_pb`o+89 zui5Zd!tB2;0eSJ9N8bkV5a_xzQV@16mHuzaE@o!Z2z77|T7Xg=RPGTYbd2-C?&@VR zrP-RN^z=O@j-jA_yB?v@G<^=Q-iRsdY6P-A^#|7u8!dkFgcV*EggO5g*J#4G07L-l zDmU3PNd(vt-^7xd1ig4|L=*^&#2h|=QSMokS)+lM7Aa8HB{n)dCYzrK+dN>QA4 zf_})5>Q?o**;Mi>qYSIrtCp=NJx$)G#-@+GLoTZwxwWCL zM5EkA_8#p%)IAc3`9lp}#Ay5g8iuk8+{V1*FD~!J)9Kf5{XjhfKP@rBJMo@`v!0S( zrKX(1soYU;%!9%HG4QIre9K@@OJ7H+iRczItLjlS9l%J-0bz5MH^@71FG|_suP(wl z=;8BtGjBkRGXLa)?EBBM`|%O#mz5~O{MS$(T95z0{q0^fj>H!|4*P!2{XDT_Z(_%a z`*F$}e|-*0-=$|=K{+TjFR?8Lw*BiGY5{q0G7K7~AvEAV4*tDi*MsB$=9`rYT?ok8xePvT8f`g$C+j$d(qn~T#Z<#`;R zd{iDek00Q@4-X6VKmz1>_!>Mfl579l^Fo(E2*6_qnfJF0wYD^Roydmqfl3DkDP0@L zQEZ}MX;(=n&o2jSS!Q9`mV(7OVwpzm(gAX?5&x3=>s;JK1=r)v_{k@5`n5}!agWWK z2)l#Wxf@m8#&<*LXFp0n08;~(_XzJC?*K332+BMxeF0~FCVd#E*HV971jo4g1pfHX ziSPj67<&Q7=r^GXg-K~sLtG$ePcRvQs!AsG2Z`S<`PX>zB79Rk`#hQf1Ewx6c@t-b zitq;$LA-8W@<%<5`%|a|^zyIq$=F@HuO$Z2d_An0v7CzC*^`l0Qig`3+)KevLSVY4 zj()^4`BA)oG_cPBnyE>$@?t(O@!5O&k-MV@hr7_l97ZWzfnca=vJiHZ2z; z1~K2j!?H?rYCfq4P9$I=J${2RLYP|pMmx50&R!iC(7m%@o6^m<8SM22H&In2s?(`q zU7@o$AXVrkTKiHh6UR&^6W<7?cCP zIwuF)x^U-HPm%h=g6^^a;^9=bbtR>~e3fGuTTsSUW=#-7c8r zLF|S(wmepJVr(KZdXzXe78@I5mkU@`YOY)exIZZ5RfBNyizH>Bdg(f+C%^t8wSS~D z7{SJxDz}jI(WR{Xf<2|Xs*tkHJA}Dd7AMdbZRmhRbg-kfr8|N&_4PJ%W6_985=^Lu z%679A^-{f!m97-!=DjuxoJr=kVd~W=%u1t{ zCR5~HQD)7y^4FKLISvU(qby&b5T3@IW|!UoF$Ary9x|d5wFA(wF;};@zvGk4)(g?t zEjx<1m8v_iFVr0ghh&o$IO?e&mB!16j!_?mC`I_a{miU?#a~JcFD3uV)vl<2)=*{G zP`_7iZ)#}rG#$~O(|b(R!~V=G&Tgj?79rckxw;klXTdtRQ*0=IzCIVTLhom@SK`Io z_PqUvk!X9UuNJK+=alhaHLzVQmB7;WJyhPLJg6bzOT<;uDtQ&MxeWE`_;Xz=2e!;& z`u_Fb4KZ1`&)@@ZNsqqM;4+R`4_U`7SDalg`1m??kMPT7WDG3e8|FGN=?rsjreDYgywX&>;y)v+|H=BTimNbWjKFsSe+ubB{`?pp{ zgUO3|-CC7{gsloUs75s)1Qx7E%^n3Q^%Mp;WJYC*OGu{BRiiz^oCAhjl;UL+6}&k~oZIDB@wU)1Xk znjN4NbTxwKJ$*Pn6_i(}%Wp2W0>2iUs!(bL!4sT2*$+(rK_ zRkjLW&Rt&#_Aqn66bRm?RJuZ`&*IE^v&ZYw zTR@)PdgQJ5hOb2*!EgSHzV9I%@XrVw_-QnL&l@X1b$d(l{M~o>C6xK@(>U{)xcbIt z^KsA5_%+G|KGUJ1vAo!xgwGTLCyD7FI8EP%OKAKbQ^YbQJH0Y7A53%t=@cOj$=bdM zQ;)@3c^R@%Du0wY9`{hMLG_3?@Lk)=H*X?L0B|%#RrXhKrnt`Ok^8X5w2uC!L&KzO zYJR91f*{OsJvtod9Y2iIU1KbnMxqcAQh`jQ5LTCFGQ}^VU3N!}wiu!I9TcL}MoRq0 z3*3)l)JxGbkPbllsr7wKG0cU&WGNNpC3*RXozF9Ku+lP>w2I{R3%YgoGI{32oYXzl z75lQ-W$v1=h) zpAp*JO8-)raaZr)4sfXzJx6uhEQ66I^r_S=>Mzt7RrML>b*iOS(#B7P@QKktHd$-@x!B_SHa|qqAeV2M zzy3iw2~nlB9-R0hcFKKd)>o0z)vZ3lAI)C}jCP3Pu&Cd{)K9G$ab|=w#ylUN7XM)#sH=+M zVmuZ{+*HonIP-Ui#QnAzXU4bV=?_yqx4|sbSshx6Q*Xq->PU{ykN;x>9*IBfrOq`Z ze;64fAe$Pvc># zlcnPn=yNc;>z4I&mK`n1$ux+>dKqR!bxw!gj%``Kds|6y3A!0QF?QIPIgeV!I~dB~p23;F#N%daoYjs_eDw)#Kkt(IPG#W(DT>tkMD{mkE1fKX<1pViUNkeusjALBtab7cY`#7~y4C_?tZ>eX2 zAkX}RuE43{u}@~V zY+AXxYWsTPS@ixV>GvKxM0uP?!pEay?&i#HUr(^#^&()`sFgSzHc_pJWZs~pIB~mT z(al|(cc5|EhbvIJ{s;@)@HNibM*gf)S&f1#ZwNua3v90w)a&t2SW>M5WNA8;8Eg_k z<#AWHwPj&&p1RbHBA3y|pXF3?+22pQ4ttDF1g5T#fK(Ya>fTiI4-{Q1b9{{sZf;t) zS6igvsSxUK^kosAO~2GgJ&*_xQY>#GMi~D~JeOtGsEkkxV$ZJUmXKD3)Fj3xYjcpB zaI+HFhiYDlxJo5JB*p6LTDHinfMPO6tC=vG!0l)NL5$Yw1ai6^^!1L2zYFTr_%@*9 zp_ayvP;pg_ihlt&81-;mF4{4BE!Ty*O|+ zoUl@(CyH>`kj(uY*3a5_+wFBNEW#h89-`TkZNLT-t4TlJ=^F|$DzHdhDxzALyKmj< zd!Ut1Oco_$!w#l;BY+e^nh^+)x8_}d&8mc3w>Z8_2kY`*xxc~M`$l42egoF!%(SGR zsXr2{YDHopnW!gq{W{c>nw~_@reIBZ1^@U*w5Ff=)iXFVlTJSePx^mz5%8!PT#ETT z9EBdFM&{$U}8K0rcdL=q;mKbOM}ejtQ`;t(pL@ znqy)O&P++7OR4(D@mn&@z8_JF)y*7P22R%H35C%J{Kl`-cMRt7j&$PSccYG9j7yI* z?epPC_4DCK56_1q)z60`&6nQnxj8WxeV0z+QPU?ypVEuxm!k9+v}rCnX_FQ5;u}9k z<0~&R1K^eI2Cr=Pd-$rGmA5~HoI&5Z$ow5d&Oc^DakiVw=A!@X1lR3A0*g((9Hm^H zniip_|sIh z9pAJMgsy*G`5JnWx`(>|=onFgpZbqFoG#R}m_OTa&~#G=;!_jF9;6nYxzsp#B-Cka zxFzkbR^;v3zIdO$N+$&vcjm3~4-QuXxtO=^w%~gf7cE4?u}o8E)aciu)O`t!`paP| za3Fjd=KUEIFChbG#+KvE&DUux3#Aq&_E-?69H8gm!3Y^221)lVLUZw!bu_Y&)K%=N ze=`@Ij|NO$v&)3&r~W_cy)h4$@(m^wxADC<9%cdg$|-S4)CtrVaqj~U-+V+$PeHEN zWm8xdrUjWYpei)^MWs)Gh7pQ8uoY$r6n_A8{?%YtClsh@UR>!U1KS+=_DzV~5Uy>& z03l{Ekge3$AV<(1fw=Q~)cx&M-2Tp?c4em-S~RDXdYX$f3r?b4zrerRlQ5IdP&RYB zlH-5tNr}(bv5KjCq0Pyu`w-wd>7<3rWhw%U$JIMt+wesGidn|fXX;O4)U@w(_2jN@ zmTakZ9=4lC>upA;2SuKu7{EnZ`XQBp0O!?+S%+`3w*brIQhXdHK0i|ZtWRopP^&*f z*FDY^ksDqt*`enmpfWIOiRdHlZMG6??JRe8s=%aIII+gI<3=Nx*E>f8J)!8!+BM#=jWCq*%O!1zLKL zF$izoK@Ywrx2jwwx5-Qzzt z*J$6Smi5Rm{kaIgP~R3u+LGgGcUQKh(t$K8o7zf0My*Pvs$edYN?%N)meFN&0bP`u zPTf}-v<9gY`;)1>wv_nRIMg{Yz>*Krki}WW(uzG#wdY|wcJQ`sfkvWM>f}g*#cmyF zcZ3LgFk}s5=Clg>Mfvun^gTeBNua(Aq{TFJ0xyI>(a=QdJKSU8qr=o4nM2>S4Up;E=w<#J-Tvfw zar|f2q4I{pOE~@FO;s1_4*2Yd)m>}TV;V(0Pe=-RYA&BWzrW^P0&?Q2e~v>=JnUB$ za)m;Tgj4|p(Ts&0z2LKZ&V=FznATfSMKZJ#?jv%N+B~FrB4&sHS z)F0Glj4GoayqQ0rewO6Pj3TH$p$zH+C%@I1-Xd(Bz4?3TnYu!ZO1bhK^$hhA`n>MWz0GdsXX?NX-{)PI8)yqt}1d#6JSCZ#Xd1%VK zDV!;SDfLrYrgTghoAQ3jl$6aWJ5#Dt)G3yfw^DvixpBvoJ7(VT;vGY&vr`wPzL{E; zs!X+{M$;;GxNF5- zS$7rR#k5_DLx-q>4%FP~1zmWcI`cKnQfQLUc z{psn?148_b=}V>;Os|`+oL)cOJl!+BW%{A%SEv6t{kIuYW)L&(oAL0BXJ))K08Gp{4I`giX z88h#mdC$xTWgU^mNHj4F_ z-QjN}ODrslLT;2}d$$&?SVeBxoV`A8HL~4N)jG!h>EuVB^$}y?QRlEOq!0gwM@4Rd z0V+yDRvu5e7iS=_+PwD>pun&zY&D)b!X@;`8?}he>C`*1{X_2NA+j$Ljku$As?3UN zPF`^pfg9ieAW2DbL(0A%oXXl9%*S_fJ4mCL&pzOw* zkL-93sn{+q6@xff$^n!BBA`+Zr5uIgIBj;TJS6673J((QOZS$V+s3Gh9#`hJ>k|LgDB=TuzA&52=~e5Ye4oaA@eAq0`|` zfW(O$x7w^&WXxUf!IQv=2Z5l>u&h$@uTTy{7u?PBkRcYC^zUHIsCjnKIxI;Z)?rVWt_s5m_<{v6BZGdKF!J%aY)7NW2< zE3n#u*m81AIT-yn`p(kTkCBh9-n2mWJW`;E@{eF6!-;2cs5#c*?n5j_Ag*WtDX1pJ z)zzG$8l-A(fw&kejXJ={rjdbu>O9nvY*_q>=H$JNK1{UvWyM&aTQP~ zYAu>T&Be%lIO7GBnxSU}a7Ih?z@anb_}OTup54G{kPub+(vrM2g&TQ0Re%bdv?nrH z!G9CKl|rE(--@SWb#iCuRWv(T)6dw3&$-#T1)>S@g^!|C*3B$<$o`f_-l$;Nxi#i0 zj9x-deG)F|PLdv{dD3QONYgkACcYbi{65HrHThSd_fF(mDppl&euONlE3Pbq64FJY zat;uZWj+njp!XRd zIgZ@HOY9a)i>sCJbT@T%bs~%)m+RzW8`r!+Ke&Q4tSB~^z&j3mc<+Z)j>|1=#LVBJ0a|hPr2dfT)Wi>cJhj&XL;8rwBTr#Aj%MW!BEoPI=C3cr~ zk##|FgVezYpl;hvRK;NZPCb#DSX9_mCXpI=M5Icg*9mK~3+HFe+K|6!-G)-37D8rP z1d2ebq)@6z<}?w(gT2lcEEH8MVq{$wcV%cN0`g8+9s#Bl1b>l1F9v1WzvG@ z1(R)C4O1TSX?n(%x#B`ZUajGY*iy5~YBhtmFcC64jUovXf-~P~X9b>RMI{j^y7Q_NstXQolzbIGA%_4GY^J~hh5iKmvq0pW27*2!&t^Qsg z;veXAG-E9uX$_g6k*X`D)wMNZ0k5{ari`~^fodukNeD;R7bFW^z+;`;^!AR>J={Pe%j=vq=uM9Kv?0VFc zsAusQBd%@REL#EQ_h@z2 zY;tzi?)BPbdak|J%l8Pq3ZE9SrX?!2$ej|8+Gh+|P8^u{9CBx$f8X>QHqfV0^pgGZ zUQTBoGMF9QvWC4yu(4!4AQ$cjNE-bnAJL1&dNDRWbFQnU{ zC}0J8D@~|}N?Px-R^SW{J_Kg}b71you;$RL9diUFh=^Zr;F4?87%UrJLTExwQq z<{45IUrg|-xICC=NJPuG6=6b|Bl0S`J-sm1CSXW z=;w1^t6Hk4f`kWv79K)lhC$o7chocB?QC2&?>SgSCNq+cpeZll5|l9t+zJb-QL8ly z6;YN~$Ux*AMR^r_=K#O|)R{9QgG5tHDp1M2@1ts&0`{4`bl#2}tXko1WMGoC=)uNz zhu7itH3i&=Ct$1hVlIzTZXwmC#Im>nB*clDAkfi4EcTJ4BHR_R-eS}iMhS*Y#*;M5 z3_^lY=S}e5fy*vlU%=yglzt164zAk7@Cq~y;>|@H83{!2Eu|fZ)Ie#s1qT7$XSmgF z{01aIAYd&odg+PnIz*>0oqvL@M}^aL`X zlm#VNRYl>_GO}v5WM>ImU=muzguw0sPEqSnWaKzGw)$!Xm16nS{J!se?E29A?;iRF zVPKJ%!{1GI`~6_SG7crg*2*$*rL;~d(;50k@wUt5g{DqCFTNb$s$3?8{}(6%XV&D z$M`Q`E>v=ZD+Eems|5j}DX6gR*YK0LT1jLltX{PUNWFmZ2*)hL1$M^kc=~nRWHUQl zq{GEvwbnINarjcMl#ps=Qbir2gwmHHHp9l}LUMiARw-!xH!~(3np#bm;j41+$F6`K+>SlliQi z+QTSg4xPICnLSI9)%TRlUdOJoLa81?#ei^(7-#&O?8?B*Q1lljaQS$;&I*1%tQ!jd z=^5S5;>H53RG^l@oVyLT*g`f3<~Auskesd)lvm|4D%12T?K^0qakya42309<3Hp>; z4I|PRPE;vmhj2z>ZdfIjd2xmq>cIr~u*nOX4j$}jZ*osEdR-l8VS>?{OyAF7{dE58 zb7L_PFLU>roW-JI#9dTw<6;WvJ$PjL(I1IZ|G4!1r`NiB8k@8(1WMQq;248lEUD!v ziE3@Nrdorj7)p!GqA=2E52zlulrB)!fj3$tUlT0sl`y92q3Rw>i!+vpLw_U$7mP`> zBtw517EW-RLk!H(>U09Q42E(Y(1zuhSnKdw$iNZC%IrA=cVG76r4MbMTf)$c;0$-P z#R`R+8^u**x-e0Lk&!@zL8%YB129Gm0FYQrX2v_HM8!}Y!l9a@fl-4i7*U)HCNhOG z)W%?Y>)aJmiB1hgjK9QXwG3KKuS9Cfi{!=F=Iq!p8)@`299lEuW1JTdLhaS~1TErH zu94q67{EU>!bqb{ln9*6U1&RT#xZ9!QQMS}C~s+I=uV?h`p;xwD5UIK1y@i*Fa~e~ zBZli32KbLbj&%<)fK6bNRFmn5))~^ZV!1p{*sNlltZAnt zhg*4!E}Ufaf$i4AFt*_g@L*&xl8Z)D;LD8+gW1ejORQtW7qJ)`xED!DNy)z_%}dlM zOioF9GwEE?%#^?W`Nx!5NmHjBO4>E$*QC3WXYtF&PjSW*_FghI-0Z& zY6otel9hx_nV)oT^3Fg1oT5!insP4bo++;+-8IGa=Vw#)COw<{b5ik?9Ee7aB&|&B z4}aDrzn-)yag51-tx4-sRwSjT-2C&;l;@K&rd&xPQanl1rwk;eOsW0z_msJR{+cqJ z#Dwo)rM#5%a7rxc?kTpUlshVtW~BI&rlibB%Dm&=q{mb6q|7PT|GYBg$3K6W;!Mg& zxi=|&O8=if-BAw5`aillpO7e{D2ku+J|@T#qZAp(p`e^$$V!MbgrGkp1T7*Y2(kzQ zS1p=NRv=Nk{$aJuWd?&m*dijR2wEtW1W6bvS?Q(_N+~O8Zs$G}q{W%{&CKI{=ic*s z>wDe~Cq;e#Z1=)G)P_8=p%Jw#VrP=mn8tB5u-E2z(&m}5Uwory+6T;7C5v{KT{ehM z_8mjzIbO0!%-Y{@+TQb~l(wHdW4+vOllpI-o%WRl`^}O~bCb>Rnbv+A*Exf{V6)tV zZDlE` zpG9ZL^YCm#hZq^w^vYqIN4M6?*cLNaA3O^_(ICk~Xx328=HxhzdH$aH;u`Z;=AL`Z zUg!GRQR~moeu($x7>`8~UvtHOlow z^r!lqVf5JxR@p$R%Z%rAchWW*Id|3<>h;>34QDg5h?Mya-$CWHP1owy}Y literal 0 HcmV?d00001 diff --git a/test/resources/fonts/otf/SourceSansProBold.otf b/test/resources/fonts/otf/SourceSansProBold.otf new file mode 100644 index 0000000000000000000000000000000000000000..8998f3de6e545d65c4a7048dd56e678ae3bf4f38 GIT binary patch literal 104072 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 E0H_sezW@LL literal 0 HcmV?d00001 -- 2.39.5