Threading and dtSearch
Written by Ian Elliot   
Wednesday, 17 August 2011
Article Index
Threading and dtSearch
Cross threading

 

All you have to do next is fill out the details of the methods that you want to use. You also have to remove the NotImplementedException from some of the ones you don't want to use. In fact a good start it to replace all of the throw new NotImplementedException statements by return except for the CheckForAbort method which returns one of:

AbortValue.Continue
AbortValue.Cancel
AbortValue.CancelImmediately

You can use this to check to see if the user has clicked an abort button and stop the search acordingly.

For now just replace the method with:

public AbortValue CheckForAbort()
{
return AbortValue.Continue;
}

When each of the methods is called is obvious from their names and you don't have to use any that you don't need. Let's look at how we could use the ProgressUpdate method to keep the user informed of the situation. Let's simply display the type of update being performed:

public void OnProgressUpdate(
SearchProgressInfo info)
{
Console.WriteLine(info.UpdateType);
}

Now all we have to do is create an instance of our class and start the search:

SearchStatus SStatus = new SearchStatus();
SJob1.StatusHandler = SStatus;
SJob1.Execute();

Now the search starts and the OnProgressUpdate is called as it progresses. Notice that in this case we are using the UI thread to run the search and print the result on the console.

If you want to make the feedback more user friendly you could pass in a ProgressBar to be updated by the OnProgressUpdate method. First we need to modify the constructor:

private ProgressBar _PB;
public SearchStatus(ProgressBar PB)
{
_PB = PB;
}

and then the OnProgressUpdate method:

public void OnProgressUpdate
(SearchProgressInfo info)
{
 _PB.PerformStep();
if (_PB.Value >= _PB.Maximum)
  _PB.Value = _PB.Minimum;
}

Now if you run the same program you will see the ProgressBar update as the search progresses.

SearchStatus SStatus = 
new SearchStatus(progressBar1);
SJob1.StatusHandler = SStatus;
SJob1.Execute();

Cross threading

There is a small problem here. We are still hogging the UI Thread. It would be better to use ExecuteInThread to run the search on another thread. However this leads to another small problem - cross threading.

If you keep the OnProgressUpdate method unchanged and simply use

SJob1.ExecuteInThread();

The program will crash with an error message

Cross-thread operation not valid: Control 'progressBar1' accessed from a thread other than the thread it was created on.

The problem is that all of the method of the Status object are run on the thread that is used for the search and .NET enforces the rule that only the thread that created a UI control can access it.

The solution to the problem sounds more involved than it is. All we have to do is to use the control's Invoke method to run a method using the thread that created the control i.e. the UI thread in this case.

Using the Invoke method is generally complicated by the need to create a delegate but in C# 4 this is very much easier because we can make use of lambda expressions. So to make the new version work we simply change the OnProgressUpdate to read:

public void OnProgressUpdate(
SearchProgressInfo info)
{
_PB.Invoke(new Action(() =>
{
_PB.PerformStep();
if (_PB.Value >= _PB.Maximum)
 _PB.Value = _PB.Minimum;
}
));
}

The Invoke method runs the code that updates the progress bar on the original UI thread.

You can handle similar cross threading problems using the same sort of technique and decouple the search thread from the UI thread, so keeping everything responsive and under the control of the user - which is what makes a good application.

Building an application around dtSearch is also a matter of what you do with the search results. You can process these as they are produced using the same sorts of techniques discussed in this article. Then there are many other features that we haven't even touched upon - CDsearch, Websearch and setting up the web Spider to name just three, but these are other stories.

To try dtSearch for yourself download the 30-day evaluation from dtsearch.com.

Further reading

Getting started with dtSearch

The Invoke pattern

 

Banner



Last Updated ( Friday, 19 August 2011 )