我正在设计一个与VB.NET中的MS Paint具有相同功能的程序。下面的代码允许我成功地单击并拖动以在图片框上绘制选择矩形,但它看起来很滞后(特别是与MS Paint本身相比)。有没有更有效的方法呢?
Public DrawCapture As Boolean = False
Public DrawCaptureOrigin As Point
Public DrawCaptureRectangle As Rectangle
Private Sub PictureBox1_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseDown
DrawCapture = True
DrawCaptureOrigin = e.Location
DrawCaptureRectangle = New Rectangle(e.Location, New Point(1, 1))
End Sub
Private Sub PictureBox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove
Dim curX As Integer = e.Location.X, curY As Integer = e.Location.Y
Dim dcoX As Integer = DrawCaptureOrigin.X, dcoY As Integer = DrawCaptureOrigin.Y
If DrawCapture Then
If curX < dcoX And curY < dcoY Then
DrawCaptureRectangle = New Rectangle(curX, curY, dcoX - curX, dcoY - curY)
ElseIf curX < dcoX Then
DrawCaptureRectangle = New Rectangle(curX, dcoY, dcoX - curX, curY - dcoY)
ElseIf curY < dcoY Then
DrawCaptureRectangle = New Rectangle(dcoX, curY, curX - dcoX, dcoY - curY)
Else
DrawCaptureRectangle = New Rectangle(dcoX, dcoY, curX - dcoX, curY - dcoY)
End If
PictureBox1.Invalidate()
End If
End Sub
Private Sub PictureBox1_MouseUp(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseUp
DrawCapture = False
PictureBox1.Invalidate()
End Sub
Private Sub PictureBox1_Paint(ByVal sender As Object, ByVal e As System.Windows.Forms.PaintEventArgs) Handles PictureBox1.Paint
If DrawCaptureRectangle.Width > 0 Then
e.Graphics.DrawRectangle(Pens.Black, DrawCaptureRectangle)
End If
End Sub
答案 0 :(得分:1)
我无法在我的电脑上重现laggynes,所以我不确定这是否会有所帮助,但请尝试启用Double Buffering。您可以在Form
属性中设置它。
答案 1 :(得分:0)
易于使用的Windows Runtime API,可通过GPU加速实现即时模式2D图形渲染。
我刚刚第一次试用了它。以下是性能的粗略比较:PictureBox
- 14.5%CPU使用率和CanvasControl
- 3.6%(减少4倍;尽管RAM使用率几乎是其中的5倍)。
所以看起来Win2D工作得更快,实际上很容易使用,但有一个问题。您只能将其用于Store App(适用于Windows或Windows Phone)。这意味着它不能在Windows 7上运行。接受或离开它。 :)
我有8核CPU,所以我假设100%加载的核心应该显示为12.5%的CPU使用率。
如何使用Win2D创建相同的应用程序
创建空白商店应用
如果这是您的第一个商店应用,那么您将被要求获得开发者许可;只需点击I Agree
。
添加Win2D
NuGet包。 (在Solution Explorer
&gt; Manage NuGet Packages...
)
在MainPage.xaml
添加CanvasControl
。将其视为PictureBox
的替代。
<Page
x:Class="Win2D_VBNET.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:Win2D_VBNET"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:canvas="using:Microsoft.Graphics.Canvas.UI.Xaml"
mc:Ignorable="d">
<Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<canvas:CanvasControl ClearColor="White"
Draw="CanvasControl_Draw"
PointerPressed="CanvasControl_PointerPressed"
PointerMoved="CanvasControl_PointerMoved"
PointerReleased="CanvasControl_PointerReleased"/>
</Grid>
</Page>
在代码隐藏中添加所有必要的事件处理程序(MainPage.xaml.vb
)。代码与您的代码完全相同。
Imports Microsoft.Graphics.Canvas.UI.Xaml
Imports Windows.UI
Imports Microsoft.Graphics.Canvas
Public NotInheritable Class MainPage
Inherits Page
Public DrawCapture As Boolean = False
Public DrawCaptureOrigin As Point
Public DrawCaptureRectangle As Rect
Private Sub CanvasControl_PointerPressed(sender As CanvasControl, e As PointerRoutedEventArgs)
Dim location As Point = e.GetCurrentPoint(Nothing).Position
DrawCapture = True
DrawCaptureOrigin = location
DrawCaptureRectangle = New Rect(location, New Size(1, 1))
End Sub
Private Sub CanvasControl_PointerMoved(sender As CanvasControl, e As PointerRoutedEventArgs)
Dim location As Point = e.GetCurrentPoint(Nothing).Position
Dim curX As Integer = location.X, curY As Integer = location.Y
Dim dcoX As Integer = DrawCaptureOrigin.X, dcoY As Integer = DrawCaptureOrigin.Y
If DrawCapture Then
If curX < dcoX And curY < dcoY Then
DrawCaptureRectangle = New Rect(curX, curY, dcoX - curX, dcoY - curY)
ElseIf curX < dcoX Then
DrawCaptureRectangle = New Rect(curX, dcoY, dcoX - curX, curY - dcoY)
ElseIf curY < dcoY Then
DrawCaptureRectangle = New Rect(dcoX, curY, curX - dcoX, dcoY - curY)
Else
DrawCaptureRectangle = New Rect(dcoX, dcoY, curX - dcoX, curY - dcoY)
End If
End If
sender.Invalidate()
End Sub
Private Sub CanvasControl_PointerReleased(sender As CanvasControl, e As PointerRoutedEventArgs)
DrawCapture = False
sender.Invalidate()
End Sub
Private Sub CanvasControl_Draw(sender As CanvasControl, args As CanvasDrawEventArgs)
If DrawCaptureRectangle.Width > 0 Then
args.DrawingSession.Antialiasing = CanvasAntialiasing.Aliased
args.DrawingSession.DrawRectangle(DrawCaptureRectangle, Colors.Black)
End If
End Sub
End Class