📄 type1font.java
字号:
CharacterSet = tok.nextToken("\u00ff").substring(1);
else if (ident.equals("FontBBox"))
{
llx = (int)Float.valueOf(tok.nextToken()).floatValue();
lly = (int)Float.valueOf(tok.nextToken()).floatValue();
urx = (int)Float.valueOf(tok.nextToken()).floatValue();
ury = (int)Float.valueOf(tok.nextToken()).floatValue();
}
else if (ident.equals("UnderlinePosition"))
UnderlinePosition = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("UnderlineThickness"))
UnderlineThickness = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("EncodingScheme"))
EncodingScheme = tok.nextToken("\u00ff").substring(1);
else if (ident.equals("CapHeight"))
CapHeight = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("XHeight"))
XHeight = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("Ascender"))
Ascender = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("Descender"))
Descender = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("StdHW"))
StdHW = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("StdVW"))
StdVW = (int)Float.valueOf(tok.nextToken()).floatValue();
else if (ident.equals("StartCharMetrics"))
{
isMetrics = true;
break;
}
}
if (!isMetrics)
throw new DocumentException("Missing StartCharMetrics in " + fileName);
while ((line = fin.readLine()) != null)
{
StringTokenizer tok = new StringTokenizer(line);
if (!tok.hasMoreTokens())
continue;
String ident = tok.nextToken();
if (ident.equals("EndCharMetrics"))
{
isMetrics = false;
break;
}
Integer C = new Integer(-1);
Integer WX = new Integer(250);
String N = "";
tok = new StringTokenizer(line, ";");
while (tok.hasMoreTokens())
{
StringTokenizer tokc = new StringTokenizer(tok.nextToken());
if (!tokc.hasMoreTokens())
continue;
ident = tokc.nextToken();
if (ident.equals("C"))
C = Integer.valueOf(tokc.nextToken());
else if (ident.equals("WX"))
WX = Integer.valueOf(tokc.nextToken());
else if (ident.equals("N"))
N = tokc.nextToken();
}
CharMetrics.add(new Object[]{C, WX, N});
}
if (isMetrics)
throw new DocumentException("Missing EndCharMetrics in " + fileName);
while ((line = fin.readLine()) != null)
{
StringTokenizer tok = new StringTokenizer(line);
if (!tok.hasMoreTokens())
continue;
String ident = tok.nextToken();
if (ident.equals("EndFontMetrics"))
return;
if (ident.equals("StartKernPairs"))
{
isMetrics = true;
break;
}
}
if (!isMetrics)
throw new DocumentException("Missing EndFontMetrics in " + fileName);
while ((line = fin.readLine()) != null)
{
StringTokenizer tok = new StringTokenizer(line);
if (!tok.hasMoreTokens())
continue;
String ident = tok.nextToken();
if (ident.equals("KPX"))
{
String first = tok.nextToken();
String second = tok.nextToken();
Integer width = new Integer((int)Float.valueOf(tok.nextToken()).floatValue());
Object relates[] = (Object[])KernPairs.get(first);
if (relates == null)
KernPairs.put(first, new Object[]{second, width});
else
{
int n = relates.length;
Object relates2[] = new Object[n + 2];
System.arraycopy(relates, 0, relates2, 0, n);
relates2[n] = second;
relates2[n + 1] = width;
KernPairs.put(first, relates2);
}
}
else if (ident.equals("EndKernPairs"))
{
isMetrics = false;
break;
}
}
if (isMetrics)
throw new DocumentException("Missing EndKernPairs in " + fileName);
fin.close();
}
/** If the embedded flag is <CODE>false</CODE> or if the font is
* one of the 14 built in types, it returns <CODE>null</CODE>,
* otherwise the font is read and output in a PdfStream object.
* @return the PdfStream containing the font or <CODE>null</CODE>
* @throws DocumentException if there is an error reading the font
*/
private PdfStream getFontStream() throws DocumentException
{
if (builtinFont || !embedded)
return null;
InputStream is = null;
try {
File file = new File(fileName.substring(0, fileName.length() - 3) + "pfb");
int fileLength = (int)file.length();
byte st[] = new byte[fileLength - 18];
is = new FileInputStream(file);
int lengths[] = new int[3];
int bytePtr = 0;
for (int k = 0; k < 3; ++k) {
if (is.read() != 0x80)
throw new DocumentException("Start marker missing in " + file.getName());
if (is.read() != pfbTypes[k])
throw new DocumentException("Incorrect segment type in " + file.getName());
int size = is.read();
size += is.read() << 8;
size += is.read() << 16;
size += is.read() << 24;
lengths[k] = size;
while (size != 0) {
int got = is.read(st, bytePtr, size);
if (got < 0)
throw new DocumentException("Premature end in " + file.getName());
bytePtr += got;
size -= got;
}
}
return new StreamFont(st, lengths);
}
catch (Exception e) {
throw new DocumentException(e.getMessage());
}
finally {
if (is != null) {
try {
is.close();
}
catch (Exception e) {
}
}
}
}
/** Generates the font descriptor for this font or <CODE>null</CODE> if it is
* one of the 14 built in fonts.
* @param fontStream the indirect reference to a PdfStream containing the font or <CODE>null</CODE>
* @return the PdfDictionary containing the font descriptor or <CODE>null</CODE>
* @throws DocumentException if there is an error
*/
private PdfDictionary getFontDescriptor(PdfIndirectReference fontStream) throws DocumentException
{
if (builtinFont)
return null;
PdfDictionary dic = new PdfDictionary(new PdfName("FontDescriptor"));
dic.put(new PdfName("Ascent"), new PdfNumber(Ascender));
dic.put(new PdfName("CapHeight"), new PdfNumber(CapHeight));
dic.put(new PdfName("Descent"), new PdfNumber(Descender));
dic.put(new PdfName("FontBBox"), new PdfRectangle(llx, lly, urx, ury));
dic.put(new PdfName("FontName"), new PdfName(FontName));
dic.put(new PdfName("ItalicAngle"), new PdfNumber(ItalicAngle));
dic.put(new PdfName("StemV"), new PdfNumber(StdVW));
if (fontStream != null)
dic.put(new PdfName("FontFile"), fontStream);
int flags = 0;
if (IsFixedPitch)
flags |= 1;
flags |= fontSpecific ? 4 : 32;
if (ItalicAngle < 0)
flags |= 64;
if (FontName.indexOf("Caps") >= 0 || FontName.endsWith("SC"))
flags |= 131072;
if (Weight.equals("Bold"))
flags |= 262144;
dic.put(new PdfName("Flags"), new PdfNumber(flags));
return dic;
}
/** Generates the font dictionary for this font.
* @return the PdfDictionary containing the font dictionary
* @param firstChar the first valid character
* @param lastChar the last valid character
* @param shortTag a 256 bytes long <CODE>byte</CODE> array where each unused byte is represented by 0
* @param fontDescriptor the indirect reference to a PdfDictionary containing the font descriptor or <CODE>null</CODE>
* @throws DocumentException if there is an error
*/
private PdfDictionary getFontBaseType(PdfIndirectReference fontDescriptor, int firstChar, int lastChar, byte shortTag[]) throws DocumentException
{
PdfDictionary dic = new PdfDictionary(PdfName.FONT);
dic.put(PdfName.SUBTYPE, PdfName.TYPE1);
dic.put(PdfName.BASEFONT, new PdfName(FontName));
boolean stdEncoding = encoding.equals("Cp1252") || encoding.equals("MacRoman");
if (!fontSpecific) {
for (int k = firstChar; k <= lastChar; ++k) {
if (!differences[k].equals(notdef)) {
firstChar = k;
break;
}
}
if (stdEncoding)
dic.put(PdfName.ENCODING, encoding.equals("Cp1252") ? PdfName.WIN_ANSI_ENCODING : PdfName.MAC_ROMAN_ENCODING);
else {
PdfDictionary enc = new PdfDictionary(new PdfName("Encoding"));
PdfArray dif = new PdfArray();
boolean gap = true;
for (int k = firstChar; k <= lastChar; ++k) {
if (shortTag[k] != 0) {
if (gap) {
dif.add(new PdfNumber(k));
gap = false;
}
dif.add(new PdfName(differences[k]));
}
else
gap = true;
}
enc.put(new PdfName("Differences"), dif);
dic.put(PdfName.ENCODING, enc);
}
}
if (!(builtinFont && (fontSpecific || stdEncoding))) {
dic.put(new PdfName("FirstChar"), new PdfNumber(firstChar));
dic.put(new PdfName("LastChar"), new PdfNumber(lastChar));
PdfArray wd = new PdfArray();
for (int k = firstChar; k <= lastChar; ++k) {
if (shortTag[k] == 0)
wd.add(new PdfNumber(0));
else
wd.add(new PdfNumber(widths[k]));
}
dic.put(new PdfName("Widths"), wd);
}
if (!builtinFont && fontDescriptor != null)
dic.put(new PdfName("FontDescriptor"), fontDescriptor);
return dic;
}
/** Outputs to the writer the font dictionaries and streams.
* @param writer the writer for this document
* @param ref the font indirect reference
* @param params several parameters that depend on the font type
* @throws IOException on error
* @throws DocumentException error in generating the object
*/
void writeFont(PdfWriter writer, PdfIndirectReference ref, Object params[]) throws DocumentException, IOException {
int firstChar = ((Integer)params[0]).intValue();
int lastChar = ((Integer)params[1]).intValue();
byte shortTag[] = (byte[])params[2];
PdfIndirectReference ind_font = null;
PdfObject pobj = null;
PdfIndirectObject obj = null;
pobj = getFontStream();
if (pobj != null){
obj = writer.addToBody(pobj);
ind_font = obj.getIndirectReference();
}
pobj = getFontDescriptor(ind_font);
if (pobj != null){
obj = writer.addToBody(pobj);
ind_font = obj.getIndirectReference();
}
pobj = getFontBaseType(ind_font, firstChar, lastChar, shortTag);
writer.addToBody(pobj, ref);
}
/** Gets the font parameter identified by <CODE>key</CODE>. Valid values
* for <CODE>key</CODE> are <CODE>ASCENT</CODE>, <CODE>CAPHEIGHT</CODE>, <CODE>DESCENT</CODE>,
* <CODE>ITALICANGLE</CODE>, <CODE>BBOXLLX</CODE>, <CODE>BBOXLLY</CODE>, <CODE>BBOXURX</CODE>
* and <CODE>BBOXURY</CODE>.
* @param key the parameter to be extracted
* @param fontSize the font size in points
* @return the parameter in points
*/
public float getFontDescriptor(int key, float fontSize) {
switch (key) {
case ASCENT:
return Ascender * fontSize / 1000;
case CAPHEIGHT:
return CapHeight * fontSize / 1000;
case DESCENT:
return Descender * fontSize / 1000;
case ITALICANGLE:
return ItalicAngle;
case BBOXLLX:
return llx * fontSize / 1000;
case BBOXLLY:
return lly * fontSize / 1000;
case BBOXURX:
return urx * fontSize / 1000;
case BBOXURY:
return ury * fontSize / 1000;
}
return 0;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -