从HTML到PDF转换生成一个异常

问题描述:

我有一个小的C#桌面应用程序,创建一个PDF文件,给出一些HTML,从* .eml文件中检索。 下面是一个示例:从HTML到PDF转换生成一个异常

<html> 
<head> 
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 
</head> 
<body> 
<div style="font: normal 13px Arial; color:#000000;"> 
    <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><font size="3"><font face="Calibri">Some text<o:p></o:p></font></font><br /> 
    </p> 
    <p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><o:p><font size="3" face="Calibri">&nbsp;</font></o:p><br /> 
    <span style="FONT-SIZE: 11pt; FONT-FAMILY: &quot;Calibri&quot;,&quot;sans-serif&quot;; mso-fareast-font-family: Calibri; mso-fareast-theme-font: minor-latin; mso-bidi-font-family: &quot;Times New Roman&quot;; mso-fareast-language: EN-US; mso-ascii-theme-font: minor-latin; mso-hansi-theme-font: minor-latin; mso-bidi-theme-font: minor-bidi; mso-ansi-language: IT; mso-bidi-language: AR-SA">Some other text</span> 
    </p> 
</div> 
</body> 
</html> 

一切正常,我的机器(Win10 x64)的就好了,但是当我运行在客户机(赢服务器2008 R2 x64)的相同的代码,我得到了“文档中有无iTextsharp异常的“页面”消息。

对于特定的HTML字符串,例如我刚发布的字符串,这种情况有时只会发生;我无法在客户端的机器上运行调试会话,但是我证实程序接收到格式良好的HTML(因为它是用HTML Agility Pack进行分析的)。

这是一个与字体相关的问题吗?我完全没有线索,这些似乎出现在客户端的机器上。

下面是我用它来创建PDF文档的代码片段(它使用的自定义图像标签处理器,但它不应该成为问题,因为没有任何给定片断):

using (var document = new Document()) 
{ 
    var writer = PdfWriter.GetInstance(document, new FileStream(destinationPath, FileMode.Create)); 
    writer.CompressionLevel = PdfStream.BEST_COMPRESSION; 
    document.Open(); 

    var tagProcessors = (DefaultTagProcessorFactory)Tags.GetHtmlTagProcessorFactory(); 
    tagProcessors.RemoveProcessor(HTML.Tag.IMG); 
    tagProcessors.AddProcessor(HTML.Tag.IMG, new CustomImageTagProcessor()); 
    CssFilesImpl cssFiles = new CssFilesImpl(); 
    cssFiles.Add(XMLWorkerHelper.GetInstance().GetDefaultCSS()); 
    var cssResolver = new StyleAttrCSSResolver(cssFiles); 
    cssResolver.AddCss(@"code { padding: 2px 4px; }", "utf-8", true); 
    var charset = Encoding.UTF8; 
    var hpc = new HtmlPipelineContext(new CssAppliersImpl(new XMLWorkerFontProvider())); 
    hpc.SetAcceptUnknown(true).AutoBookmark(true).SetTagFactory(tagProcessors); 
    var htmlPipeline = new HtmlPipeline(hpc, new PdfWriterPipeline(document, writer));        
    var pipeline = new CssResolverPipeline(cssResolver, htmlPipeline); 
    var worker = new XMLWorker(pipeline, true); 
    var xmlParser = new XMLParser(true, worker, charset); 
    xmlParser.Parse(new StringReader(fixedMarkup)); 
} 

发现的问题。正如我怀疑的那样,它与字体有关。

在我的机器上,Calibri字体可以嵌入* .pdf文档,而在其他机器上,其“字体嵌入性”属性设置为“受限制”。

我想我将不得不解析HTML并将“字体家族”标签中的所有值更改为非限制性的值。

您应该迁移到PDFHTML,即将HTML转换为PDF的iText7(最新版本的iText)插件。 多年来修复了很多bug(与表格,字体和布局有关),因此默认情况下,pdfHTML更有可能进行转换。

示例代码:

HtmlConverter.convertToPdf(
    "<b>This text should be written in bold.</b>", 
    new PdfWriter(new File("C://users/mentre83/output.pdf"))); 
+0

感谢您的建议,我会尝试获得试用许可证以验证这是否是更好的解决方案。我仍然想确定两台机器上不同行为的原因。 – mentre83

+0

我认为(但是这基于更多的经验,而不是实际运行代码),它可能需要对字体或其他资源在一台计算机上不可用,但在另一台计算机上可用。例如,如果字形不能被渲染(因为字体没有那个字形),iText将不会渲染那个字符。如果所有角色都被跳过,则不会添加任何内容,并且您会看到“文档没有页面”例外。 Arial unicode在所有机器上都不可用。 –

+0

我的想法。虽然字形似乎不是问题,但我怀疑这与字体有关。在资源方面,我用来测试代码的机器(我也在几台虚拟机上试过)似乎几乎完全相同。 – mentre83