【问题标题】:C# winforms startup (Splash) form not hidingC# winforms 启动(Splash)表单不隐藏
【发布时间】:2010-10-05 09:01:49
【问题描述】:

我有一个 winforms 应用程序,我在其中使用 2 个表单来显示所有必要的控件。第一个表单是一个闪屏,它告诉用户它正在加载等。所以我使用以下代码:

Application.Run( new SplashForm() );

一旦应用程序完成加载,我希望 SplashForm 隐藏或将我发送到后面并显示主要来源。我目前正在使用以下内容:

private void showMainForm()
{
    this.Hide();
    this.SendToBack();

    // Show the GUI
    mainForm.Show();
    mainForm.BringToFront();
}

我看到的是 MainForm 已显示,但 SplashForm 仍然在“顶部”可见。我目前正在做的是单击 MainForm 以手动将其置于前面。关于为什么会发生这种情况的任何想法?

【问题讨论】:

    标签: c# winforms show-hide


    【解决方案1】:

    您可能只想关闭启动表单,而不是将其发送回。

    我在单独的线程上运行启动表单(这是 SplashForm 类):

    class SplashForm
    {
        //Delegate for cross thread call to close
        private delegate void CloseDelegate();
    
        //The type of form to be displayed as the splash screen.
        private static SplashForm splashForm;
    
        static public void ShowSplashScreen()
        {
            // Make sure it is only launched once.
    
            if (splashForm != null)
                return;
            Thread thread = new Thread(new ThreadStart(SplashForm.ShowForm));
            thread.IsBackground = true;
            thread.SetApartmentState(ApartmentState.STA);
            thread.Start();           
        }
    
        static private void ShowForm()
        {
            splashForm = new SplashForm();
            Application.Run(splashForm);
        }
    
        static public void CloseForm()
        {
            splashForm.Invoke(new CloseDelegate(SplashForm.CloseFormInternal));
        }
    
        static private void CloseFormInternal()
        {
            splashForm.Close();
            splashForm = null;
        }
    ...
    }
    

    主程序功能如下:

    [STAThread]
    static void Main(string[] args)
    {
        SplashForm.ShowSplashScreen();
        MainForm mainForm = new MainForm(); //this takes ages
        SplashForm.CloseForm();
        Application.Run(mainForm);
    }
    

    【讨论】:

    • 我只将它用于 WinForms,对不起。
    • 我在你的类中定义了一个像“frmSplash splashForm”这样的变量,但是我得到了一些错误,比如“非静态字段、方法或属性需要对象引用”来定义变量。我怎么能从你的课上使用?
    • 我遇到了一个奇怪的问题,我的初始屏幕不在单独的线程中,但在 Win7 中运行良好,但在 XP 中,尽管使用了 BringToFront(),但它仍然在其他东西之下。我添加了上面的代码以将其放入自己的线程中,现在它的行为符合预期!所以,谢谢。
    【解决方案2】:

    这对于防止初始屏幕在关闭后窃取焦点并将主窗体推到后台至关重要:

    protected override bool ShowWithoutActivation {
        get { return true; }
    }
    

    将此添加到您的初始表单类。

    【讨论】:

    • 感谢您分享这些有用的信息:)
    【解决方案3】:

    如果我理解正确,您应该只在主窗体上使用 Application.Run。所以要么先显示你的飞溅,只需使用类似的东西:

    using(MySplash form = new MySplash())
       form.ShowDialog();
    

    然后随时在 MySplash 中手动关闭它。

    或者在你的主窗体 Load 事件处理程序中显示它,然后等待它关闭或其他任何东西,直到你让 Load 方法完成。 (可能在显示之前将 Visible 设置为 false,然后再设置为 true。

    【讨论】:

      【解决方案4】:

      我认为这可能是我当前设计中的设计缺陷!

      我认为实现我需要的最佳方式是从 MainForm 控制所有内容。所以我可以使用:

      Application.Run(new MainForm());
      

      这将负责显示/更新/隐藏 SplashScreen。通过这种方式,我可以对 MainForm 管理的系统的其余部分进行必要的复杂操作。

      【讨论】:

        猜你喜欢
        • 2010-10-06
        • 1970-01-01
        • 1970-01-01
        • 2017-12-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多