为什么我的表格这么害羞?
编辑2
好的,根据下面答案的建议,我消除了线程方法,现在我的程序如下所示: program.cs
static void Main(){
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
FrmWWCShell FrmWWCShell = null;
var splash = new FrmSplash();
splash.SplashFormInitialized += delegate
{
FrmWWCShell = new FrmWWCShell();
splash.Close();
};
Application.Run(splash);
Application.Run(FrmWWCShell);
}
和 FrmSplash.cs 像这样:
public partial class FrmSplash : Form
{
public FrmSplash()
{
InitializeComponent();
}
protected override void OnLoad(EventArgs e)
{
splashTimer.Interval = 1;
splashTimer.Tick +=
delegate { if (SplashFormInitialized != null) SplashFormInitialized(this, EventArgs.Empty); };
splashTimer.Enabled = true;
}
public event EventHandler SplashFormInitialized;
}
问题是它现在根本不起作用。 闪屏突然弹出一瞬间,品牌进度条甚至从未初始化,然后在我等待 10 秒 dll 和主窗体出现时消失,而我却盯着什么都没有。...给
我严重的颜色现在很困惑!
原帖--> 作为参考,
我实现了一个应用程序加载初始屏幕,该屏幕在加载所有 dll 并且正在“绘制”表单时在单独的线程上运行。 这按预期工作。 奇怪的是,现在当 Splash 表单退出时,如果还有其他打开的内容(例如 Outlook),它会将我的主表单发送到后面。 我在 Program.cs 中启动线程,
static class Program
{
public static Thread splashThread;
[STAThread]
static void Main()
{
splashThread = new Thread(doSplash);
splashThread.Start();
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new FrmWWCShell());
}
private static void doSplash()
{
var splashForm = new FrmSplash();
splashForm.ShowDialog();
}
}
然后在触发 FrmSearch_Shown 事件后结束它。
private void FrmSearch_Shown(object sender, EventArgs e)
{
Program.splashThread.Abort();
this.Show();
this.BringToFront();
}
正如您所看到的,我尝试在 FrmSearch 上调用 Show() 和/或 BringToFront(),但它仍然“跳”到后面。
我错过了什么?
我还能尝试什么?
我这样做是否太无知了,以至于是我的流程导致了这种情况?
我应该申请提前退休吗?
感谢您的任何见解!
编辑 1
我尝试将主窗体上的 TopMost 属性设置为 TRUE。 这可以防止我的表单隐藏,但也可以防止用户查看任何其他应用程序。 看来我有点自恋了……
EDIT 2
Okay, based on the advice on the answers below I eliminated my thread approach and now my program looks like this:
program.cs
static void Main(){
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
FrmWWCShell FrmWWCShell = null;
var splash = new FrmSplash();
splash.SplashFormInitialized += delegate
{
FrmWWCShell = new FrmWWCShell();
splash.Close();
};
Application.Run(splash);
Application.Run(FrmWWCShell);
}
And FrmSplash.cs like this:
public partial class FrmSplash : Form
{
public FrmSplash()
{
InitializeComponent();
}
protected override void OnLoad(EventArgs e)
{
splashTimer.Interval = 1;
splashTimer.Tick +=
delegate { if (SplashFormInitialized != null) SplashFormInitialized(this, EventArgs.Empty); };
splashTimer.Enabled = true;
}
public event EventHandler SplashFormInitialized;
}
The problem is that it doesn't work at all now. The splash screen pops up for a split second, the marque progress bar never even initializes, and then disappears while I wait the 10 secs for the dll's and Main Form to show up while staring at nothing....
Color me severely confused now!
ORIGINAL POST--> for reference
I implemented a App Loading splash screen that operates on a seperate thread while all of the dll's are loading and the form is getting "Painted." That works as expected. What is strange is that now when the Splash form exits it sends my main Form to the back, if there is anything else open(i.e. Outlook). I start the thread in Program.cs,
static class Program
{
public static Thread splashThread;
[STAThread]
static void Main()
{
splashThread = new Thread(doSplash);
splashThread.Start();
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new FrmWWCShell());
}
private static void doSplash()
{
var splashForm = new FrmSplash();
splashForm.ShowDialog();
}
}
And then I end it once my FrmSearch_Shown event is fired.
private void FrmSearch_Shown(object sender, EventArgs e)
{
Program.splashThread.Abort();
this.Show();
this.BringToFront();
}
I, as you can see, have tried calling a Show() and/or BringToFront() on FrmSearch and it still "jumps" to the back.
What am I missing?
What else can I try?
Am I doing this so horribly ignorant that it is my process that is causing this?
Should I file for early retirement?
Thanks for any insight!
EDIT 1
I tried setting the TopMost Property on my Main Form to TRUE. This keeps my form from hiding but it also keeps the user from looking at any other app. Seems a little narcissistic of me...
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
首先,UI 工作在主应用程序线程上完成非常重要。 实际上,我有点惊讶的是,通过在后台线程上显示启动屏幕,您并没有遇到更严重的错误。
这是我使用过的一种技术:
在初始表单而不是“真实”表单上使用 Application.Run。
在您的启动表单中,有一个初始化事件:
创建一个在一毫秒内触发的计时器,并触发该事件。
然后在您的应用程序运行方法中,您可以加载真实表单,然后关闭启动表单并在真实表单上执行 Application.Run
启动可能包括:
First of all, it's very important that UI work is done on the primary application thread. I'm actually kind of surprised that you're not getting more serious errors already by showing the splash screen on a background thread.
Here's a technique I've used:
Use Application.Run on your splash form rather than your "real" form.
In your splash form, have an initialized event:
Create a timer that fires in one millisecond, and triggers that event.
Then in your application run method you can load your real form, then close your splash form and do an Application.Run on the real form
The splash might include:
尝试在演出结束后立即调用 Application.DoEvents() 。
警告:不要经常调用 DoEvents,但这是其中之一。
编辑:克莱德注意到了一些我没有注意到的事情:你正在讨论这个。 不要在另一个线程上运行任何 UI。 取出线程,留在Application.DoEvents()中。
Try calling Application.DoEvents() right after show.
Warning: do not call DoEvents very often, but this is one of those time.
EDIT: Clyde noticed something I did not: you are threading this. Don't run any UI on another thread. Take out the thread, leave in the Application.DoEvents().