使用iTextSharp将HTML样式(虚线下划线)转换为PDF
问题描述:
我试图从下面的HTML生成PDF,即带有虚线下划线的文本。 (下面是样品的实际HTML是大得多)使用iTextSharp将HTML样式(虚线下划线)转换为PDF
<u style="border-bottom: 1px dotted #000;text-decoration: none;"> Hello </u>
如How to convert HTML to PDF using iTextSharp说明。输出应该有一个虚线,我可以在HTML文件中看到,但iTextSharp生成的PDF显示正常下划线,而不是虚线下划线。这里是我的完整方法
public void UsingXMLWorker()
{
Byte[] bytes;
//Create a stream that we can write to, in this case a MemoryStream
using (var ms = new MemoryStream())
{
using (var doc = new Document())
{
//Create a writer that's bound to our PDF abstraction and our stream
using (var writer = PdfWriter.GetInstance(doc, ms))
{
//Open the document for writing
doc.Open();
//sample HTML and CSS
var example_html = @"<u style=""border-bottom: 1px dotted #000;text-decoration: none;"" > Hello </u>";
using (var srHtml = new StringReader(example_html))
{
//Parse the HTML
iTextSharp.tool.xml.XMLWorkerHelper.GetInstance().ParseXHtml(writer, doc, srHtml);
}
//var example_html = @"<u class=""dottedBorder""> Hello </u>";
//var example_css = @".dottedBorder{border-bottom: 1px dotted #000;text-decoration: none;font-size:38px;}";
//using (var msCss = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(example_css)))
//{
// using (var msHtml = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(example_html)))
// {
// //Parse the HTML
// iTextSharp.tool.xml.XMLWorkerHelper.GetInstance().ParseXHtml(writer, doc, msHtml, msCss);
// }
//}
doc.Close();
}
}
bytes = ms.ToArray();
}
var testFile = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Desktop), "test.pdf");
System.IO.File.WriteAllBytes(testFile, bytes);
}
我甚至尝试其他方法,如下面的代码我依然看到,而不是一个点式下划线正常下划线生成的PDF文件。我在这里错过了什么?
var example_html = @"<u class=""dottedBorder""> Hello </u>";
var example_css = @".dottedBorder{border-bottom: 1px dotted #000;text-decoration: none;font-size:38px;}";
using (var msCss = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(example_css)))
{
using (var msHtml = new MemoryStream(System.Text.Encoding.UTF8.GetBytes(example_html)))
{
//Parse the HTML
iTextSharp.tool.xml.XMLWorkerHelper.GetInstance().ParseXHtml(writer, doc, msHtml, msCss);
}
}
答
根据CSS conformance list,只有表格单元格支持边框。
您看到的这条线实际上是<u>
标签的默认底部边框,您的text-decoration
代码实际上正被<u>
标签的默认代码覆盖。如果您观看iTextSharp\tool\xml\css\StyleAttrCSSResolver.cs
中的ResolveStyles
方法,则设置tagCss
的键和值的顶部块(5.5.6中的大约170)会正确查找并设置您的属性。然后,接下来的代码块会特殊处理某些HTML标签,并强制执行某些规则。
// inherit css from parent tags, as defined in provided CssInheritanceRules or if property = inherit
IDictionary<String, String> css = t.CSS;
if (t.Name != null)
{
if (t.Name.Equals(HTML.Tag.I) || t.Name.Equals(HTML.Tag.CITE)
|| t.Name.Equals(HTML.Tag.EM) || t.Name.Equals(HTML.Tag.VAR)
|| t.Name.Equals(HTML.Tag.DFN) || t.Name.Equals(HTML.Tag.ADDRESS)) {
tagCss[CSS.Property.FONT_STYLE] = CSS.Value.ITALIC;
}
else if (t.Name.Equals(HTML.Tag.B) || t.Name.Equals(HTML.Tag.STRONG)) {
tagCss[CSS.Property.FONT_WEIGHT] = CSS.Value.BOLD;
}
else if (t.Name.Equals(HTML.Tag.U) || t.Name.Equals(HTML.Tag.INS)) {
tagCss[CSS.Property.TEXT_DECORATION] = CSS.Value.UNDERLINE;
}
else if (t.Name.Equals(HTML.Tag.S) || t.Name.Equals(HTML.Tag.STRIKE)
|| t.Name.Equals(HTML.Tag.DEL)) {
tagCss[CSS.Property.TEXT_DECORATION] = CSS.Value.LINE_THROUGH;
}
else if (t.Name.Equals(HTML.Tag.BIG)) {
tagCss[CSS.Property.FONT_SIZE] = CSS.Value.LARGER;
}
else if (t.Name.Equals(HTML.Tag.SMALL)) {
tagCss[CSS.Property.FONT_SIZE] = CSS.Value.SMALLER;
}
}
由于该块之后你的CSS发生你会看到,你不能在一个<u>
标签删除下划线,因为它总是会重新打开。同样,除非设置了父容器的字体大小,否则也不能取消加粗的<strong>
标记,非斜体<em>
或明确设置<big>
标记的字体大小(我忘记了实际上是标记!)。
因此,不幸的是,修改源文件的时间不长,我不确定您正在寻找什么是可能的。
谢谢你的更新克里斯。我尝试过使用不同的HTML标签,但问题仍然存在。例如
就像我说的,你只能改变表格单元格上的边框样式,没有别的,所以div不会帮你。你需要把它和另一个混合起来(我忘了我甚至写过)! –