0

I am writing a small application for reminders. For this, I got great help from a similar question and answer on Stack Overflow. I used the code mentioned by Thunder from here.

The relevant code is:

private void Form1_Load(object sender, EventArgs e)
    {
        System.Threading.TimerCallback callback = new            System.Threading.TimerCallback(ProcessTimerEvent);
        var dt =    new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day   , 10, 0, 0);

        if (DateTime.Now < dt)
        {
            var timer = new System.Threading.Timer(callback, null, dt - DateTime.Now, TimeSpan.FromHours(24));
        this.Hide(); // This line works... Form hides itself
        }

    }

    private void ProcessTimerEvent(object obj)
    {
        //MessageBox.Show("Hi Its Time");
        this.Show();  //This line does not work. Form gets disposed off instead of show
    }

My problem: I get everything as mentioned in that answer (including MessageBox). However, if I try to hide the form when a callback is made and show it once again instead of MessageBox.Show("Hi Its Time") it does not work. See my comments on each line. I don't understand why the form gets disposed.

this.Visible() // does not work and disposed off the same way

Also tried to move the form out of screen by changing its location property. On return, bring back to its original location but this also does not work. What can I do to hide & show the form on return ?

halfer
  • 19,824
  • 17
  • 99
  • 186
Anand
  • 173
  • 2
  • 9

2 Answers2

1

I believe you're having a cross thread issue. Your callback should look like this:

private void ProcessTimerEvent(object obj)
{
    if (this.InvokeRequired)
    {
        this.Invoke(new Action<object>(this.ProcessTimerEvent), obj);
    }
    else
    {
         this.Show();
    }
}
Francois Nel
  • 1,662
  • 2
  • 19
  • 29
0

I just checked and found that your code is getting this error:

Cross-thread operation not valid: Control 'Form1' accessed from a thread other than the thread it was created on.

You just have to change ProcessTimerEvent function to this:

if (this.InvokeRequired)
{
    this.BeginInvoke(new Action<object>(ProcessTimerEvent), obj);

    // To wait for the thread to complete before continuing.
    this.Invoke(new Action<object>(ProcessTimerEvent), obj);
}
else
{
    this.Show();
}
Vishal Suthar
  • 17,013
  • 3
  • 59
  • 105
  • Why do you suggest a double invoke? Your comment of "To wait for the thread to complete before continuing." before the Invoke call is not correct. – Francois Nel Sep 10 '12 at 07:35