C# 我遗漏了什么步骤,或者我的顺序不正确,导致PDF编写失败?
我有一个生成PDF文件的代码,但它无法打开,Edge在我尝试时告诉我,“无法打开PDF。有什么东西阻止打开此PDF。” 以下是不知怎么搞砸了/乱七八糟的代码(省略了非永久性和冗余代码): 我看到“文件已写入”messagebox.show,但随后出现“无法访问封闭流” 更新 我现在正在创建MemoryStream,但没有使用“关闭”,并在写入之前关闭文档,但我仍然收到一条消息,即PDF文件(尽管它确实有一些内容(2KB))无法打开 我认为“writer”至少是问题的一部分,因为没有它,PDF是0KB的,但是有了它,“writer”就会变灰,好像它没有被使用一样。下面是我现在的代码(只有上面提到的差异): 我没有看到任何异常消息 更新2 好的,这就是工作所需要的:C# 我遗漏了什么步骤,或者我的顺序不正确,导致PDF编写失败?,c#,pdf,itextsharp,filestream,C#,Pdf,Itextsharp,Filestream,我有一个生成PDF文件的代码,但它无法打开,Edge在我尝试时告诉我,“无法打开PDF。有什么东西阻止打开此PDF。” 以下是不知怎么搞砸了/乱七八糟的代码(省略了非永久性和冗余代码): 我看到“文件已写入”messagebox.show,但随后出现“无法访问封闭流” 更新 我现在正在创建MemoryStream,但没有使用“关闭”,并在写入之前关闭文档,但我仍然收到一条消息,即PDF文件(尽管它确实有一些内容(2KB))无法打开 我认为“writer”至少是问题的一部分,因为没有它,PDF是0
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
PdfWriter.GetInstance(doc, ms);
doc.Open();
. . . // contents added to the file, same as before
doc.Add(tblHeadings);
} // using doc
var bytes = ms.ToArray();
String PDFFileName = $"ChairmensCounselInfo_{DateTime.Now.ToShortTimeString()}.pdf";
PDFFileName = PDFFileName.Replace(":", "_");
var chairmansPDFFile = $"C:\\AYttFMApp\\{PDFFileName}";
File.WriteAllBytes(chairmansPDFFile, bytes);
MessageBox.Show($"{PDFFileName} written");
在关闭
文档
之前,您正在使用内存流
创建一个字节
数组。这将导致PDF不完整
在使用创建文档的的结尾处,PDF已完成(例如,基本交叉引用表已写入),但此时,您已使用不完整的流写入PDF文件
如何解决这个问题
不要使用use
创建MemoryStream
。等待文档
关闭,然后将内存流
的字节写入PDF文件
更新:
您在更新中没有正确遵循我的建议。你有这样的想法:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
using (var writer = PdfWriter.GetInstance(doc, ms))
{
doc.Open();
// adding content
var bytes = ms.ToArray();
doc.Close();
// write bytes to a file.
}
}
正如我前面解释的,这是错误的。您正在将不完整PDF的内容写入名为bytes
的字节数组。该PDF已损坏,因为它没有交叉引用表。只有在显式或隐式地Close()
文档时,才会创建交叉引用表。现在,您可以在创建bytes
数组后显式关闭()文档。那太晚了
你需要这样的东西:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
var writer = PdfWriter.GetInstance(doc, ms));
doc.Open();
// adding content
}
var bytes = ms.ToArray();
// write bytes to a file
如果您不需要编写器
,您甚至可以执行以下操作:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
PdfWriter.GetInstance(doc, ms));
doc.Open();
// adding content
}
var bytes = ms.ToArray();
// write bytes to a file
只需确保您创建了完整的PDF:
文档
有机会关闭之前,不要关闭编写器
文档有机会关闭之前,不要使用ms
在关闭
文档
之前,您正在使用内存流
创建一个字节
数组。这将导致PDF不完整
在使用创建文档的的结尾处,PDF已完成(例如,基本交叉引用表已写入),但此时,您已使用不完整的流写入PDF文件
如何解决这个问题
不要使用use
创建MemoryStream
。等待文档
关闭,然后将内存流
的字节写入PDF文件
更新:
您在更新中没有正确遵循我的建议。你有这样的想法:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
using (var writer = PdfWriter.GetInstance(doc, ms))
{
doc.Open();
// adding content
var bytes = ms.ToArray();
doc.Close();
// write bytes to a file.
}
}
正如我前面解释的,这是错误的。您正在将不完整PDF的内容写入名为bytes
的字节数组。该PDF已损坏,因为它没有交叉引用表。只有在显式或隐式地Close()
文档时,才会创建交叉引用表。现在,您可以在创建bytes
数组后显式关闭()文档。那太晚了
你需要这样的东西:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
var writer = PdfWriter.GetInstance(doc, ms));
doc.Open();
// adding content
}
var bytes = ms.ToArray();
// write bytes to a file
如果您不需要编写器
,您甚至可以执行以下操作:
var ms = new MemoryStream();
using (var doc = new Document(PageSize.A4.Rotate(), 25, 25, 25, 25))
{
PdfWriter.GetInstance(doc, ms));
doc.Open();
// adding content
}
var bytes = ms.ToArray();
// write bytes to a file
只需确保您创建了完整的PDF:
文档
有机会关闭之前,不要关闭编写器
文档有机会关闭之前,不要使用ms
您在更新中所说的与下面的代码相矛盾。您说您在写入之前关闭文档,但事实并非如此:您在关闭文档之前将
ms
写入bytes
。你所做的违背了基本逻辑。另外:当您使用时,不需要关闭文档
。我已经更新了我的答案,您现在可以看到如何解释我的初始答案。B。Clay Shannon,你有一个不起作用的代码,试图让它在不知道怎么做的情况下工作。不如从工作代码(如basic)开始,一步一步地进行更改,每次更改后进行测试,看看是什么更改导致了错误。当然,我们可以为您提供有关使用iTextSharp类的提示(@Bruno在这里已经做了很好的工作),但我们不知道您使用的所有其他内容是否如预期的那样工作。@mkl感谢您的澄清。在过去的一年里,我已经回答了B.Clay Shannon提出的许多问题;到目前为止,B.克莱·香农应该已经有了一些使用iTextSharp的经验。不幸的是,这本书似乎是B.Clay Shannon想要使用的唯一资源::d您在更新中所说的内容与下面的代码相矛盾。您说您在写入之前关闭文档,但事实并非如此:您在关闭文档之前将ms
写入bytes
。你所做的违背了基本逻辑。另外:当您使用时,不需要关闭文档
。我已经更新了我的答案,您现在可以看到如何解释我的初始答案。B。Clay Shannon,你有一个不起作用的代码,试图让它在不知道怎么做的情况下工作。不如从工作代码(如basic)开始,一步一步地进行更改,每次更改后进行测试,看看是什么更改导致了错误。我们当然可以给你机会