When I cancel and dispose of my background worker, despite it disappearing from the VS threads list it continues to report busy to my application which is waiting for it to close. Also my RunWorkerCompleted event is never raised.
Debugging shows that the code is exited with no further pending execution that I can see.
If I remove the .IsBusy check, VS reports that "This BackgroundWorker is currently busy and cannot run multiple tasks concurrently"
I cannot understand why the thread which is no longer listed in VS continues to operate after closing.
private void UpdateTimeLine()
{
txtb_timeline.Text = "Updating...";
startTimelineUpdater.DoWork += new DoWorkEventHandler(startTimelineUpdater_DoWork);
startTimelineUpdater.RunWorkerAsync("hometimeline");
startTimelineUpdater.WorkerReportsProgress = true;
startTimelineUpdater.ProgressChanged += new ProgressChangedEventHandler
(startTimelineUpdater_ProgressChanged);
startTimelineUpdater.WorkerSupportsCancellation = true;
}
void startTimelineUpdater_DoWork(object sender, DoWorkEventArgs e)
{
//begin the thread to maintain updates of SQL
beginRegUpdateTimeline.DoWork += new DoWorkEventHandler(beginRegUpdateTimeline_DoWork);
beginRegUpdateTimeline.RunWorkerAsync();
beginRegUpdateTimeline.WorkerSupportsCancellation = true;
while (true)
{
List<string[]> sqlset;
Xtweet getSQL = new Xtweet();
if(e.Argument.ToString() == "hometimeline")
{
sqlset = getSQL.CollectLocalTimelineSql();
}
else
{
sqlset = getSQL.CollectLocalTimelineSql(Int64.Parse(e.Argument.ToString()));
}
int i = 0;
while (i < 10)
{
foreach (var stringse in sqlset)
{
StringBuilder sb = new StringBuilder();
sb.Append(stringse[0]);
sb.Append(": ");
sb.Append(stringse[1]);
sb.Append(" @ ");
sb.Append(stringse[2]);
sb.Append("\n");
BackgroundWorker bkgwk = sender as BackgroundWorker;
bkgwk.ReportProgress(0, sb.ToString());
Thread.Sleep(1000);
i++;
if(startTimelineUpdater.CancellationPending)
{
e.Cancel = true;
startTimelineUpdater.Dispose();
break;
}
}
if (e.Cancel == true)
{
break;
}
}
if (e.Cancel == true)
{
break;
}
}
}
/// <summary>
/// Handles the DoWork event of the beginRegUpdateTimeline control.
/// Updates the timeline sql on a regular basis
/// </summary>
/// <param name="sender">The source of the event.</param>
/// <param name="e">The <see cref="System.ComponentModel.DoWorkEventArgs"/> instance containing the event data.</param>
void beginRegUpdateTimeline_DoWork(object sender, DoWorkEventArgs e)
{
while (true)
{
//update time in seconds
int secs = 10;
Xtweet.PreSqlDataCollection(null,null);
Thread.Sleep(secs*1000);
if(beginRegUpdateTimeline.CancellationPending)
{
e.Cancel = true;
beginRegUpdateTimeline.Dispose();
break;
}
}
}
private void startTimelineUpdater_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
txtb_timeline.Text = e.UserState.ToString();
}