将iTextSharp PDF作为内存流返回会导致StreamNotSupported [英] Returning iTextSharp PDF as memorystream causes StreamNotSupported
问题描述
我正在使用iTextSharp中的PdfStamper创建一个PDF文件,并将PDF作为memorystream
对象返回给调用函数,然后用于在WinForms的Teleriks PDF Viewer Component中显示PDF。
I'm creating a PDF file using the PdfStamper in iTextSharp and return the PDF as a memorystream object to the calling function, that is then used to display the PDF in Teleriks PDF Viewer Component for WinForms.
这是目标。
现在,创建PDF可以正常工作,并返回数据我应该将内存流内容写入文件流,然后在Adobe Reader中打开,一切看起来都很好。
Right now, creating the PDF works as it should, and it returns the data to the Calling function, and in the Calling function, should I write the memorystream contents to a file stream and then open it in Adobe Reader Everything looks just fine.
但是,如何调用函数和调用函数如果我选择在PDF Viewer Control中显示PDF,我只会收到不支持的流类型错误。
However, if I choose to display the PDF in the PDF Viewer Control I just get an "Unsupported Stream type" error.
现在,我发现PDF数据出错了所以我决定创建PDF文件,将其保存到磁盘,然后在调用函数中将其读取到内存流,并在PDF查看器中显示该内存流,对于某些我未知的原因,它可以工作....
Now, I figured something was wrong in the PDF data so I decided to create the PDF file, save it to disk, then read it to a memorystream in the Calling function and display that memorystream in the PDF Viewer and that, for some to me unknown reason, works....
我真的无法理解这一点并需要一些帮助。
I really can't get my head around this and need some help.
所以,这个不会工作:
//The Calling function
private void dlgViewPDF_Load(object sender, EventArgs e)
{
MemoryStream ms = PDFcreator.GeneratePDFdata(id);
rPdfView.LoadDocument(ms);
}
//The PDF generator
public static MemoryStream GeneratePDFdata(string id)
{
MemoryStream ms = new MemoryStream();
string sTemplate = string.Concat(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "\\template.pdf");
PdfReader pdfReader = new PdfReader(sTemplate);
PdfStamper pdfStamper = new PdfStamper(pdfReader, ms);
PdfContentByte cb = pdfStamper.GetOverContent(1);
BaseFont baseFont = BaseFont.CreateFont(BaseFont.HELVETICA, BaseFont.CP1250, BaseFont.EMBEDDED);
BaseFont baseFontBold = BaseFont.CreateFont(BaseFont.HELVETICA_BOLD, BaseFont.CP1250, BaseFont.EMBEDDED);
cb.SetColorFill(iTextSharp.text.Color.BLACK);
cb.SetFontAndSize(baseFontBold, 14);
cb.BeginText();
cb.ShowTextAligned(PdfContentByte.ALIGN_LEFT, "TEST!!", 385, 750, 0);
cb.EndText();
cb.SetColorStroke(new CMYKColor(0f, 0f, 0f, 1f));
cb.SetColorFill(new CMYKColor(0f, 0f, 0f, 1f));
cb.MoveTo(139, 398);
cb.LineTo(146, 398);
cb.LineTo(146, 391);
cb.LineTo(139, 391);
cb.ClosePathEoFillStroke();
pdfStamper.Close();
pdfReader.Close();
return ms;
}
然而,由于某种原因,这确实有效:
However THIS does work for some reason:
//The Calling function
private void dlgViewPDF_Load(object sender, EventArgs e)
{
MemoryStream ms = new MemoryStream();
FileStream file = new FileStream(@"c:\temp\testfile.pdf", FileMode.Open, FileAccess.Read);
byte[] bytes = new byte[file.Length];
file.Read(bytes, 0, (int)file.Length);
ms.Write(bytes, 0, (int)file.Length);
rPdfView.LoadDocument(ms);
}
//The PDF generator
public static void GeneratePDFdata(string id)
{
MemoryStream ms = new MemoryStream();
string sTemplate = string.Concat(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "\\template.pdf");
PdfReader pdfReader = new PdfReader(sTemplate);
FileStream fs = new FileStream(@"c:\temp\testfile.pdf", FileMode.Create, FileAccess.Write, FileShare.None);
PdfStamper pdfStamper = new PdfStamper(pdfReader, fs);
PdfContentByte cb = pdfStamper.GetOverContent(1);
BaseFont baseFont = BaseFont.CreateFont(BaseFont.HELVETICA, BaseFont.CP1250, BaseFont.EMBEDDED);
BaseFont baseFontBold = BaseFont.CreateFont(BaseFont.HELVETICA_BOLD, BaseFont.CP1250, BaseFont.EMBEDDED);
cb.SetColorFill(iTextSharp.text.Color.BLACK);
cb.SetFontAndSize(baseFontBold, 14);
cb.BeginText();
cb.ShowTextAligned(PdfContentByte.ALIGN_LEFT, "TEST!!", 385, 750, 0);
cb.EndText();
cb.SetColorStroke(new CMYKColor(0f, 0f, 0f, 1f));
cb.SetColorFill(new CMYKColor(0f, 0f, 0f, 1f));
cb.MoveTo(139, 398);
cb.LineTo(146, 398);
cb.LineTo(146, 391);
cb.LineTo(139, 391);
cb.ClosePathEoFillStroke();
pdfStamper.Close();
pdfReader.Close();
}
但为什么呢?我宁愿将它全部保存在内存中,让用户保存生成的PDF,如果他/她愿意,而不是将其写入磁盘然后显示它。
But why? I'd rather keep it all in memory and let the user save the resulting PDF if he/she so wishes than having to write it to disk and then displaying it.
推荐答案
问题出现是因为当PdfStamper关闭时,内存流会被隐式关闭。为防止此添加
The problem arises because the memory stream gets implicitly closed when the PdfStamper is closed. To prevent this add
pdfStamper.Writer.CloseStream = false;
之前
pdfStamper.Close();
这指示压模不要关闭流。
This instructs the stamper not to close the stream.
这篇关于将iTextSharp PDF作为内存流返回会导致StreamNotSupported的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!