/// <summary> /// Monitors the progress (via a separate monitor thread) of a blocking /// API call that is about to be run on the main thread. The query to /// get a handle to the blocking task will not be performed for half a /// second, giving the caller time to initiate the blocking task after /// calling this method. /// Note: When the blocking task returns, the caller should immediately /// call the TaskComplete method to wait for the monitor thread to /// complete. Otherwise progress updates can be intermingled with log /// output. /// </summary> public void MonitorBlockingTask(IOutput output) { TaskInfo task = null; _progressMonitor = new ProgressMonitor(output); _progressMonitor.MonitorProgressAsync(delegate(bool cancel, out bool isRunning) { int progress; if (task == null) { // First time through (half a second later), so get task // which should now be running task = GetRunningTask(); if (task != null && output.Operation == null) { output.Operation = task.TaskType.ToString(); } } if (task != null) { // Check on the task progress progress = GetTaskProgress(task); isRunning = task.TaskStatus == ETaskStatus.Running; if (cancel && isRunning) { CancelRunningTask(task.TaskId); } } else { // No task is running - either it finished already, or there // was an error launching it; either way, indicate we are done isRunning = false; progress = 100; } return(progress); }); }