''' <summary>
''' Converts a text file to a PDF document.
''' </summary>
''' <param name="sourceTextFilename">The filename of source text file.</param>
''' <param name="destPdfFilename">The filename of destination PDF document.</param>
Public Shared Sub ConvertTextFileToPdfDocument(sourceTextFilename As String, destPdfFilename As String)
' font name
Dim fontName As String = "Arial"
' font size, in points
Dim fontSize As Integer = 12
' text padding, in points
Dim textPadding As New Vintasoft.Imaging.PaddingF(30)
' get text from text file
Dim text As String = System.IO.File.ReadAllText(sourceTextFilename, System.Text.Encoding.UTF8)
' set new line to '\n' character
text = text.Replace(vbCr & vbLf, vbLf)
text = text.Replace(vbLf & vbCr, vbLf)
text = text.Replace(vbCr, vbLf)
' create PDF document
Using document As New Vintasoft.Imaging.Pdf.PdfDocument(destPdfFilename, Vintasoft.Imaging.Pdf.PdfFormat.Pdf_14)
Dim font As Vintasoft.Imaging.Pdf.Tree.Fonts.PdfFont
' find TTF font that should be used for drawing a text
Using fontProgramSearchResult As Vintasoft.Imaging.Fonts.FontProgramSearchResult = document.FontProgramsController.GetTrueTypeFontProgram(New Vintasoft.Imaging.Fonts.FontInfo(fontName))
' create PDF font based on TTF font program
font = document.FontManager.CreateCIDFontFromTrueTypeFont(fontProgramSearchResult.FontProgramFilename)
End Using
Do
' create page of A4 size
Dim pdfPage As New Vintasoft.Imaging.Pdf.Tree.PdfPage(document, Vintasoft.Imaging.ImageSize.FromPaperKind(Vintasoft.Imaging.PaperSizeKind.A4))
' add page to the PDF document
document.Pages.Add(pdfPage)
' get PdfGraphics that is associated with PDF page
Using graphics As Vintasoft.Imaging.Pdf.Drawing.PdfGraphics = Vintasoft.Imaging.Pdf.Drawing.PdfGraphics.FromPage(pdfPage)
' create a brush that should be used for drawing a text
Dim brush As New Vintasoft.Imaging.Pdf.Drawing.PdfBrush(System.Drawing.Color.Black)
' specify a rectangle where text should be drawn
Dim rect As System.Drawing.RectangleF = pdfPage.MediaBox
' apply padding
rect = textPadding.ApplyTo(rect)
' get text that must be drawn on current page
Dim drawnText As String = GetDrawnText(graphics, font, fontSize, rect.Width, rect.Height, text)
' draw text on the PDF page
graphics.DrawString(drawnText, font, fontSize, brush, rect, Vintasoft.Imaging.Pdf.Drawing.PdfContentAlignment.Left, _
True)
End Using
Loop While Not String.IsNullOrEmpty(text)
' subset font
document.FontManager.PackAllFonts()
' pack PDF document
document.Pack()
End Using
End Sub
''' <summary>
''' Returns the text portion that can be drawn on specified PDF graphics in rectange with specified size.
''' </summary>
''' <param name="graphics">The PDF graphics.</param>
''' <param name="font">The text font.</param>
''' <param name="fontSize">The text font size.</param>
''' <param name="maxWidth">The width of text rectangle.</param>
''' <param name="maxHeight">The height of text rectangle.</param>
''' <param name="text">The text.</param>
''' <returns>The text portion that can be drawn in rectange.</returns>
Private Shared Function GetDrawnText(graphics As Vintasoft.Imaging.Pdf.Drawing.PdfGraphics, font As Vintasoft.Imaging.Pdf.Tree.Fonts.PdfFont, fontSize As Single, maxWidth As Single, maxHeight As Single, ByRef text As String) As String
Dim lineHeight As Single = fontSize
Dim textToDraw As New System.Text.StringBuilder()
Dim totalHeight As Single = 0
Dim line As String = Nothing
While text IsNot Nothing OrElse line IsNot Nothing
' if there is not text line to process
If line Is Nothing Then
' cut next line from source text
line = CutTextPart(text, ControlChars.Lf)
End If
' add line to the result text
textToDraw.Append(GetDrawnLine(graphics, font, fontSize, maxWidth, line))
textToDraw.Append(vbLf)
' increase height of result text
totalHeight += lineHeight
' if height of result text is greater than rectangle height
If totalHeight + lineHeight > maxHeight Then
Exit While
End If
End While
If line IsNot Nothing Then
text = line & ControlChars.Lf & text
End If
Return textToDraw.ToString()
End Function
''' <summary>
''' Returns the line portion that must be drawn on specified PDF graphics in rectange with specified size.
''' </summary>
''' <param name="graphics">The PDF graphics.</param>
''' <param name="font">The text font.</param>
''' <param name="fontSize">The text font size.</param>
''' <param name="maxWidth">The width of text rectangle.</param>
''' <param name="line">The text line.</param>
''' <returns>The text portion that must be drawn.</returns>
Private Shared Function GetDrawnLine(graphics As Vintasoft.Imaging.Pdf.Drawing.PdfGraphics, font As Vintasoft.Imaging.Pdf.Tree.Fonts.PdfFont, fontSize As Single, maxWidth As Single, ByRef line As String) As String
Dim drawnLine As String = Nothing
Dim word As String = Nothing
While line IsNot Nothing
' cut next word from line
word = CutTextPart(line, " "C)
' create next drawn line
Dim nextDrawnLine As String
If drawnLine IsNot Nothing Then
nextDrawnLine = drawnLine.ToString() & " "C & word
Else
nextDrawnLine = word
End If
' measure next drawn line
Dim currentWidth As Single, currentHeight As Single
graphics.MeasureString(nextDrawnLine, font, fontSize, Single.MaxValue, False, currentWidth, _
currentHeight)
' if next draw line width greater than max width
If currentWidth > maxWidth Then
' if drawn line is empty
If drawnLine Is Nothing Then
' add part of word to drawn line
drawnLine = word
word = ""
Do
word = drawnLine.Substring(drawnLine.Length - 1) & word
drawnLine = drawnLine.Substring(0, drawnLine.Length - 1)
graphics.MeasureString(drawnLine.ToString(), font, fontSize, Single.MaxValue, False, currentWidth, _
currentHeight)
Loop While currentWidth > maxWidth
End If
Exit While
End If
If drawnLine IsNot Nothing Then
drawnLine += " "C
End If
drawnLine += word
word = Nothing
End While
If word IsNot Nothing Then
line = word & " "C & line
End If
Return drawnLine
End Function
''' <summary>
''' Cuts a text part from text start to the specified separator.
''' </summary>
''' <param name="text">The source text.</param>
''' <param name="separator">The separator.</param>
''' <returns>The result text.</returns>
Private Shared Function CutTextPart(ByRef text As String, separator As Char) As String
Dim newLineIndex As Integer = text.IndexOf(separator)
Dim result As String
If newLineIndex < 0 Then
result = text
text = Nothing
Return result
End If
result = text.Substring(0, newLineIndex)
If newLineIndex = text.Length - 1 Then
text = Nothing
Else
text = text.Substring(newLineIndex + 1)
End If
Return result
End Function