GDI+移动线内存泄漏

发布于 2024-09-07 22:35:26 字数 1362 浏览 4 评论 0原文

我尝试使用 GDI+/Invalidate 和线形控件来完成此操作。在这两种情况下,记忆都会失控。为了进行演示,创建一个带有计时器对象的 Windows 窗体应用程序,该计时器对象设置为 100 毫秒并启用并使用以下代码:

Public Class Form1
   Private Y As Integer
   Private intDirection As Integer = 1

   Private Sub timTest_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles timTest.Tick
      Me.Invalidate()
   End Sub

   Private Sub Form1_Paint(ByVal sender As Object, ByVal e As System.Windows.Forms.PaintEventArgs) Handles Me.Paint

      Dim g As Graphics = Me.CreateGraphics
      Dim myPen As New Pen(Color.Black)

      myPen.Width = 1
      g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
      g.DrawLine(myPen, 10, 10, 200, Y)

      Y += intDirection

      If Y > Me.Height - 20 Then intDirection = -1
      If Y < 0 Then intDirection = 1
      g.Dispose()
      myPen.Dispose()
   End Sub
End Class

因此,上面的代码会在线条移动时导致内存泄漏。我认为原因是在幕后创建了非托管位图来绘制未发布的表单,因为在托管端它只是一个指针。

如果我在绘制函数的开头

  Dim intAlloc As Integer = Me.Width * Me.Height * 16
  GC.AddMemoryPressure(intAlloc)

和函数的末尾添加以下代码,我调用

  GC.RemoveMemoryPressure(intAlloc)

内存利用率会增加一点并缩小一点,但永远不会失去控制。 AddMemoryPressure 和RemoveMemoryPressure 似乎提醒GC 它需要运行。有没有更好的方法来做到这一点或者这是正确的?上面的代码只是为了示例目的而进行的简化,以找到我在具有多条移动线的较大组件中遇到的问题的根源。这也是计算放置在 AddMemoryPressure 中的正确值的最佳方法吗?

I have tried to do this both with GDI+/Invalidate and by using a Line Shape Control. In both cases the memory spirals out of control. To demonstrate, create a windows form application with a timer object which is set to 100ms and enabled and use the following code:

Public Class Form1
   Private Y As Integer
   Private intDirection As Integer = 1

   Private Sub timTest_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles timTest.Tick
      Me.Invalidate()
   End Sub

   Private Sub Form1_Paint(ByVal sender As Object, ByVal e As System.Windows.Forms.PaintEventArgs) Handles Me.Paint

      Dim g As Graphics = Me.CreateGraphics
      Dim myPen As New Pen(Color.Black)

      myPen.Width = 1
      g.SmoothingMode = Drawing2D.SmoothingMode.AntiAlias
      g.DrawLine(myPen, 10, 10, 200, Y)

      Y += intDirection

      If Y > Me.Height - 20 Then intDirection = -1
      If Y < 0 Then intDirection = 1
      g.Dispose()
      myPen.Dispose()
   End Sub
End Class

So the code above causes a memory leak as the line moves. I think the reason is that there are unmanaged bitmaps created behind the scenes to paint the form which are not being released because on the managed side it is just a pointer.

If I add the following code at the start of the paint function

  Dim intAlloc As Integer = Me.Width * Me.Height * 16
  GC.AddMemoryPressure(intAlloc)

and at the end of the function I call

  GC.RemoveMemoryPressure(intAlloc)

The memory utilization grows a little and shrinks a little but never grows out of control. The AddMemoryPressure and RemoveMemoryPressure seems to alert the GC that it needs to run. Is there a better way to do this or is this correct? The code above is just a simplification for example purposes to get to the root of a problem I have in a larger component with several moving lines. Also is this the best way to calculate the proper value to place in AddMemoryPressure?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文