如何从另一个线程中的表单关闭新线程上的表单?

时间:2013-10-25 17:30:55

标签: c# winforms

过去一天左右,我一直试图解决这个问题。

我有一个包含Form1的程序,以及一个在新线程中生成Form2的按钮。

我在Form1上还有另一个按钮,它应关闭Form2,但由于Form2在另一个线程中,我无法直接触摸该对象。

我可以做t.Abort(),但会引发异常。

我怎样才能优雅地触摸另一个线程?做点东西吗?

例如,如何从Form1中关闭表单?

我搜索了谷歌“如何从另一个线程中关闭一个表单”,并找到了几个暗示Invoke和Delegate的链接,但在尝试了一些事情之后,我显然无法弄清楚如何正确使用它。 / p>

任何人都可以帮助我理解它如何应用于我的代码,以便我能理解它们如何被使用?在哪种情况下?

为方便起见,我已将项目上传到github:https://github.com/powercat/WindowsFormsApplication7/archive/master.zip

-

代码:

[Form1.cs中]

    public void FormThread()
    {
        Application.Run(new Form2());
    }

    private void button1_Click(object sender, EventArgs e)
    {
        Thread t = new Thread(new ThreadStart(FormThread));
        t.Start();
    }

    private void button2_Click(object sender, EventArgs e)
    {

        //Need to close Form2 from here.

    }

[Form2.cs]

有其他表单代码。

1 个答案:

答案 0 :(得分:2)

一般来说,为两种形式设置两个线程并不是一个好主意。将所有表单放在主要的UI线程上,并将逻辑和工作转移到后台线程上几乎总是更好的主意。

话虽如此,如果表单是在单独的线程中运行,您应该可以使用BeginInvoke来关闭它:

 otherForm.BeginInvoke(new Action(() => otherForm.Close()));

编辑:

在您的情况下,您需要保存实例:

Form2 otherForm;
public void FormThread()
{       
    otherForm = new Form2();
    Application.Run(otherForm);
}

private void button1_Click(object sender, EventArgs e)
{
    Thread t = new Thread(new ThreadStart(FormThread));
    t.SetApartmentState(ApartmentState.STA); // THIS IS REQUIRED!
    t.Start();
}

private void button2_Click(object sender, EventArgs e)
{
    //Need to close Form2 from here.
    if (otherForm != null)
    {
       otherForm.BeginInvoke(new Action( () => otherForm.Close() ));
       otherForm = null;
    }
}