我的目标
我想要一个主处理线程(非 GUI),并且能够根据需要在自己的后台线程中分离 GUI,并让我的主非 GUI 线程继续工作。换句话说,我希望我的主要非 GUI 线程成为 GUI 线程的所有者,反之亦然。我不确定这甚至可以使用 Windows 窗体(?)
背景
我有一个基于组件的系统,其中控制器动态加载程序集并实例化和运行实现IComponent
具有单个方法的通用接口的类DoStuff()
。
加载哪些组件是通过 xml 配置文件和添加包含不同实现的新程序集来配置的IComponent
。组件向主应用程序提供实用功能。虽然主程序正在做它的事情,例如控制核电站,但组件可能正在执行实用任务(在它们自己的线程中),例如清理数据库,发送电子邮件,在打印机上打印有趣的笑话,你有什么。我想要的是让这些组件中的一个能够显示 GUI,例如带有所述电子邮件发送组件的状态信息。
整个系统的生命周期是这样的
- 应用程序启动。
- 检查配置文件以加载要加载的组件。加载它们。
- 对于每个组件,运行
DoStuff()
以对其进行初始化,并使其在自己的线程中过上自己的生活。 - 继续做主要的应用程序,永远的工作之王。
如果组件在DoStuff()
. 它只是停止,直到 GUI 关闭。直到关闭 GUI,程序才会进入第 4 点。
如果允许这些组件启动它们自己的 Windows 窗体 GUI,那就太好了。
问题
当组件尝试在其中启动 GUI 时DoStuff()
(确切的代码行是组件运行时Application.Run(theForm)
),组件以及因此我们的系统在该行“挂起”,Application.Run()
直到 GUI 关闭。好吧,正如预期的那样,刚刚启动的 GUI 工作正常。
组件示例。一个与 GUI 无关,而第二个打开一个可爱的窗口,里面有粉红色的毛茸茸的兔子。
public class MyComponent1: IComponent
{
public string DoStuff(...) { // write something to the database }
}
public class MyComponent2: IComponent
{
public void DoStuff()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form());
// I want the thread to immediately return after the GUI
// is fired up, so that my main thread can continue to work.
}
}
我试过这个没有运气。即使我尝试在它自己的线程中启动 GUI,执行也会停止,直到 GUI 关闭。
public void DoStuff()
{
new Thread(ThreadedInitialize).Start()
}
private void ThreadedInitialize()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form());
}
是否可以分拆 GUI 并在之后返回Application.Run()
?