vb.net VB.NET绘制方法?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/20638943/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
VB.NET paint method?
提问by Doug Hauf
Is this the best way to paint images on a form? I have most of my experience in Java and little in VB.net. In Java there is repaint() that can be called? There is a Me.refresh(). Is this what you wnat to call when you have something to add to the form or to paint to the form.
这是在表单上绘制图像的最佳方式吗?我在 Java 方面拥有大部分经验,而在 VB.net 方面经验很少。在 Java 中有可以调用的 repaint() 吗?有一个 Me.refresh()。当您要向窗体添加某些内容或要在窗体上绘画时,这是否是您想要调用的。
Class:
班级:
Public Class Form1
Private Sub Form1_Paint(sender As System.Object, e As System.Windows.Forms.PaintEventArgs) Handles MyBase.Paint
' Create image.
Dim newImage As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
' Create Point for upper-left corner of image.
Dim ulCorner As New Point(50, 50)
' Draw image to screen.
e.Graphics.DrawImage(newImage, ulCorner)
Dim newImage2 As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
' Create Point for upper-left corner of image.
Dim ulCorner2 As New Point(150, 150)
' Draw image to screen.
e.Graphics.DrawImage(newImage2, ulCorner2)
End Sub
End Class
I tried this code here with one button on the form with a click event
我在此处使用带有单击事件的表单上的一个按钮尝试了此代码
Public Class Form1
Dim i As Integer
Private Sub Form1_Paint(sender As System.Object, e As System.Windows.Forms.PaintEventArgs) Handles MyBase.Paint
i = 0
' Create image.
Dim newImage As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
' Create Point for upper-left corner of image.
Dim ulCorner As New Point(50, 50)
' Draw image to screen.
e.Graphics.DrawImage(newImage, ulCorner)
Dim newImage2 As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
' Create Point for upper-left corner of image.
Dim ulCorner2 As New Point(150, 150)
' Draw image to screen.
e.Graphics.DrawImage(newImage2, ulCorner2)
If i = 5 Then
' Create image.
Dim newImage3 As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
' Create Point for upper-left corner of image.
Dim ulCorner3 As New Point(250, 250)
' Draw image to screen.
e.Graphics.DrawImage(newImage3, ulCorner3)
End If
End Sub
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
i = 5
Me.Refresh()
End Sub
End Class
Just Tried this code here:
刚刚在这里尝试了这段代码:
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
i = 5
Me.Invalidate()
End Sub
New Class just Tested:
刚刚测试的新类:
Public Class Form2
Dim newImage As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
Dim newImage2 As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
Dim newImage3 As Image = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
Private bgImage As Bitmap
Private srcImages As Image()
Protected Overrides Sub OnPaint(e As System.Windows.Forms.PaintEventArgs)
Dim img As Bitmap = Me.bgImage
If (img Is Nothing) Then
Me.bgImage = New Bitmap(Me.ClientSize.Width, Me.ClientSize.Height)
img = Me.bgImage
End If
If (Not Me.srcImages Is Nothing) Then
End If
MyBase.OnPaint(e)
End Sub
Private Sub _Load(sender As Object, e As EventArgs) Handles MyBase.Load
Me.srcImages = New Image(3 - 1) {}
Me.srcImages(0) = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
Me.srcImages(1) = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
Me.srcImages(2) = Image.FromFile("C:\Users\itpr13266\Desktop\Pic\article-tip.gif")
End Sub
Private Sub _Disposed(sender As Object, e As EventArgs) Handles MyBase.Disposed
If (Not Me.srcImages Is Nothing) Then
For Each img As Image In Me.srcImages
If (Not img Is Nothing) Then
img.Dispose()
End If
Next
Me.srcImages = Nothing
End If
If (Not Me.bgImage Is Nothing) Then
Me.bgImage.Dispose()
Me.bgImage = Nothing
End If
End Sub
Private Sub _Resize(sender As Object, e As EventArgs) Handles MyBase.SizeChanged, MyBase.Resize
If (Not Me.bgImage Is Nothing) Then
Me.bgImage.Dispose()
Me.bgImage = Nothing
End If
End Sub
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
Me.Invalidate()
End Sub
End Class
采纳答案by Bj?rn-Roger Kringsj?
Calling Me.Invalidate()invalidates the entire surface of the control and causes the control to be redrawn.
调用Me.Invalidate()会使控件的整个表面无效并导致重新绘制控件。
I also suggest that you don'tload your images in everypaint cycle. You could load the source images in the forms load event and destroy them when the form disposes.
我还建议您不要在每个绘制周期都加载图像。您可以在表单加载事件中加载源图像并在表单处理时销毁它们。
Public Class Form1
Protected Overrides Sub OnPaint(e As System.Windows.Forms.PaintEventArgs)
Dim img As Bitmap = Me.bgImage
If (img Is Nothing) Then
Me.bgImage = New Bitmap(Me.ClientSize.Width, Me.ClientSize.Height)
img = Me.bgImage
End If
'TODO: Draw and paint.
If (Not Me.srcImages Is Nothing) Then
End If
MyBase.OnPaint(e)
End Sub
Private Sub _Load(sender As Object, e As EventArgs) Handles MyBase.Load
Me.srcImages = New Image(3 - 1) {}
Me.srcImages(0) = Image.FromFile("...")
Me.srcImages(1) = Image.FromFile("...")
Me.srcImages(2) = Image.FromFile("...")
End Sub
Private Sub _Disposed(sender As Object, e As EventArgs) Handles MyBase.Disposed
If (Not Me.srcImages Is Nothing) Then
For Each img As Image In Me.srcImages
If (Not img Is Nothing) Then
img.Dispose()
End If
Next
Me.srcImages = Nothing
End If
If (Not Me.bgImage Is Nothing) Then
Me.bgImage.Dispose()
Me.bgImage = Nothing
End If
End Sub
Private Sub _Resize(sender As Object, e As EventArgs) Handles MyBase.SizeChanged, MyBase.Resize
If (Not Me.bgImage Is Nothing) Then
Me.bgImage.Dispose()
Me.bgImage = Nothing
End If
End Sub
Private bgImage As Bitmap
Private srcImages As Image()
End Class
回答by Hans Passant
The 1st snippet shows no evidence of needing any help. Nothing in the Paint event handler depends on the state of class so there's no reason to force a repaint. Default painting is already good enough.
第一个片段没有显示需要任何帮助的证据。Paint 事件处理程序中的任何内容都不依赖于类的状态,因此没有理由强制重新绘制。默认绘画已经足够好了。
The 2nd snippet does, through the artificial ivariable. You'd always call Me.Invalidate()in such a case, that marks the entire client region of the form as requiring a repaint. The UI then eventually gets a Paint event when nothing more important needs to be done. Using Me.Refresh()works too but is heavy-handed and it is exceedingly rare to need it. I can't think of a good example.
第二个片段是通过人工i变量。Me.Invalidate()在这种情况下,您总是会调用,这会将表单的整个客户区域标记为需要重新绘制。当没有更重要的事情需要做时,UI 最终会得到一个 Paint 事件。使用Me.Refresh()也有效,但操作繁琐,需要它的情况极为罕见。我想不出一个很好的例子。
Note how Invalidate()has some overloads, you can mark just a portion of the window to require repainting. This is an optimization that makes painting more efficient.
请注意Invalidate()如何有一些重载,您可以仅标记窗口的一部分需要重新绘制。这是一种使绘画更有效的优化。
As written, your program is likely to crash after using it for a while. You must call the Dispose() method of the images you load. Take a look at the VB.NET Usingstatement. You'll want to pre-load the images so it doesn't happen while painting and won't happen repeatedly. Following a Winforms programming tutorial or book is highly recommended to avoid these kind of traps.
正如所写,您的程序在使用一段时间后可能会崩溃。您必须调用加载的图像的 Dispose() 方法。查看 VB.NET Using语句。您需要预加载图像,以便在绘画时不会发生,也不会重复发生。强烈建议遵循 Winforms 编程教程或书籍以避免此类陷阱。

