在不同的线程上使用Application.Run()

请看下面的代码:

var splashForm = new SplashForm(); m_Thread = new Thread( () => System.Windows.Forms.Application.Run( splashForm ) ) m_Thread.Start(); // Do some initialization // ... // the following method just invokes `Close()` on the right thread splashForm.Shutdown(); // Loop until the thread is no longer alive // ... System.Windows.Forms.Application.Run( mainForm ); 

它看起来好像一切正​​常:首先我看到了闪屏,后来主变形开始了。 但不知怎的,我得到了奇怪的错误,例如:图形元素(无尽的ProgressBar)没有正确显示。
编辑 :我有两个进度条,一个在启动画面上,在主窗体上。 他们都在无尽模式中表现出相同(错误)的行为:没有进步,只有纯粹的背景。 /编辑
在我看来,这是由于Application.Run()在不同的线程上的调用。 在启动splashscreen之前调用mainForm的任何函数/属性可以消除这种错误 – 例如

 mainForm.Text = mainForm.Text; 

任何人都可以请确认此代码可能会导致问题 – 或者它应该表现良好,我必须在其他地方寻找错误?
我已经找过了flashscreen实现,我知道它可以以不同的方式完成。 但我有兴趣了解这个实现及其可能存在的问题。 谢谢!

SplashForm显示的线程需要有一个Windows消息泵才能处理每个窗口/控件产生的消息。 为此,您需要使该线程成为STA线程。 尝试启动线程之前调用SetApartmentState

我将Application.Run()执行的线程上创建表单。

 SplashForm splashForm = null; m_Thread = new Thread(delegate { splashForm = new SplashForm(); System.Windows.Forms.Application.Run(splashForm); }); m_Thread.Start(); 

但真正需要做的是通过InvokeRequired和BeginInvoke技术访问它。 点击这里

你正在做的事情没有任何重大错误。 我发现这个方法很有趣,可以用来制作一个演示,但它运行正常。 我还可以说kek444的答案不是问题。 在主线程上创建SplahForm没有任何区别。

所以我猜这是你控制Progressbar的方式,或者更一般地说你是如何在2个线程之间进行通信。

天哪,我找到了答案:
Application.EnableVisualStyles(); 如果我的mainForm(为什么?)在ctor中被调用。 必须在创建任何控件之前调用它。 将它移动到static Main()就可以了。 无尽的(ProgressBarStyle.Marquee)进度条需要视觉样式。
现在这个splashscreen解决方案可以正常工作。