How do I print just one or two controls instead of the whole form in Visual Basic
I have a program that gives the user driving directions, I would like the user to be able to print just the directions or just the directions and a map by selecting a corresponding radio button for each option. How can I print just these sections and not the whole form? And how can I use the radio buttons to tell it what to print? Thanks
Updated code:
Private Sub btnprint_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnprint.Click
If rbprintall.Checked = True Then
'Ad code to print all here
ElseIf rbprintdirections.Checked = True Then
lbldirections.DrawToBitmap()
lbldirections2.DrawToBitmap()
lbldirections3.DrawToBitmap()
lbldirections4.DrawToBitmap()
Else
MessageBox.Show("You must select one of the开发者_C百科 above options!")
End If
If you're using Windows Forms, almost all of the built-in controls can be easily rendered to an image using their DrawToBitmap
method. If you simply want to print whatever is currently displayed by a control, this is the easiest way to do it. Do note, however, that there are a couple of caveats to what can be drawn this way. See the linked documentation for details.
Printing in the .NET Framework is also made relatively simple by taking advantage of the functionality provided in the System.Drawing.Printing
namespace. If you aren't already experienced with this, Google for some tutorials. For example, there's a pretty good article here from the MSDN Magazine.
So, to accomplish your ultimate goal, you'll need to do the following:
- When the user clicks "Print", determine which radio button is currently selected.
- Create a temporary bitmap and grab a copy of the appropriate control in that bitmap using the control's
DrawToBitmap
method. (If you need to print multiple controls, create a separate temporary bitmap for each of them, and then print each of them in the next step.) - Draw that image to the printer using the
Graphics.DrawImage
method in thePrintPage
event handler method for aPrintDocument
object you've created.
EDIT: I'm not really sure where your question is with regards to the code that you've posted, but I see two primary problems.
In the first block of your
if
statement, the comment suggests you don't know how to print all of the controls. You have a couple of different options. If you just want to print every control on the form as it appears, you can simply use theDrawToBitmap
method of theForm
itself. That will create a bitmap of the form's entire client area, including all of the controls it contains.If there are still some controls on the form that you don't want to print, even when the user chooses "Print All", you'll need to call the
DrawToBitmap
methods on each individual control. You might set up a loop so that you don't have to write a line of code for every control, but there's not really another good option.I suspect you're going to have problems with the second
elseif
block working as you expect it to, also. Recall that I said above you need to create temporary bitmap images, and then draw into those bitmaps? TheDrawToBitmap
method takes two parameters:bitmap: a
System.Drawing.Bitmap
that you want an image of the control to be drawn intotargetBounds: a
System.Drawing.Rectangle
that describes the bounds of the control that will be rendered
The code you've shown is missing both of those parameters. In this case, the second (
targetBounds
) is simple—because you want to draw the entire control, all you need to do is specify it'sClientRectangle
property for that parameter.For the first (
bitmap
) parameter, you need to do as I mentioned above and create a newBitmap
image by declaring a temporary variable. Then, you need to call theDrawToBitmap
method with this temporary bitmap specified.Maybe I can be clearer with an example. Modify your above code to look like this:
'Declare some class-level variables to hold images of the controls to print Private bmpDirections1 As System.Drawing.Bitmap Private bmpDirections2 As System.Drawing.Bitmap Private bmpDirections3 As System.Drawing.Bitmap Private bmpDirections4 As System.Drawing.Bitmap Private Sub btnprint_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnprint.Click If rbprintall.Checked = True Then 'Add code to print all here ElseIf rbprintdirections.Checked = True Then 'Draw lbldirections control to bitmap variable named bmpDirections1 bmpDirections1 = New Bitmap(lbldirections.Width, lbldirections.Height) lbldirections.DrawToBitmap(bmpDirections1, lbldirections.ClientRectangle) 'Draw lbldirections2 control to bitmap variable named bmpDirections2 bmpDirections2 = New Bitmap(lbldirections2.Width, lbldirections2.Height) lbldirections2.DrawToBitmap(bmpDirections2, lbldirections2.ClientRectangle) 'Draw lbldirections3 control to bitmap variable named bmpDirections3 bmpDirections3 = New Bitmap(lbldirections3.Width, lbldirections3.Height) lbldirections3.DrawToBitmap(bmpDirections3, lbldirections3.ClientRectangle) 'Draw lbldirections4 control to bitmap variable named bmpDirections4 bmpDirections4 = New Bitmap(lbldirections4.Width, lbldirections4.Height) lbldirections4.DrawToBitmap(bmpDirections4, lbldirections4.ClientRectangle) Else MessageBox.Show("You must select one of the above options!") End If End Sub
The only thing to remember is that you need to call the
Dispose
method on each bitmap variable when you are finished using it. TheDispose
method "releases the resources owned by the image", which means that it frees up the memory it was using. There's no reason to keep those large-ish images around if you're not going to use them again. So, you should probably do this after the print job is completed. Once you dispose the bitmap object, you will no longer be able to use the image it contained, but you can always create a new bitmap object and assign it to the variable (as shown in the above code) the next time the user clicks print.Unrelated: There's no reason to test for
If x = True
. The simplerIf x
is the same thing, and considered by most programmers to be better style. Effectively, you're doing a double comparison againstTrue
, which isn't necessary.
精彩评论