Home Random Page


CATEGORIES:

BiologyChemistryConstructionCultureEcologyEconomyElectronicsFinanceGeographyHistoryInformaticsLawMathematicsMechanicsMedicineOtherPedagogyPhilosophyPhysicsPolicyPsychologySociologySportTourism






Nbsp;   Designing a Type That Listens for an Event

The hard work is definitely behind you at this point. In this section, I’ll show you how to define a type

that uses an event provided by another type. Let’s start off by examining the code for the Fax type.

 

internal sealed class Fax {

// Pass the MailManager object to the constructor public Fax(MailManager mm) {

 

// Construct an instance of the EventHandler<NewMailEventArgs>

// delegate that refers to our FaxMsg callback method.

// Register our callback with MailManager's NewMail event mm.NewMail += FaxMsg;

}

 

// This is the method the MailManager will call

// when a new email message arrives

private void FaxMsg(Object sender, NewMailEventArgs e) {


// 'sender' identifies the MailManager object in case

// we want to communicate back to it.

 

// 'e' identifies the additional event information

// the MailManager wants to give us.

 

// Normally, the code here would fax the email message.

// This test implementation displays the info in the console Console.WriteLine("Faxing mail message:"); Console.WriteLine(" From={0}, To={1}, Subject={2}",

e.From, e.To, e.Subject);

}

 

// This method could be executed to have the Fax object unregister

// itself with the NewMail event so that it no longer receives

// notifications

public void Unregister(MailManager mm) {

 

// Unregister with MailManager's NewMail event mm.NewMail ­= FaxMsg;

}

}

 

When the email application initializes, it would first construct a MailManager object and save the reference to this object in a variable. Then the application would construct a Fax object, pass- ing the reference to the MailManager object as a parameter. In the Fax constructor, the Fax object registers its interest in MailManager’s NewMail event using C#’s += operator.

 

mm.NewMail += FaxMsg;

 

Because the C# compiler has built-in support for events, the compiler translates the use of the +=

operator into the following line of code to add the object’s interest in the event.

 

mm.add_NewMail(new EventHandler<NewMailEventArgs>(this.FaxMsg));

 

As you can see, the C# compiler is generating code that will construct an EventHandler<New­ MailEventArgs> delegate object that wraps the Fax class’s FaxMsg method. Then, the C# compiler calls the MailManager’s add_NewMail method, passing it the new delegate. Of course, you can verify all of this by compiling the code and looking at the IL with a tool such as ILDasm.exe.

Even if you’re using a programming language that doesn’t directly support events, you can still register a delegate with the event by calling the add accessor method explicitly. The effect is identical; the source code will just not look as pretty. It’s the add method that registers the delegate with the event by adding it to the event’s list of delegates.

When the MailManager object raises the event, the Fax object’s FaxMsg method gets called. The method is passed a reference to the MailManager object as the first parameter, sender. Most of the time, this parameter is ignored, but it can be used if the Fax object wants to access members of the MailManager object in response to the event notification. The second parameter is a reference to a NewMailEventArgs object. This object contains any additional information the designer of Mail­ Manager and NewMailEventArgs thought would be useful to the event receivers.




From the NewMailEventArgs object, the FaxMsg method has easy access to the message’s sender, the message’s recipient, and the message’s subject. In a real Fax object, this information would be faxed somewhere. In this example, the information is simply displayed in the console window.

When an object is no longer interested in receiving event notifications, it should unregister its inter- est. For example, the Fax object would unregister its interest in the NewMail event if the user no longer wanted his or her email forwarded to a fax. As long as an object has registered one of its methods with an event, the object can’t be garbage collected. If your type implements IDisposable’s Dispose method, the implementation should cause it to unregister interest in all events. (See Chapter 21, “The Managed Heap and Garbage Collection,” for more information about IDisposable.)

Code that demonstrates how to unregister for an event is shown in Fax’s Unregister method. This method is practically identical to the code shown in the Fax constructor. The only difference is that this code uses ­= instead of +=. When the C# compiler sees code using the ­= operator to unreg- ister a delegate with an event, the compiler emits a call to the event’s remove method.

 

mm.remove_NewMail(new EventHandler<NewMailEventArgs>(FaxMsg));

 

As with the += operator, even if you’re using a programming language that doesn’t directly sup- port events, you can still unregister a delegate with the event by calling the remove accessor method explicitly. The remove method unregisters the delegate from the event by scanning the list for a delegate that wraps the same method as the one passed in. If a match is found, the existing delegate is removed from the event’s list of delegates. If a match isn’t found, no error occurs, and the list is unaltered.

By the way, C# requires your code to use the += and ­= operators to add and remove delegates from the list. If you try to call the add or remove method explicitly, the C# compiler produces the CS0571 cannot explicitly call operator or accessor error message.

 

 


Date: 2016-03-03; view: 650


<== previous page | next page ==>
Nbsp;   How the Compiler Implements an Event | Nbsp;   Explicitly Implementing an Event
doclecture.net - lectures - 2014-2024 year. Copyright infringement or personal data (0.007 sec.)