我正在使用Here的启动画面。我喜欢它有多简单。但问题是,在我点击之前,启动画面不会消失。在IDE中运行时,它可以正常工作。有任何想法吗?我在这里附上代码,但由于某种原因它没有正确插入。
private System.Windows.Forms.Timer timer1;
//private Splash sp=null;
public Form1()
{
InitializeComponent();
Thread th = new Thread(new ThreadStart(DoSplash));
//th.ApartmentState = ApartmentState.STA;
//th.IsBackground=true;
th.Start();
Thread.Sleep(3000);
th.Abort();
Thread.Sleep(1000);
}
private void DoSplash()
{
Splash sp = new Splash();
sp.ShowDialog();
}
private void timer1_Tick(object sender, System.EventArgs e)
{
// sp.Close();
}
答案 0 :(得分:6)
首先,使用Thread.Abort完成该页面上的启动画面的方式是不正确的做事方式。
永远不要致电Thread.Abort,除非您正在关闭线程所在的AppDomain。
让我重申强调。 您应该致电Thread.Abort的唯一时间是当您对Thread.Abort了解得足够多以及知道您永远不应该打电话时的行为方式。
在StackOverflow上查看另一个问题:Multi-Threaded splash screen in c#?。
如果您想保留现有的解决方案,可以采用更好的方法将计时器放入启动画面,将计时器设置为您希望启动画面停留在屏幕上的时间,然后调用{{3}在其Tick事件处理程序中。
在同一地点,我只需关闭原始线程,然后移除其他线路。
换句话说,从该页面的第一个代码块开始,我将保留这两行:
Thread th = new Thread(new ThreadStart(DoSplash));
th.Start();
在窗体上将那个计时器与表单自动关闭结合起来,并且你的形状比试图掌握Thread.Abort更好。
你不应该打电话。
答案 1 :(得分:2)
DoSplash可能应该调用sp.Show()
而不是sp.ShowDialog()
但是调用Sleep(x000)构成主线程以显示启动画面效率不高,并且应该保留Thread.Abort()以便更好地使用。
更好的方法是使用Timer关闭SplashForm并设置最小延迟。在启动时,你可以Show()和Update()SplahForm并继续加载东西。在MainForm完成初始化并进入EventLoop之前,计时器事件不会触发。不需要线程,也不必涉及MainForm。
只是为了给你一个MessageLoop驱动的SplashForm的主要成分:
public partial class SplashForm : Form
{
// default stuff
public static void Splash()
{
var s = new SplashForm();
s.Show();
s.Update();// force paint
}
private void SplashForm_Load(object sender, EventArgs e)
{
Timer t = new Timer();
t.Interval = 1; // wait for EventLoop
t.Tick += GoAway;
t.Enabled = true;
}
private void GoAway(object sender, EventArgs e)
{
this.Close();
}
}
然后,在Program.cs中,
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
SplashForm.Splash();
Application.Run(new MainForm());
答案 2 :(得分:1)
这是一个丑陋的实施。你应该看看this SO thread。这描述了如何使用C#中的VisualBasic.NET命名空间和OnCreateSplashScreen方法来实现更清晰的初始屏幕实现。