internal bool ExecuteInBackgroundAndCallback(Func<object> task, Action<bool, object> resultHandler, string taskDescription, bool timeout)
{
// make sure only one background task can be executed at a time
if (!IsBusy && Monitor.TryEnter(this))
{
try
{
IsBusy = true;
abortedByUser = false;
_CurrentResultHandler = resultHandler;
_CurrentTaskDescription = taskDescription;
_CurrentResult = null;
_CurrentError = null;
// while this is null the task has not finished (or later on timeout),
// true indicates successfull completion and false error
_CurrentTaskSuccess = null;
// init and show the wait cursor in MediaPortal
GUIWaitCursor.Init();
GUIWaitCursor.Show();
backgroundThread = new Thread(delegate()
{
try
{
_CurrentResult = task.Invoke();
_CurrentTaskSuccess = true;
}
catch (ThreadAbortException)
{
if (!abortedByUser)
TraktLogger.Info("Timeout waiting for results");
Thread.ResetAbort();
}
catch (Exception threadException)
{
_CurrentError = threadException;
TraktLogger.Warning(threadException.ToString());
_CurrentTaskSuccess = false;
}
timeoutTimer.Stop();
// hide the wait cursor
GUIWaitCursor.Hide();
// execute the ResultHandler on the Main Thread
GUIWindowManager.SendThreadCallbackAndWait((p1, p2, o) =>
{
ExecuteTaskResultHandler();
return 0;
}, 0, 0, null);
})
{
Name = "Trakt",
IsBackground = true
};
// disable timeout when debugging
if (timeout && !System.Diagnostics.Debugger.IsAttached)
timeoutTimer.Start();
// start background task
backgroundThread.Start();
// successfully started the background task
return true;
}
catch (Exception ex)
{
TraktLogger.Error(ex.Message);
IsBusy = false;
_CurrentResultHandler = null;
// hide the wait cursor
GUIWaitCursor.Hide();
// could not start the background task
return false;
}
}
else
{
TraktLogger.Warning("Another thread tried to execute a task in background");
return false;
}
}