System.ObjectDisposedException在WinForms应用程序中将按钮样式设置为FlatStyle.System时

Man*_*wal 6 c# vb.net exception button winforms

System.ObjectDisposedException当按钮样式设置为FlatStyle.SystemWinForms应用程序时

我有一个子表单,显示单击父项中的按钮.代码如下所示.

Public Class Parent

    Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    End Sub

    Private Sub btnOpenChild_Click(sender As Object, e As EventArgs) Handles btnOpenChild.Click
        Child.Show()
    End Sub

End Class
Run Code Online (Sandbox Code Playgroud)

子表单依次是一个自动关闭的按钮.

Public Class Child
    Private Sub btnCloseMe_Click(sender As Object, e As EventArgs) Handles btnCloseMe.Click
        Me.Close()
    End Sub
End Class
Run Code Online (Sandbox Code Playgroud)

获得异常的步骤:

  • 在调试模式下,打开一个断点 Me.Close()
  • 然后点击孩子的关闭按钮.
  • 在破发点击打开记事本和
  • 回到解决方案然后继续

例外:

System.ObjectDisposedException was unhandled
  HResult=-2146232798
  Message=Cannot access a disposed object.
Object name: 'Button'.
  Source=System.Windows.Forms
  ObjectName=Button
  StackTrace:
       at System.Windows.Forms.Control.CreateHandle()
       at System.Windows.Forms.Control.get_Handle()
       at System.Windows.Forms.Control.PointToScreen(Point p)
       at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
       at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
       at System.Windows.Forms.Control.WndProc(Message& m)
       at System.Windows.Forms.ButtonBase.WndProc(Message& m)
       at System.Windows.Forms.Button.WndProc(Message& m)
       at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
       at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
       at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
       at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
       at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(IntPtr dwComponentID, Int32 reason, Int32 pvLoopData)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
       at System.Windows.Forms.Application.Run(ApplicationContext context)
       at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.OnRun()
       at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.DoApplicationModel()
       at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.Run(String[] commandLine)
       at WindowsApplication2.My.MyApplication.Main(String[] Args) in 17d14f5c-a337-4978-8281-53493378c1071.vb:line 81
       at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
       at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
       at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
       at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
       at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
       at System.Threading.ThreadHelper.ThreadStart()
  InnerException: 
Run Code Online (Sandbox Code Playgroud)

有没有人有任何想法,当按钮样式设置为时,这是明确的 FlatStyle.System

Iva*_*oev 2

很快,这是一个错误。/内部实现维护一些ButtonButtonBase鼠标状态相关的标志,在这种情况下这些标志未正确清除。FlatStyle.System似乎是一个特殊情况,涉及源代码中的很多分支,所以显然其中一些分支丢失了一些东西。

解决方法是创建并使用您自己的Button子类,如下所示(抱歉,对于 C#,我确信您可以将其转换为 VB):

public class MyButton : Button
{
    protected override void OnMouseUp(MouseEventArgs mevent)
    {
        if (this.IsDisposed) return;
        base.OnMouseUp(mevent);
    }
}
Run Code Online (Sandbox Code Playgroud)