Don't like ads? PRO users don't see any ads ;-)
Guest

Untitled

By: a guest on Apr 25th, 2012  |  syntax: None  |  size: 3.30 KB  |  hits: 8  |  expires: Never
download  |  raw  |  embed  |  report abuse  |  print
Text below is selected. Please press Ctrl+C to copy to your clipboard. (⌘+C on Mac)
  1. stop an asynchronous operation to start a replacing one
  2. Task currentTask;
  3. CancellationTokenSource cancelTokenSource;
  4. CancellationToken cancelToken;
  5. Task newTask;
  6. CancellationTokenSource newCancelTokenSource;
  7. CancellationToken newCancelToken;
  8.  
  9. public Form1()
  10. {
  11.     InitializeComponent();
  12. }
  13.  
  14. private void button1_Click(object sender, EventArgs e)
  15. {
  16.     if(currentTask != null && currentTask.Status == TaskStatus.Running)
  17.     {
  18.         //Cancel the running task
  19.         cancelTokenSource.Cancel();
  20.         //Prepare a new Task to be triggered when the other cancels
  21.         //You could store new tasks/tokens in a dictionary if you wanted,also
  22.         //A new cancel token is always needed since the old stays cancelled
  23.         newCancelTokenSource = new CancellationTokenSource();
  24.         newCancelToken = newCancelTokenSource.Token;
  25.         newTask = new Task(()=>LongRunningTask(), newCancelToken);
  26.  
  27.         //Continue that deals with both cancel and completion
  28.         //There is a different way to deal with this below, also
  29.         newTask.ContinueWith((previousTask)=>
  30.         {
  31.             if(previousTask.Status == TaskStatus.Cancelled)
  32.             {
  33.                 label1.Text = "New Task Cancelled, Another New Starting";
  34.                 BeginNewTask();
  35.             }
  36.             else
  37.                 label1.Text = "New Task Ran To Completion";
  38.         },
  39.         //If cancelled token is passed, it will autoskip the continue
  40.         new CancellationTokenSource().Token, TaskContinuationOptions.None,
  41.         //This is to auto invoke the UI thread
  42.         TaskScheduler.FromCurrentSynchronizationContext());
  43.     }
  44.     else
  45.     {
  46.         cancelTokenSource = new CancellationTokenSource();
  47.         cancelToken = cancelTokenSource.Token;
  48.         //Start a fresh task since none running
  49.         currentTask = Task.Factory.StartNew(()=>LongRunningTask(),
  50.             cancelToken);
  51.  
  52.         //OnCancelContinue
  53.         currentTask.ContinueWith((previousTask)=>
  54.         {
  55.             label1.Text = "First Task Cancelled, New Starting";
  56.             BeginNewTask();
  57.         },
  58.         //If cancelled token is passed, it will autoskip the continue
  59.         new CancellationTokenSource().Token,
  60.         TaskContinuationOptions.OnlyOnCancelled,
  61.         //This is to auto invoke the UI thread
  62.         TaskScheduler.FromCurrentSynchronizationContext());
  63.  
  64.         //OnCompleteContinue
  65.         currentTask.ContinueWith((previousTask)=>
  66.         {
  67.             label1.Text = "First Task Ran To Completion";
  68.         },
  69.         //If cancelled token is passed, it will autoskip the continue
  70.         new CancellationTokenSource().Token,
  71.         TaskContinuationOptions.OnlyOnRanToCompletion,
  72.         //This is to auto invoke the UI thread
  73.         TaskScheduler.FromCurrentSynchronizationContext());
  74.     }
  75. }
  76.  
  77. private void LongRunningTask()
  78. {
  79.      for(int i = 0; i < 60; i++)
  80.      {
  81.          if(cancelToken.IsCancellationRequested)
  82.              cancelToken.ThrowIfCancellationRequested();
  83.          Thread.Sleep(1000);
  84.      }
  85. }
  86.  
  87. private void BeginNewTask()
  88. {
  89.     //Since the old task is cancelled, reset it with the new one
  90.     //Probably should do some error checks
  91.     currentTask = newTask;
  92.     cancelTokenSource = newCancelTokenSource;
  93.     cancelToken = newCancelToken;
  94.     //This is to make sure this task does not run on the UI thread
  95.     currentTask.Start(TaskScheduler.Default);
  96. }