0

I've been scratching my head on this one for a while now and despite looking for solutions, im not quite understanding the implementations (several answers on stack overflow have already been looked at)

My program loads a splash page when it is opened, during which it checks for a database connection. If there is a connection, the splash page closes and the main form loads, otherwise it provides an error message then closes completely.

public partial class StartupSplash : Form
{

    ThreadStart th;
    Thread thread;

    public StartupSplash()
    {
        InitializeComponent();

        th = new ThreadStart(DbAvaliable);
        thread = new Thread(th);
        thread.Start();

    }

    private void DbAvaliable()
    {

        Boolean result = false;

        using (var connectiontest = new SqlConnection("myConnString"))
            try
            {
                connectiontest.Open();
                result = true;
            }
            catch (Exception ex)
            {
                result = false;
            }

        if (result)
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainWindow());

        }
        else
        {
            MessageBox.Show("Unable to establish database connection. Please check your data connection and try again.");
        }
    }
}

I understand that I can't simply call this.Close() due to cross thread issues. I've read something about invoking methods, but im not too clear how to achieve the result above.

Initially I tried to use form load/shown events instead of alternate threads, but the image on the forms failed to load until after the messagebox had shown the error (rather than displaying, then running the connection check)

Takarii
  • 1,612
  • 2
  • 18
  • 29
  • Could you do the db in a task that returns true or false for connection and then you just wait on it and close application or continue depending on result? – Jacobr365 Jul 27 '16 at 13:54
  • 2
    It is buggy and is going to cause you a lot of grief. The .NET Framework already has [excellent support](http://stackoverflow.com/a/393870/17034) for splash screens, rather best to use it. – Hans Passant Jul 27 '16 at 13:57

2 Answers2

0

Could you set up an event to fire on Form2 with the results of the db check? Subscribe to the event on Form1 and tell it to close if the conditions warrant.

Not sure if it would work or not, but something like:

public Form2 : Form
{
    public delegate void DbCheckHandler(object sender, DbEventArgs e);
    public event DbCheckHandler DbCheckComplete;

    //check the db
    DbCheckComplete(this, new DbEventArgs { ShouldClose = true; });

}

public Form1 : Form
{
    Form2 form2 = new Form2();
    form2.DbCheckComplete += new DbCheckHandler(CheckDbResult);
    form2.Show();

    private void CheckDbResult(object sender, DbEventArgs e)
    {
        if(e.ShouldClose)
        {
            this.Close();
        }

    }
}
gev125
  • 152
  • 3
  • 9
0

With some help from previous answers posted by Hans Passant (here and here), My solution was as follows:

static class Program
{
    /// <summary>
    /// The main entry point for the application.
    /// </summary>
    [STAThread]
    static void Main(string[] args)
    {   
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        new MyApp().Run(args);

    }

class MyApp : WindowsFormsApplicationBase
{
    protected override void OnCreateSplashScreen()
    {
        this.SplashScreen = new StartupSplash();
    }

    protected override void OnCreateMainForm()
    {
        Boolean result = false;
        using (var connectiontest = new SqlConnection("myConnectionString"))
            try
            {
                connectiontest.Open();
                result = true;
            }
            catch (Exception ex)
            {
                result = false;
            }
        // pause not needed while checking for db connection as that takes its own amount of time to complete.


        if (result)
        {
            System.Threading.Thread.Sleep(3000); //pause moved here to give the splash some time on screen if db connection available
            this.MainForm = new MainWindow();
        }
        else
        {
            MessageBox.Show("Unable to connect to the database");

            Environment.Exit(1); // shuts down the program if database connection not avaliable.

        }

    }


}
Community
  • 1
  • 1
Takarii
  • 1,612
  • 2
  • 18
  • 29