/** Reads the font metrics
* @param rf the AFM file
* @throws DocumentException the AFM file is invalid
* @throws IOException the AFM file could not be read
*/
public void Process(RandomAccessFileOrArray rf)
{
string line;
bool isMetrics = false;
while ((line = rf.ReadLine()) != null)
{
StringTokenizer tok = new StringTokenizer(line, " ,\n\r\t\f");
if (!tok.HasMoreTokens())
{
continue;
}
string ident = tok.NextToken();
if (ident.Equals("FontName"))
{
FontName = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("FullName"))
{
FullName = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("FamilyName"))
{
FamilyName = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("Weight"))
{
Weight = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("ItalicAngle"))
{
ItalicAngle = float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("IsFixedPitch"))
{
IsFixedPitch = tok.NextToken().Equals("true");
}
else if (ident.Equals("CharacterSet"))
{
CharacterSet = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("FontBBox"))
{
llx = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
lly = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
urx = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
ury = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("UnderlinePosition"))
{
UnderlinePosition = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("UnderlineThickness"))
{
UnderlineThickness = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("EncodingScheme"))
{
EncodingScheme = tok.NextToken("\u00ff").Substring(1);
}
else if (ident.Equals("CapHeight"))
{
CapHeight = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("XHeight"))
{
XHeight = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("Ascender"))
{
Ascender = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("Descender"))
{
Descender = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("StdHW"))
{
StdHW = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("StdVW"))
{
StdVW = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("StartCharMetrics"))
{
isMetrics = true;
break;
}
}
if (!isMetrics)
{
throw new DocumentException(MessageLocalization.GetComposedMessage("missing.startcharmetrics.in.1", fileName));
}
while ((line = rf.ReadLine()) != null)
{
StringTokenizer tok = new StringTokenizer(line);
if (!tok.HasMoreTokens())
{
continue;
}
string ident = tok.NextToken();
if (ident.Equals("EndCharMetrics"))
{
isMetrics = false;
break;
}
int C = -1;
int WX = 250;
string N = "";
int[] B = null;
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 = int.Parse(tokc.NextToken());
}
else if (ident.Equals("WX"))
{
WX = (int)float.Parse(tokc.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
}
else if (ident.Equals("N"))
{
N = tokc.NextToken();
}
else if (ident.Equals("B"))
{
B = new int[] { int.Parse(tokc.NextToken()),
int.Parse(tokc.NextToken()),
int.Parse(tokc.NextToken()),
int.Parse(tokc.NextToken()) };
}
}
Object[] metrics = new Object[] { C, WX, N, B };
if (C >= 0)
{
CharMetrics[C] = metrics;
}
CharMetrics[N] = metrics;
}
if (isMetrics)
{
throw new DocumentException(MessageLocalization.GetComposedMessage("missing.endcharmetrics.in.1", fileName));
}
if (!CharMetrics.ContainsKey("nonbreakingspace"))
{
Object[] space = (Object[])CharMetrics["space"];
if (space != null)
{
CharMetrics["nonbreakingspace"] = space;
}
}
while ((line = rf.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(MessageLocalization.GetComposedMessage("missing.endfontmetrics.in.1", fileName));
}
while ((line = rf.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();
int width = (int)float.Parse(tok.NextToken(), System.Globalization.NumberFormatInfo.InvariantInfo);
Object[] relates = (Object[])KernPairs[first];
if (relates == null)
{
KernPairs[first] = new Object[] { second, width }
}
;
else
{
int n = relates.Length;
Object[] relates2 = new Object[n + 2];
Array.Copy(relates, 0, relates2, 0, n);
relates2[n] = second;
relates2[n + 1] = width;
KernPairs[first] = relates2;
}
}
else if (ident.Equals("EndKernPairs"))
{
isMetrics = false;
break;
}
}
if (isMetrics)
{
throw new DocumentException(MessageLocalization.GetComposedMessage("missing.endkernpairs.in.1", fileName));
}
rf.Close();
}