I have this code in a button click
private async void btnStart_Click(object sender, EventArgs e)
{
Msg.Clear();
stopWatch.Reset();
timer.Start();
stopWatch.Start();
lblTime.Text = stopWatch.Elapsed.TotalSeconds.ToString("#");
progressBar.MarqueeAnimationSpeed = 30;
try
{
await Task.Factory.StartNew(() =>
{
try
{
Reprocess();
}
catch (Exception ex)
{
Msg.Add(new clsMSG(ex.Message, "Error", DateTime.Now));
timer.Stop();
stopWatch.Stop();
throw;
}
});
}
catch
{
throw;
}
}
and this on the Reprocess method
private void Reprocess()
{
try
{
clsReprocess reprocess = new clsReprocess(tbBD.Text, dtpStart.Value, 50000);
reprocess.Start(reprocess.BD);
}
catch
{
throw;
}
}
when the Reprocess method fails, the Task goes to catch, but the throw fails (the throw inside catch (Exception ex)) and the UI blocks until the reprocess.Start method is completed. I have two questions:
- First: How can I catch the throw in the catch of my button?
- Second: How can I prevent the UI blocks?
I hope you can understand me, sorry for my bad english.
You should not use
Task.Factory.StartNew
;Task.Run
is both safer and shorter to write.Also, you can only access UI controls from the UI thread. This may be the cause of the problems you're seeing, if
Msg
is data-bound to the UI. Even if it's not, you don't want to access unprotected collections (e.g.,List<clsMSG>
) from multiple threads.Applying both of these guidelines reduces the code to:
If
Reprocess
throws an exception, that exception will be placed on the task returned fromTask.Run
. When your codeawait
s that task, that exception is re-raised and caught in thecatch
. At the end of thecatch
, the code will re-raise that exception (throw;
).