如何确定是否正在卸载C#控件?

时间:2009-09-08 09:40:30

标签: c# timer user-controls

在我的C#Windows窗体应用程序中,我有一个包含其他控件的用户控件,并且有自己的逻辑。其中一个是延迟调用(Timer-invoked),它在用户完成键盘输入(实时过滤器文本)后执行某些操作。它访问其他控件,其中一个是文本输入控件。在最后一个输入事件后500毫秒调用此方法。

现在,当应用程序终止时,延迟调用正在运行时出现问题。当我输入一些文本,然后等待大约500毫秒(它似乎每次都有效),然后按Alt + F4关闭窗口,应用程序在尝试访问文本输入控件时抛出NullReferenceException。当我在最后一次输入后立即关闭窗口或在之后的一秒或更长时间后关闭窗口时,不会发生这种情况。

似乎正在处理控件或某些东西,其方法无法再访问子控件。因此,当控件被置于该状态时(由任何人和任何状态exaclty),这些计时器需要首先停止,以便可以安全地处理控件。

我已经尝试在OnHandleDestroyed方法(覆盖)和Designer生成的Dispose方法的开头停止计时器。什么都没有帮助。

在调用base.OnFormClosed()之前,在重写的OnFormClosed方法中停止计时器时,此过程在常规表单中正常工作。我在用户控件中找不到合适的事件。

1 个答案:

答案 0 :(得分:1)

在UserControl中尝试此操作:

bool isDisposed;
protected override void Dispose(bool disposeManaged)
{
    if(!isDisposed)
    {
        if(disposeManaged)
        {
            //Dispose your timer here
        }
        isDisposed = true;
    }
}

另一种可能性是你的一个UI类没有进行清理。例如。它为一个事件注册自己,但在手动处理时不会注销。它从未被GC收集,并且当下次触发事件时,它会尝试访问之前在Dispose(...)调用期间设置为null的某些成员。

另一种可能性是你的代码中存在更复杂的竞争条件,但是从这里很难说。