Including CSS file in pdf using itextsharp - vb.net

I am making a pdf file using iTextSharp.
However, the external CSS that is linked in the source HTML does not shown in the PDF.
How can I include the external css file so iTextSharp renders correctly?
Dim doc As Document = New Document
PdfWriter.GetInstance(doc, New FileStream(Request.PhysicalApplicationPath + _
"\ListingDetails.pdf", FileMode.Create))
Dim content As String = File.ReadAllText(Server.MapPath("~/PDFPage.aspx"))
doc.Open()
Dim parsedHtmlElements = HTMLWorker.ParseToList(New StringReader(content), Nothing)
For Each htmlElement As Object In parsedHtmlElements
doc.Add(TryCast(htmlElement, IElement))
Next
doc.Close()

Related

Show PDF without saving it with itext 7 and vb.net

I currently have the following code, which opens a PDF file and has fillable fields, saves it to a path, and then displays it on the screen (Adobe Reader). What I currently want is to open the PDF, pass the data to it and just display it either in a browser or in Adobe Reader without the need to save it to the local disk.
Dim destino = "C:\generacion\ejemplo.pdf"
Dim leerpdf = "C:\plantillas\plantilla.pdf"
Dim reader As PdfReader = New PdfReader(leerpdf)
Dim writer As PdfWriter = New PdfWriter(CStr(destino))
Dim PdfDocument As PdfDocument = New PdfDocument(reader, writer)
Dim form As iText.Forms.PdfAcroForm = PdfAcroForm.GetAcroForm(PdfDocument, False)
form.GetField("dato1").SetValue(nombre)
form.GetField("dato2").SetValue(direccion)
form.GetField("dato3").SetValue(telefono)
form.FlattenFields()
PdfDocument.Close()
Process.Start(destino)

PDF fill in not merging correctly

We are using an asp.net website with iTextSharp.dll version 5.5.13
We can merge multiple PDF files into one using a stream and it works perfectly. However, when we use a PDF that was created in a "fill-in" function the new PDF file does not correctly merge into the other documents. It merges without the filled in values. However, if I open the filled in PDF that it creates the filled in data displays and prints fine.
I have tried merging the new "filled in" PDF at a later time but it still displays the template file as though the filled in data was missing.
Below code fills in the data
Dim strFileName As String = Path.GetFileNameWithoutExtension(strSourceFile)
Dim strOutPath As String = HttpContext.Current.Server.MapPath("~/Apps/Lifetime/OfficeDocs/Export/")
newFile = strOutPath & strFileName & " " & strRONumber & ".pdf"
If Not File.Exists(newFile) Then
Dim pdfReader As PdfReader = New PdfReader(strSourceFile)
Using pdfStamper As PdfStamper = New PdfStamper(pdfReader, New FileStream(newFile, FileMode.Create))
Dim pdfFormFields As AcroFields = pdfStamper.AcroFields
pdfFormFields.SetField("CUSTOMER NAME", strCustomer)
pdfFormFields.SetField("YR MK MODEL", strVehicle)
pdfFormFields.SetField("RO#", strRONumber)
pdfStamper.FormFlattening = False
pdfStamper.Dispose()
End Using
End If
Then code below here merges multiple PDF files/paths sent to it
Public Shared Sub MergePDFs(ByVal files As List(Of String), ByVal filename As String)
'Gets a list of full path files and merges into one memory stream
'and outputs it to a browser response.
Dim MemStream As New System.IO.MemoryStream
Dim doc As New iTextSharp.text.Document
Dim reader As iTextSharp.text.pdf.PdfReader
Dim numberOfPages As Integer
Dim currentPageNumber As Integer
Dim writer As iTextSharp.text.pdf.PdfWriter = iTextSharp.text.pdf.PdfWriter.GetInstance(doc, MemStream)
doc.Open()
Dim cb As iTextSharp.text.pdf.PdfContentByte = writer.DirectContent
Dim page As iTextSharp.text.pdf.PdfImportedPage
Dim strError As String = ""
For Each strfile As String In files
reader = New iTextSharp.text.pdf.PdfReader(strfile)
numberOfPages = reader.NumberOfPages
currentPageNumber = 0
Do While (currentPageNumber < numberOfPages)
currentPageNumber += 1
doc.SetPageSize(reader.GetPageSizeWithRotation(currentPageNumber))
doc.NewPage()
page = writer.GetImportedPage(reader, currentPageNumber)
cb.AddTemplate(page, 0, 0)
Loop
Next
doc.Close()
doc.Dispose()
If MemStream Is Nothing Then
HttpContext.Current.Response.Write("No Data is available for output")
Else
HttpContext.Current.Response.Clear()
HttpContext.Current.Response.ContentType = "application/pdf"
HttpContext.Current.Response.AppendHeader("Content-Disposition", "inline; filename=" + filename)
HttpContext.Current.Response.BinaryWrite(MemStream.ToArray)
HttpContext.Current.Response.OutputStream.Flush()
HttpContext.Current.Response.OutputStream.Close()
HttpContext.Current.Response.OutputStream.Dispose()
MemStream.Close()
MemStream.Dispose()
End If
End Sub
I expect the "filled in" PDF in the list of files to retain the filled in data but it does not. Even if I try to merge the filled in file later it still comes up missing the filled in data. If I print the filled in file it looks perfect.
PdfWriter.GetImportedPage only returns you a copy of the page contents. This does not include any annotations, in particular not the widget annotations of form fields on the page at hand.
To also copy the annotations of the source pages, use the iText PdfCopy class instead. This class is designed to copy pages including all annotations. Furthermore, it includes methods to copy all pages of a source document in one step.
You have to tell the PdfCopy object to merge fields, otherwise the document-wide form structure won't be built.
As an aside, your code creates many PdfReader objects but does not close them. That may increase your memory requirements substantially.
Thus:
Public Shared Sub MergePDFsImproved(ByVal files As List(Of String), ByVal filename As String)
Using mem As New MemoryStream()
Dim readers As New List(Of PdfReader)
Using doc As New Document
Dim copy As New PdfCopy(doc, mem)
copy.SetMergeFields()
doc.Open()
For Each strfile As String In files
Dim reader As New PdfReader(strfile)
copy.AddDocument(reader)
readers.Add(reader)
Next
End Using
For Each reader As PdfReader In readers
reader.Close()
Next
HttpContext.Current.Response.Clear()
HttpContext.Current.Response.ContentType = "application/pdf"
HttpContext.Current.Response.AppendHeader("Content-Disposition", "inline; filename=" + filename)
HttpContext.Current.Response.BinaryWrite(mem.ToArray)
HttpContext.Current.Response.OutputStream.Flush()
HttpContext.Current.Response.OutputStream.Close()
HttpContext.Current.Response.OutputStream.Dispose()
End Using
End Sub
Actually I'm not sure whether it is a good idea to Close and Dispose the response output stream here, that shouldn't be the responsibility of a PDF merging method.
This is a related answer for the Java version of iText; you may want to read it for additional information. Unfortunately many links in that answer meanwhile are dead.

How to display a word document in WebBrowser control in Windows Form Application using vb.net?

I created an application which can load a pdf document and then converted it into docx file using aspose.dll library. Lastly, it will display the docx file in WebBrowser control in the windows form application.
This is the code snippet for pdf to word docx conversion.
Dim filePath As String = txtPath.Text
' Dim pdfDocx As Aspose.Pdf.Document = New Aspose.Pdf.Document(filePath)
'open pdf document
Dim pdfDocument As Document = New Document(filePath)
' instantiate DocSaveOptions object
Dim saveOptions As DocSaveOptions = New DocSaveOptions()
' specify the output format as DOCX
Try
saveOptions.Format = DocSaveOptions.DocFormat.DocX
' save document in docx format
pdfDocument.Save("output.docx", saveOptions)
MsgBox("sUCCESS")
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
The saveoptions succeed but now I want to display it in WebBrowser control. How can I do this? Thanks

Add a table to a PDF template using iTextSharp and VB.net

I've been stuck on this far longer than I care to admit. I'm trying to use iTextSharp to build a table that I can then insert into a PDF template (which is really just a PDF with a header and an acrofield that needs to be populated). I've currently got code that follows the same outline below:
Dim doc As New Document
Dim reader As PdfReader
Dim stamper As PdfStamper
Dim filestream As FileStream
Dim tempfile As String = My.Computer.FileSystem.GetTempFileName
filestream = New FileStream(tempfile, FileMode.Create)
PdfWriter.GetInstance(doc, filestream)
doc.Open()
generateTableForPdf(listOfData, numColumns, doc)
doc.Close()
reader = New PdfReader(pdfTemplatePath)
stamper = New PdfStamper(reader, filestream)
stamper.AcroFields.SetField("topmostSubform[0].Page1[0].headerField", "some text to go in the field")
The pdfTemplatePath is a private const that has the template's file path that I am trying to use and generateTableForPdf simply creates a dynamically sized table and puts it in doc (doc is passed by ref). I know the table is created because it displays when the page loads, however, the header in the template doesn't appear. I've looked around and found a couple of examples that use byte streams or memory streams, but my attempts at implementing those methods have failed more dramatically. Any help or guidance in better understanding how to go about this is greatly appreciated.

How can I test if a PDF document is PDF/A compliant using iTextSharp?

I have a existing PDF file and with iTextSharp I want to test if it is PDF/A compliant.
I don't want convert or create a file, just read and check if it is a PDF/A.
I have not tried anything because I did not find any methods or properties of the class PdfReader of iTextSharp, saying that the PDF is PDF/A. For now it would be enough to know how to verify that the document claims to be PDF/A compatible
Thanks
Antonio
After a long search i tried this way and seems to work:
Dim reader As iTextSharp.text.pdf.PdfReader = New iTextSharp.text.pdf.PdfReader(sFilePdf)
Dim yMetadata As Byte() = reader.Metadata()
Dim bPDFA As Boolean = False
If Not yMetadata Is Nothing Then
Dim sXmlMetadata = System.Text.ASCIIEncoding.Default.GetString(yMetadata)
Dim xmlDoc As Xml.XmlDocument = New Xml.XmlDocument()
xmlDoc.LoadXml(sXmlMetadata)
Dim nodes As Xml.XmlNodeList = xmlDoc.GetElementsByTagName("pdfaid:conformance")
If nodes.Item(0).FirstChild.Value.ToUpper = "A" Then
bPDFA = True
End If
End If
Return bPDFA
I also found some reference to the class XmpReader, but not sufficient to do what I wanted