为什么一个NullReferenceException抛出点击两次ToolStrip的按钮时 - openFileDialog.showDialog()?两次、抛出、按钮、NullReference

2023-09-05 01:58:46 作者:追风筝的孩子

我创建了一个干净的WindowsFormsApplication解决方案,增加了一个的ToolStrip 的主要形式,并放置在其上的一个按钮。我还添加了打开文件对话框,使点击事件ToolStripButton 如下所示:

 私人无效toolStripButton1_Click(对象发件人,EventArgs的)
{
    openFileDialog1.ShowDialog();
}
 

我没有改变任何其他属性或事件。

有趣的是,当我双击 ToolStripButton (第二次点击必须相当快,在对话框打开之前),然后取消这两个对话框(或选择一个文件,它其实并不重要),然后单击主窗体的客户区,一个的NullReferenceException 崩溃的应用程序(错误信息附加在帖子的末尾) 。 请注意,点击事件被实施,而的DoubleClick 不是的。

什么是更奇怪的是,当打开文件对话框将替换为任何用户实现形式,在 ToolStripButton 从块被点击两次的。

我使用VS2008与.NET3.5在 Windows 7专业版(从MSDNAA)与最新的更新。我没有VS(只字体大小,工作区文件夹和行号)更改许多选项。

有谁知道如何解决这个问题?它是100%复制我的机器上,它是别人吗?

这是我能想到打电话 OpenFileDialog.ShowDialog(),然后启用按钮回到之前禁用按钮的一种解决方案(但不是很好)。任何其他的想法?

而现在的承诺错误的详细信息:

  

System.NullReferenceException是未处理        消息=对象未设置为一个对象的实例。        来源=System.Windows.Forms的        堆栈跟踪:             在System.Windows.Forms.NativeWindow.WindowClass.Callback(IntPtr的的HWND,味精的Int32,IntPtr的WPARAM,IntPtr的LPARAM)             在System.Windows.Forms.UnsafeNativeMethods.PeekMessage(MSG和放大器;味精,Han​​dleRef HWND,的Int32满足msgmin,的Int32 MSGMAX,的Int32删除)             在System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(Int32 dwComponentID,的Int32原因的Int32 pvLoopData)             在System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(的Int32原因,ApplicationContext的情况下)             在System.Windows.Forms.Application.ThreadContext.RunMessageLoop(的Int32原因,ApplicationContext的情况下)             在System.Windows.Forms.Application.Run(表格的MainForm)             在WindowsFormsApplication1.Program.Main()W C:\用户\ Marchewek \桌面\工作区\的VisualStudio \ WindowsFormsApplication1 \的Program.cs:行20             在System.AppDomain._nExecuteAssembly(议会会议,字串[] args)             在System.AppDomain.ExecuteAssembly(字符串assemblyFile,证据assemblySecurity,字串[] args)             在Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()             在System.Threading.ThreadHelper.ThreadStart_Context(对象状态)             在System.Threading.ExecutionContext.Run(ExecutionContext中的ExecutionContext,ContextCallback回调,对象的状态)             在System.Threading.ThreadHelper.ThreadStart()    的InnerException:

解决方案

我能复制这样的事情在Windows 7计算机 - 我不明白例外,但我的形式将不再重画。这可能是因为我没有在Win 7的机器上运行的调试器的异常被吞噬。

霍尊不甘退圈 借陈岚之手实名举报,晒转账,她为什么要帮他呢

这不会发生在我的XP的机器。当我用toolStripButton并在其上双击了我第一次打开的对话​​框这只发生。如果我正常打开对话框,然后首先关闭它然后双击不能打开该对话框的两倍。

我的犯罪嫌疑人的,什么是发生在这里的类似以竞争状态 - 在框架开发万万没有想到,他们的code可以输入两次,但已经发生,因为一个新的呼叫回消息循环。那么,为什么会出现这种情况 - 看起来像我的错误。

我发现了一个很简单的解决办法,从发生停止它 - 让toolStripButton的doubleClickEnabled属性。您没有实现双击处理程序 - 它对待双击作为一个单一的点击,然后和它所有的作品。

我会处理这个问题是这样的:

 公共Form1中()
    {
        的InitializeComponent();

        //这是一个解决方法的框架错误
        //看等等等等
        toolStripButton1.DoubleClickEnabled = TRUE;

    }
 

下次你升级的框架,你可以尝试删除它。

尼尔

I created a clean WindowsFormsApplication solution, added a ToolStrip to the main form, and placed one button on it. I've added also an OpenFileDialog, so that the Click event of the ToolStripButton looks like the following:

private void toolStripButton1_Click(object sender, EventArgs e)  
{  
    openFileDialog1.ShowDialog();  
}

I didn't change any other properties or events.

The funny thing is that when I double-click the ToolStripButton (the second click must be quite fast, before the dialog opens), then cancel both dialogs (or choose a file, it doesn't really matter) and then click in the client area of main form, a NullReferenceException crashes the application (error details attached at the end of the post). Please note that the Click event is implemented while DoubleClick is not.

What's even more strange that when the OpenFileDialog is replaced by any user-implemented form, the ToolStripButton blocks from being clicked twice.

I'm using VS2008 with .NET3.5 on Windows 7 Professional (from MSDNAA) with latest updates. I didn't change many options in VS (only fontsize, workspace folder and line numbering).

Does anyone know how to solve this? It is 100% replicable on my machine, is it on others too?

One solution that I can think of is disabling the button before calling OpenFileDialog.ShowDialog() and then enabling the button back (but it's not nice). Any other ideas?

And now the promised error details:

System.NullReferenceException was unhandled Message="Object reference not set to an instance of an object." Source="System.Windows.Forms" StackTrace: at System.Windows.Forms.NativeWindow.WindowClass.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam) at System.Windows.Forms.UnsafeNativeMethods.PeekMessage(MSG& msg, HandleRef hwnd, Int32 msgMin, Int32 msgMax, Int32 remove) at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(Int32 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(Form mainForm) at WindowsFormsApplication1.Program.Main() w C:\Users\Marchewek\Desktop\Workspaces\VisualStudio\WindowsFormsApplication1\Program.cs:line 20 at System.AppDomain._nExecuteAssembly(Assembly 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.Run(ExecutionContext executionContext, ContextCallback callback, Object state) at System.Threading.ThreadHelper.ThreadStart() InnerException:

解决方案

I was able to replicate something like this on a windows 7 Machine - I don't get exception the but my form will no longer redraw. It may be that because I am not running in a debugger on the win 7 box that the exception is being swallowed.

This does not happen on my XP machine. This only happened when I used the toolStripButton and double clicked on it the first time I opened the dialog. If I opened the dialog normally and then closed it first then the double click does not open the dialog twice.

I suspect that what is happening here is similar to a race condition - where the framework developer never expected that their code could be entered twice, but that has occurred because of a new call back into the message loop. So why is this happening - looks like a bug to me.

I found one quite easy workaround that stops it from happening - enable the DoubleClickEnabled property of the toolStripButton. You don't have to implement the double click handler - it treats the double click as a single click then and it all works.

I would handle this thus:

    public Form1()
    {
        InitializeComponent();

        // This is a workaround for a framework bug
        // see blah blah
        toolStripButton1.DoubleClickEnabled = true; 

    }

Next time you upgrade frameworks you can try removing it.

Neil