PDFsharp & MigraDoc Foundation https://forum.pdfsharp.net/ |
|
Bug discovered when using condensed font in PdfSharp https://forum.pdfsharp.net/viewtopic.php?f=3&t=2826 |
Page 1 of 1 |
Author: | philfordjour [ Thu May 29, 2014 8:25 pm ] |
Post subject: | Bug discovered when using condensed font in PdfSharp |
I discovered an issue with how font names are being constructed inside PdfSharp which affects the library from picking the appropriate font face. Also, when you examine the fonts embedded inside a PDF file (created from PdfSharp lib), Adobe does not recognize the font names correctly under the document properties or if you try to modify the document using Acrobat. I have a working solution below that addresses these font issues. Code: //File: PDFsharp/PdfSharp.Pdf.Advanced/PdfTrueTypeFont.cs //Class: PdfSharp.Pdf.Advanced.PdfTrueTypeFont //OLD CODE: public PdfType0Font(PdfDocument document, XFont font, bool vertical) : base(document) { Elements.SetName(Keys.Type, "/Font"); Elements.SetName(Keys.Subtype, "/Type0"); Elements.SetName(Keys.Encoding, vertical ? "/Identity-V" : "/Identity-H"); OpenTypeDescriptor ttDescriptor = (OpenTypeDescriptor)FontDescriptorStock.Global.CreateDescriptor(font); this.fontDescriptor = new PdfFontDescriptor(document, ttDescriptor); this.fontOptions = font.PdfOptions; Debug.Assert(this.fontOptions != null); this.cmapInfo = new CMapInfo(ttDescriptor); this.descendantFont = new PdfCIDFont(document, this.fontDescriptor, font); this.descendantFont.CMapInfo = this.cmapInfo; // Create ToUnicode map this.toUnicode = new PdfToUnicodeMap(document, this.cmapInfo); document.Internals.AddObject(toUnicode); Elements.Add(Keys.ToUnicode, toUnicode); //if (this.fontOptions.BaseFont != "") //{ // BaseFont = this.fontOptions.BaseFont; //} //else { BaseFont = font.Name.Replace(" ", ""); switch (font.Style & (XFontStyle.Bold | XFontStyle.Italic)) { case XFontStyle.Bold: this.BaseFont += ",Bold"; break; case XFontStyle.Italic: this.BaseFont += ",Italic"; break; case XFontStyle.Bold | XFontStyle.Italic: this.BaseFont += ",BoldItalic"; break; } } // CID fonts are always embedded BaseFont = PdfFont.CreateEmbeddedFontSubsetName(BaseFont); this.fontDescriptor.FontName = BaseFont; this.descendantFont.BaseFont = BaseFont; PdfArray descendantFonts = new PdfArray(document); Owner.irefTable.Add(descendantFont); descendantFonts.Elements.Add(descendantFont.Reference); Elements[Keys.DescendantFonts] = descendantFonts; } Code: //NEW CODE: public PdfTrueTypeFont(PdfDocument document, XFont font) : base(document) { Elements.SetName(Keys.Type, "/Font"); Elements.SetName(Keys.Subtype, "/TrueType"); // TrueType with WinAnsiEncoding only OpenTypeDescriptor ttDescriptor = (OpenTypeDescriptor)FontDescriptorStock.Global.CreateDescriptor(font); this.fontDescriptor = new PdfFontDescriptor(document, ttDescriptor); this.fontOptions = font.PdfOptions; Debug.Assert(this.fontOptions != null); this.cmapInfo = new CMapInfo(ttDescriptor); if (ttDescriptor.fontData.name != null && !string.IsNullOrEmpty(ttDescriptor.fontData.name.Name)) { BaseFont = ttDescriptor.fontData.name.Name.Replace(" ", ""); } else { BaseFont = font.Name.Replace(" ", ""); switch (font.Style & (XFontStyle.Bold | XFontStyle.Italic)) { case XFontStyle.Bold: BaseFont += ",Bold"; break; case XFontStyle.Italic: BaseFont += ",Italic"; break; case XFontStyle.Bold | XFontStyle.Italic: BaseFont += ",BoldItalic"; break; } } // CID fonts are always embedded BaseFont = PdfFont.CreateEmbeddedFontSubsetName(BaseFont); this.fontDescriptor.FontName = BaseFont; this.descendantFont.BaseFont = BaseFont; PdfArray descendantFonts = new PdfArray(document); Owner.irefTable.Add(descendantFont); descendantFonts.Elements.Add(descendantFont.Reference); Elements[Keys.DescendantFonts] = descendantFonts; } Similar code change is required for the following class. File: PDFsharp/PdfSharp.Pdf.Advanced/PdfType0Font.cs Class: PdfSharp.Pdf.Advanced.PdfType0Font Actual code is not shown here. Code: //File: PDFSharp/PdfSharp.Fonts.OpenType/OpenTypeDescriptor.cs //Class: PdfSharp.Fonts.OpenType.OpenTypeDescriptor //OLD CODE: public OpenTypeDescriptor(XFont font, XPdfFontOptions options) { try { this.fontData = new FontData(font, options); this.fontName = font.Name; Initialize(); } catch { throw; } } //NEW CODE: public OpenTypeDescriptor(XFont font, XPdfFontOptions options) { try { this.fontData = new FontData(font, options); if (this.fontData.name != null && !string.IsNullOrEmpty(this.fontData.name.Name)) { this.fontName = this.fontData.name.Name; } else { this.fontName = font.Name; } this.fontStretch = font.Stretch; Initialize(); } catch { throw; } } The FontSeclector class should include XFontStretch property as a member variable. Also need an accessor method. Code: //File: PDFSharp/PdfSharp.Fonts/FontDescriptorStock.cs
//Class: PdfSharp.Fonts.FontSelector //OLD CODE: public FontSelector(XFontFamily family, XFontStyle style) { this.name = family.Name; this.style = style; this.fontType = FontType.Type0; } public override int GetHashCode() { return this.name.GetHashCode() ^ this.style.GetHashCode(); } //NEW CODE: public FontSelector(XFontFamily family, XFontStyle style, XFontStretch stretch) { this.name = family.Name; this.style = style; this.fontType = FontType.Type0; this.stretch = stretch; } public override int GetHashCode() { return this.name.GetHashCode() ^ this.style.GetHashCode() ^ this.stretch.GetHashCode(); } |
Page 1 of 1 | All times are UTC |
Powered by phpBB® Forum Software © phpBB Group https://www.phpbb.com/ |