Still celebrating National IT Professionals Day with 3 months of free Premium Membership. Use Code ITDAY17

x
?
Solved

How to subscribe to an event through a delegate

Posted on 2013-11-22
6
Medium Priority
?
328 Views
Last Modified: 2013-11-25
I'd like to assign an event to a delegate instead of assigning the event to the method directly.
The code example is below:

class FindPlace
{
    private delegate void QueryExecuteCompleted(object sender, QueryEventArgs args);

    private void CountyComboBox_SelectionChanged(
        object sender,
        SelectionChangedEventArgs selectionEvArgs)
    {        
        QueryTask queryTask;       
        string layerName;        
        QueryExecuteCompleted CountySelectionChanged_ExComp;        

        if (StateType == StateTypes.AbstractState)
        {        
            layerName = "TX Abstracts";
            CountySelectionChanged_ExComp =  qryCplt.AbstractQueryTask_ExecuteCompleted;          
        }
        else if (StateType == StateTypes.NonPlssState)
        {        
            layerName = "Districts"; 
            CountySelectionChanged_ExComp = qryCplt.DistrictQueryTask_ExecuteCompleted;            
        }
        else
        {     
            layerName = "PLSS Townships";
            CountySelectionChanged_ExComp = qryCplt.TownshipQueryTask_ExecuteCompleted;
        }

        queryTask = new QueryTask(layerName);           
        queryTask.ExecuteCompleted += CountySelectionChanged_ExComp;
        queryTask.ExecuteAsync(query); 
    }
}

Open in new window


That causes this error:
Cannot implicitly convert type FindPlace.QueryExecuteCompleted to System.EventHandler<QueryEventArgs>

The error occurs on this line:
queryTask.ExecuteCompleted += CountySelectionChanged_ExComp;

I can get the code to work if I do this:
//. . .
if (StateType == StateTypes.AbstractState)
{        
    layerName = "TX Abstracts";
    queryTask = new QueryTask(layerName);        
    queryTask.ExecuteCompleted = qryCplt.AbstractQueryTask_ExecuteCompleted;  }
//. . .

Open in new window


But I don't want to do that.
I'd rather prefer to have the method subscribe to the event indirectly through a delegate.
0
Comment
Question by:XTO
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
6 Comments
 
LVL 96

Expert Comment

by:Bob Learned
ID: 39671387
I don't see where the event is defined...
0
 
LVL 2

Accepted Solution

by:
Pavel_Kudishin earned 800 total points
ID: 39672777
Please replace
queryTask.ExecuteCompleted += CountySelectionChanged_ExComp;

Open in new window

with
queryTask.ExecuteCompleted += 
new EventHandler<QueryEventArgs>(CountySelectionChanged_ExComp);

Open in new window

0
 
LVL 27

Assisted Solution

by:MikeToole
MikeToole earned 800 total points
ID: 39672841
I'm not entirely certain, but here's my thoughts...
When assigned individually, it's the method that's getting added to the delegate.
However, the  statement ...
queryTask.ExecuteCompleted += CountySelectionChanged_ExComp;
... is trying to add a Delegate where a method is expected - which will work, I think, if they're the same delegate type, but not if they're different, even when they have the same signature.

Try explicitly extracting the first member of the invocation list from your local delegate:
queryTask.ExecuteCompleted += CountySelectionChanged_ExComp.GetInvocationList()[0];

Open in new window

0
Docker-Compose to Simplify Multi-Container Builds

Our veteran DevOps Author takes you through how to build a multi-container environment, managed with a single utility in order to simplify your deployments.

 
LVL 96

Expert Comment

by:Bob Learned
ID: 39673161
If you need to pass the fact that the query is completed to the caller, then you still need a public event, like this:

public event EventHandler<QueryEventArg>;

Open in new window

0
 

Author Comment

by:XTO
ID: 39673330
Thanks all.

re: Pavel,
I will try the
+= new EventHandler<QueryEventArgs>(CountySelectionChanged_ExComp);
when I get back to work tomorrow.
Hopefully the QueryTask object event handler, ExecuteCompleted, will be able to recognize the delegate as pointing to the method to execute such that the QueryTask object's ExecuteAsync method will trigger it.

re:
I will try the
+= CountySelectionChanged_ExComp.GetInvocationList()[0];
tomorrow also.
I had tried the GetInvocationList() without the array element, [0]. I have not tried it with pointing to the first method in the list as you have suggested.
I had also tried,
+= CountySelectionChanged_ExComp.Method
and
+= CountySelectionChanged_ExComp.Target
but both of those of those failed.

re: TheLearnedOne,
The QueryTask class is from a third party API. I'll see if I can access its documentation through the Visual Studio Object Explorer to get some more info on their ExecuteHandler event.
I have made certain, though, that my delegate, QueryExecuteCompleted, does have the same signature as the one that it is expecting by using the same signature as the methods that do correctly work with it.

Thanks all again.
I'll have more info tomorrow.
0
 

Author Comment

by:XTO
ID: 39675061
re, Pavel and Mike,

Both your suggestions worked brilliantly.

But first, I had to change this,
CountySelectionChanged_ExComp = qryCplt.TownshipQueryTask_ExecuteCompleted;

Open in new window

into this,
CountySelectionChanged_ExComp = new QueryExecuteCompleted(qryCplt.TownshipQueryTask_ExecuteCompleted);

Open in new window

So for instance, the else clause will look like this:
else
{     
       layerName = "PLSS Townships";
       CountySelectionChanged_ExComp = new QueryExecuteCompleted(qryCplt.TownshipQueryTask_ExecuteCompleted);
}

Open in new window

I was worried I might have to resort to some convoluted System.Reflection type code.

-------------------

re: TheLearnedOne,

Here is the info I was able to find on the ExecuteCompleted event.

This is from the metadata,
// Summary:
//     Occurs when the query completes.
[ScriptableMember]
public event EventHandler<QueryEventArgs> ExecuteCompleted;

Open in new window


And this is from Visual Studio's Object Browser,
public event System.EventHandler<QueryEventArgs> ExecuteCompleted
    Member of ESRI.ArcGIS.Client.Tasks.QueryTask

Open in new window


Summary:
Occurs when the query completes.
0

Featured Post

Get your Disaster Recovery as a Service basics

Disaster Recovery as a Service is one go-to solution that revolutionizes DR planning. Implementing DRaaS could be an efficient process, easily accessible to non-DR experts. Learn about monitoring, testing, executing failovers and failbacks to ensure a "healthy" DR environment.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

This article is for Object-Oriented Programming (OOP) beginners. An Interface contains declarations of events, indexers, methods and/or properties. Any class which implements the Interface should provide the concrete implementation for each Inter…
Wouldn’t it be nice if you could test whether an element is contained in an array by using a Contains method just like the one available on List objects? Wouldn’t it be good if you could write code like this? (CODE) In .NET 3.5, this is possible…
This course is ideal for IT System Administrators working with VMware vSphere and its associated products in their company infrastructure. This course teaches you how to install and maintain this virtualization technology to store data, prevent vuln…
Video by: ITPro.TV
In this episode Don builds upon the troubleshooting techniques by demonstrating how to properly monitor a vSphere deployment to detect problems before they occur. He begins the show using tools found within the vSphere suite as ends the show demonst…

704 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question