support type 1 normal fonts and fix bug with fetching resource dictionary

This commit is contained in:
Eliot Jones
2018-01-08 21:58:07 +00:00
parent 133ab43d45
commit b1fbcd0ccd
5 changed files with 96 additions and 5 deletions

View File

@@ -78,7 +78,7 @@
return descriptor.FontName;
}
throw new InvalidFontFormatException($"Could not find a name for this TrueType font {dictionary}.");
throw new InvalidFontFormatException($"Could not find a name for this font {dictionary}.");
}
}
}

View File

@@ -1,6 +1,5 @@
namespace UglyToad.Pdf.Fonts.Parser.Handlers
{
using System;
using Cmap;
using ContentStream;
using Cos;
@@ -71,7 +70,7 @@
Encoding encoding = encodingReader.Read(dictionary, reader, isLenientParsing, descriptor);
return new TrueTypeSimpleFont(name, firstCharacter, lastCharacter, widths, descriptor, toUnicodeCMap, encoding);
return new Type1Font(name, firstCharacter, lastCharacter, widths, descriptor, encoding, toUnicodeCMap);
}
}
}

View File

@@ -0,0 +1,86 @@
namespace UglyToad.Pdf.Fonts.Simple
{
using Cmap;
using Composite;
using Core;
using Cos;
using Encodings;
using Geometry;
using IO;
/// <summary>
/// TODO: implement this properly if you find a Type 1 font in the wild.
/// </summary>
internal class Type1Font : IFont
{
private readonly int firstChar;
private readonly int lastChar;
private readonly decimal[] widths;
private readonly FontDescriptor fontDescriptor;
private readonly Encoding encoding;
private readonly ToUnicodeCMap toUnicodeCMap;
private readonly TransformationMatrix fontMatrix = TransformationMatrix.FromValues(0.001m, 0, 0, 0.001m, 0, 0);
public CosName Name { get; }
public bool IsVertical { get; } = false;
public Type1Font(CosName name, int firstChar, int lastChar, decimal[] widths, FontDescriptor fontDescriptor, Encoding encoding, CMap toUnicodeCMap)
{
this.firstChar = firstChar;
this.lastChar = lastChar;
this.widths = widths;
this.fontDescriptor = fontDescriptor;
this.encoding = encoding;
this.toUnicodeCMap = new ToUnicodeCMap(toUnicodeCMap);
Name = name;
}
public int ReadCharacterCode(IInputBytes bytes, out int codeLength)
{
codeLength = 1;
return bytes.CurrentByte;
}
public bool TryGetUnicode(int characterCode, out string value)
{
if (toUnicodeCMap.CanMapToUnicode)
{
return toUnicodeCMap.TryGet(characterCode, out value);
}
value = null;
if (encoding == null)
{
return false;
}
var name = encoding.GetName(characterCode);
value = GlyphList.AdobeGlyphList.NameToUnicode(name);
return true;
}
public PdfVector GetDisplacement(int characterCode)
{
return fontMatrix.Transform(new PdfVector(GetWidth(characterCode), 0));
}
public decimal GetWidth(int characterCode)
{
if (characterCode < firstChar || characterCode > lastChar)
{
return 250;
}
return widths[characterCode - firstChar];
}
public TransformationMatrix GetFontMatrix()
{
return fontMatrix;
}
}
}

View File

@@ -133,6 +133,13 @@ namespace UglyToad.Pdf.Graphics
}
else if (parameter.ParameterType == typeof(decimal[]))
{
if (operands[offset] is ArrayToken arr)
{
arguments.Add(arr.Data.OfType<NumericToken>().Select(x => x.Data).ToArray());
offset++;
continue;
}
var array = new List<decimal>();
while (offset < operands.Count && operands[offset] is NumericToken numeric)
{

View File

@@ -189,8 +189,7 @@
if (resources is CosObject resourceObject)
{
var resourceDictionary =
pdfObjectParser.Parse(resourceObject.ToIndirectReference(), reader, isLenientParsing);
var resourceDictionary = DirectObjectFinder.Find<PdfDictionary>(resourceObject, pdfObjectParser, reader, isLenientParsing);
if (resourceDictionary is PdfDictionary resolvedDictionary)
{