PrintPageEventArgs
contains a member HasMorePages
that you can set to True to raise the same event again at the end of current iteration.
To print page numbers, you'll need to keep a local class variable to track current page number. Then use an e.Graphics.DrawString()
overload to print page numbers anywhere on the page.
An example using your own code:
Private mPageNumber As Integer = 1
Private Sub printDocument1_PrintPage(ByVal sender As System.Object, ByVal e As _
System.Drawing.Printing.PrintPageEventArgs) Handles PrintDocument1.PrintPage
Dim rect1 As Rectangle = New Rectangle(New Point(0, 0), PictureBox1.Image.Size)
Dim rect2 As Rectangle = New Rectangle(New Point(100, 200), PictureBox1.Image.Size)
Dim fmt As StringFormat = New StringFormat()
e.Graphics.DrawImage(PictureBox1.Image, rect1)
e.Graphics.DrawString(RichTextBox1.Text, RichTextBox1.Font, New SolidBrush(Color.Red), rect2, fmt)
Using f as New Font("Arial" , 10)
e.Graphics.DrawString(mPageNumber.ToString(), , Brushes.Black, 0, 0) 'Page number at top-left of the page
End Using
mPageNumber += 1
e.HasMorePages = (mPageNumber <= 10) 'Will keep printing till 10 pages are printed
End Sub
Going to next page is entirely dependent upon how you want to compute next page. Specifically, you'll need to print each character in its own font (since it is a RichTextBox
) and then take care of paragraphs etc. as well. And as if that were not enough, you may need to tackle bidirectional text, text wrapping, alignment and what not too. Welcome to the world of printing!!
I won't be writing the exact code here, but will give you some hints so you could start your journey. RichTextBox
has a method named GetPositionFromCharIndex()
that gives you the x,y coordinates of the specified character index. You could use a loop to determine the last character whose Y-coordinate is less than or equal to e.MarginBounds.Height
in your PrintPage
event handler and then send all words upto that index to DrawString()
function. You should keep a class level variable to track the last character upto which you have printed on the current page and then start from that point forward in the next iteration. You could use DrawString()
overload that takes layout rectangle as parameter and send e.MarginBounds
to it to let it automatically do word-wrapping for you.
Remember that this will only work with RichTextBox that has a single font used for all its text, which is highly unlikely given the very purpose of RichTextBox. For situations where you have multiple fonts, you'll need to call DrawString()
many times for each character range comprising of a single font. As I said, this has lots of details (such as font kerning, hanging edges and other devils) that cannot be covered here. Keep reading and you'll find lots of good stuff on SO and other places.