What is the difference between using MessagingCenter and standard .NET event handlers for informing interested parties of changes?
Two (untested) implementations of the same thing are below to demonstrate:
public class FooClass {
public event EventHandler SomeEvent;
public void DoSomeWork() {
// ... stuff
if(SomeEvent != null)
SomeEvent(this, EventArgs.Empty);
}
}
public class BarClass {
FooClass _foo;
public BarClass() {
_foo = new FooClass();
_foo.SomeEvent += delegate {
// ... did something
};
}
}
Verses:
public class FooClass {
public const string SomeEventName = "SomeEvent";
public void DoSomeWork() {
// ... stuff
MessagingCenter.Send<FooClass>(this, SomeEventName);
}
}
public class BarClass : IDisposable {
public BarClass() {
MessagingCenter.Subscribe<FooClass>(this, FooClass.SomeEventName, delegate {
// .. did something
});
}
public void Dispose() {
MessagingCenter.Unsubscribe<FooClass>(this, FooClass.SomeEventName);
}
}
From what I can tell there doesn't seem to be any difference, but if anyone can suggest any pros or cons for either, that'd help me understand. Currently, I've been using event handlers.
Is there any point in switching to using MessagingCenter? Or any new best practice?
The MessagingCenter from Xamarin is used to reduce coupling between ViewModels, as the sender and receiver do not need to know each other.
You can still build a similar structure by creating something like an "EventHub"/"EventAggregator" which knows sender and receiver and uses .NET events.
The MessagingCenter itself is kind of an EventAggregator
ImageSource : https://msdn.microsoft.com/en-us/library/ff921122.aspx
Here is a nice explanation of EventAggregators.
An Event Aggregator is a simple element of indirection. In its
simplest form you have it register with all the source objects you are
interested in, and have all target objects register with the Event
Aggregator. The Event Aggregator responds to any event from a source
object by propagating that event to the target objects.
To Answer the question:
Is there any point in switching to using MessagingCenter? Or any new
best practice?
If you are not using something like an EventAggregator it is a good choice to switch to the MessagingCenter, or build an EventAggregator on your own.
As Saruman made a good hint on explaining what coupling is. You allways want to reduce coupling for a clean code.
MessagingCenter is basically used in the Model-View-ViewModel
pattern.
It is a great way to communicate and pass data or notify about
updates among ViewModels without knowing who sent it to whom via a simple Message Contract.
Ex. In one screen if you make any service call to fetch the new data
and you want to notify other screens to update their UI via
broadcasting message from your current screen, then MessagingCenter
is the best approach.
It decouples them without making any dependency among ViewModels,
while EventHandlers makes dependency and may prohibit something
from being released. You explicitly have to decouple event handlers
from the events to better release the resources.
MessagingCenter should be applied when the receiver doesn't care
who sent the message and the sender doesn't care who will receive it.
Events should be used when the receiver needs to know who sent the
message, but the sender still doesn't care who handles it.
It is good to use MessagingCenter over Events but, if you make too much use of
too many Messages using MessagingCenter, it would be hard to
identify who sent it and when sent it, the relation between messages
would be hard to guess, thus making it hard time while debugging the
app.
If you have access to those classes (i.e from where you want to call your methods) then there really is not a lot of difference.
However if you don't have access to those classes(i.e inside a view model or decoupled class) then message subscription event aggregation is a useful tool
Message center reduces coupling and enables view models and other
components to communicate with without having to know anything about
each other besides a simple Message contract.
Coupling
In software engineering, coupling is the degree of interdependence
between software modules; a measure of how closely connected two
routines or modules are the strength of the relationships between
modules.
I found articles about and solutions to this question pertaining to Prism, but I didn't find anything pertaining to Caliburn Micro. I checked all questions here tagged with Caliburn.Micro and EventAggregator, but didn't find anything Caliburn specific about this seemingly basic issue.
Scenario: I want to publish events to the EventAggregator that don't have any information, other than signaling that something happened.
Problem: First, in Caliburn Micro, the EventAggregator's Publish() method requires an instance of a type to be sent. Second, subscribing and handling events require the implementation of the IHandle<T> interface, where T is the type of instances that we want to receive. It seems that this is fully designed around publishing and handling actual data.
Goal: To be able to publish simple events without having to create and instantiate multiple empty/dummy classes, and without having to Handle() unnecessary events that I need to filter further with conditionals.
My solution so far
This is what I want to improve/replace. (Obviously, this solution is problematic because it creates tighter coupling around the concrete classes, but in my use case this is not a big issue, since it's a small project with singular publishing components for a given event, and the EventAggregator serves other practical goals.)
I made a generic Signal<T> class that implements the singleton pattern, providing a static instance of itself through the Instance property:
public class Signal<T>
{
public static readonly Signal<T> Instance = new Signal<T>();
private Signal() { }
}
So I can publish events in the following way (SignalSourceClass is an example):
_eventAggregator.PublishOnUIThread(Signal<SignalSourceClass>.Instance);
And handle events by declaring the implementation of IHandle<T> in the following way:
IHandle<Signal<SignalSourceClass>>
This way I can send and receive "empty" events by creating only this single Signal class. (Of course this is a limited solution, since components can only send one event this way.)
I suspect that this solution is primitive (well, let's just call it a fact), and that there is something better that I'm overlooking.
Just create a enum with all possible signals you want:
public enum ProjectSignals
{
Connected,
Disconnected,
Openned
}
then just
_eventAggregator.PublishOnUIThread( ProjectSignals.Connected );
and
class SomeClass : IHandle<ProjectSignals>
{
public void Handle( ProjectSignals signal )
{
switch (signal)
{
case Connected:
break;
}
}
}
I have a game with many classes that need to listen to events. But under certain circumstances, those classes are destroyed or disabled. When that happens, I need to remove their listening methods from the events manager delegate table.
I don't want to modify the EventsManager and I would like to each class that adds any events to it to know which events it added.
I'm currently using something like this do add and remove the events in each class:
void AddEventsListeners() {
EventsManager.AddListener<OnClickDown>(OnClickDownHandler);
EventsManager.AddListener<OnClickUp>(OnClickUpHandler);
EventsManager.AddListener<OnClick>(OnClickHandler);
}
void RemoveEventsListeners() {
EventsManager.RemoveListener<OnClickDown>(OnClickDownHandler);
EventsManager.RemoveListener<OnClickUp>(OnClickUpHandler);
EventsManager.RemoveListener<OnClick>(OnClickHandler);
}
Those OnClick are all derived from GameEventBase, and the OnClickHandler are methods declared as
void OnClickDown(OnClickHandler e) {}
to match the delegate that is used in the EventsManager, which is declared as
delegate void EventDelegate<T>(T e) where T : GameEventBase;
I want to be able to fill a special hash table named, say, events, that has keyvalue pairs like
<T, EventDelegate<T>> where T: GameEventBase
That is, I want to be able to do events.add(OnClick, OnClickHandler), where OnClickHandler is declared as
OnClickHandler(OnClick e) {}
And I want adding to fail if OnClickHandler where defined, for example, as
OnClickHandler(OtherGameEventBaseDerivedEvent e) {}
That requirement translates to me wanting type safety in that special dictionary.
One of my attempts involved not a dictionary, but a way to decide which method to call, between the AddListener and RemoveListener
I didn't like it because it introduces a parameter to the method and the code reads really weird with it. It does work, and does reduce the repetition, but is too ugly.
I create a AddOrRemoveAllListeners(AddOrRemove addOrRemove), which I populated with calls to AddOrRemoveListener for each event.
Now all I had to do is AddOrRemoveAllListeners(AddOrRemove.Remove) or AddOrRemoveAllListeners(AddOrRemove.Add), to add or remove my events.
enum AddOrRemove {
Remove,
Add
}
void AddOrRemoveListener<T>(EventsManager.EventDelegate<T> del, AddOrRemove addOrRemove)
where T : GameEventBase {
switch (addOrRemove) {
case AddOrRemove.Remove:
EvMan.RemoveListener<T>(del);
break;
case AddOrRemove.Add:
EvMan.AddListener<T>(del);
break;
}
}
Another attempt involved creating the type
class EventsDictionary<T> : Dictionary<T, EventsManager.EventDelegate<T>> where T : GameEventBase { }
And using it like this:
EventsDictionary<GameEventBase> events = new MyCustomDictionary<GameEventBase>();
void AddEventHandlerPairToEventsDictionary<T>(T e, EventsManager.EventDelegate<T> handler) where T : GameEventBase {
if (!events.ContainsKey(e)) {
events.Add(e, handler);
}
}
But the events.Add(e, handler) fails and forces me to declare the handler as
EventsManager.EventDelegate<GameEventBase>
instead of
EventsManager.EventDelegate<T>
If I do that, I could add keyvalue pairs that don't make sense in that events type, i.e., I lose the event handling type safety.
I want to have such a structure because I don't like all those repetitions. It would be really bad if someone forgot to remove an event in the RemoveEventsListeners().
Having such a dictionary, I could use a foreach loop to add/remove the handlers to the EventsManager, which would be really nice.
As for performance, this is for a game and it needs to have good performance. Those adding/removing of events can happen a lot (sometimes hundreds of times per frame) because a lot of objects are destroyed (can't leave null handlers in the EventsManager) or disabled (need to stop listening to everything until enabled again) all the time. This means reflection and lots of casting/boxing or anything that creates lots of garbage collected objects is out.
I'm, of course, open to suggestions as to other ways to approach this.
Thanks for your assistance!
I'm attaching the relevant parts of the EventsManager being used (The RemoveListener() is analogous to the AddListener). The GameEventBase is just an empty shell. It isn't a .NET event nor uses EventArgs.
public class EventsManager : ManagedBase {
public delegate void EventDelegate<T>(T e) where T : GameEventBase;
private delegate void EventDelegate(GameEventBase e);
private readonly Dictionary<Type, EventDelegate> delegates = new Dictionary<Type, EventDelegate>();
private readonly Dictionary<Delegate, EventDelegate> delegateLookup = new Dictionary<Delegate, EventDelegate>();
public void AddListener<T>(EventDelegate<T> del) where T : GameEventBase {
// Early-out if we've already registered this delegate
if (delegateLookup.ContainsKey(del)) {
return;
}
// Create a new non-generic delegate which calls our generic one.
// This is the delegate we actually invoke.
EventDelegate internalDelegate = (e) => del((T) e);
delegateLookup[del] = internalDelegate;
EventDelegate tempDel;
if (delegates.TryGetValue(typeof (T), out tempDel)) {
delegates[typeof (T)] = tempDel + internalDelegate;
}
else {
delegates[typeof (T)] = internalDelegate;
}
}
public void Raise(GameEventBase e) {
EventDelegate del;
if (delegates.TryGetValue(e.GetType(), out del)) {
del.Invoke(e);
}
}
}
Your problems seem to be solved if you use the EventAggregator pattern.
There is a short description of it by Martin Fowler
Some very good implementations of it already exist, for example in caliburn micro and
Microsoft Prism
The general idea is that you simplify event registration and deregistration and have a single source of events for many objects.
I never had performance issues with it. You simply put a _eventAggregator.Subscribe(this) when you want to start listening to events for an object and Unsubscribe if you want to stop. Whereever you want to fire an event, just publish it, EventAggregator does the routing.
This once again looks like an XY problem. OP seems to want to have a central place to handle event handlers, registration and disposal. The OP has gone down the route of trying to create a pattern that deal with this in a generic way, but has not looked into the state of the art regarding how this problem is typically solved. He has now come up against a problem in his design and is now asking for a solution to THAT problem, rather than the original problem of event handlers.
There are two good solutions to event handler registration lifecycle management that I know of in .net.
Weak Event Handler
You state that "It would be really bad if someone forgot to remove an event in the RemoveEventsListeners()." Yet do not actually mention WHY it is bad. Typically the only reason for this being bad is that the event handler will now keep an object in reference, that should be collected. With weak reference event handlers, the GC will still be able to collect your object, even when it subscribes to an object that is still alive.
Rx.Net
Rx.Net abstracts event registrations into IDisposables, which you can tie to the object's lifetime, assuming of course you want to control the lifetime of the registrations.
However I actually find the IObservable pattern much nicer to work with than event handler pattern, mostly because C# lacks first class support for event handlers (this is not the case with F#).
F#
Most of your problems will have stemmed from the short sighted design of events keyword handling in C# (specifically not making events a first class construct). F# however does support first class events, and thus should be able to support the pattern you are trying to construct.
Thus with this option you should scrap your code base and rewrite it in F#.
*EDIT added tongue in cheek option of rewriting in F#.
I am .Net developer. i want to know that is there any event handling mechanism in Java for Events Handling like C#.
what i want to do is i want to raise/fire an event form my class upon some condition. and consumer of this class should register that event and write event handling method.
this can be done easily in C#. i have to implement this thing in Java.
after googling out i found some links but all those are talking about GUI events in AWT and swing.
can any one help me out.
Although most of the examples will be to do with GUI events, the principles are basically the same. You basically want an interface or abstract class to represent a handler for the event, e.g.
public interface EventHandler
{
// Change signature as appropriate of course
void handleEvent(Object sender, EventArgs e);
}
then the publisher of the event would have:
public void addEventHandler(EventHandler handler)
public void removeEventHandler(EventHandler handler)
It would either keep a list of event handlers itself, or possibly have them encapsulated in a reusable type. Then when the event occurs, you just call handleEvent in each handler in turn.
You can think of delegate types in C# as being very similar to single-method interfaces in Java, and events are really just an add/remove pair of methods.
I love C# Events,
They are simple to use and convenient. i missed them in java so wrote a small utility class that mimics the very basics of C# Event.
using java 8 (for lambdas)
no += operator, instead call .addListener((x) -> ...)
to trigger an event, call .broadcast(<EventArgs insance>)
Online Demo - https://repl.it/DvEo/2
Event.java
import java.util.HashSet;
import java.util.Set;
import java.util.function.Consumer;
public class Event {
private Set<Consumer<EventArgs>> listeners = new HashSet();
public void addListener(Consumer<EventArgs> listener) {
listeners.add(listener);
}
public void broadcast(EventArgs args) {
listeners.forEach(x -> x.accept(args));
}
}
You may want com.google.common.collect.Sets.newConcurrentHashSet() for thread safety
EventArgs.java
public class EventArgs {
}
Java has support through various event handling implementations - the simple Observer/Observable in java.util, PropertyChangeEvents in java.beans, and GUI events which inherit from AWTEvent.
An Observable object has a list of observers which implement the Observer interface, and mechanisms for adding and removing observers. If o.notifyObservers(x) is called on the observable, update(o,x) will be called on each observer. This mechanism is somewhat old fashioned and rarely used in new code - it dates from Java 1.0 before EventObject was added in Java 1.1 and better event handling added for AWT and beans.
Beans and GUI events propagate an object which extends java.util.EventObject to listeners which implement a sub-interface of EventListener. Usually if you're using an existing API you will only care about the events and listeners for that API, but if you're defining an API the events and listeners should follow that convention.
It's also the convention in Java APIs to call the handlers for events "listeners" rather than handlers, and all listener interface names end with Listener. The names of the methods don't start with 'on' but should be past tense -mouseMoved or handshakeCompleted rather than onMouseMove or handleMouseMove.
The PropertyChangeSupport class provides an implementation of the mechanism for adding and removing listeners from a bean, and is also used for properties of Swing widgets.
If you write your own listener handling, it's conventional to allow listeners to remove themselves by calling source.removeXXXListener(this) from within their event handling method. Just iterating over a simple collection of listeners and calling their handling methods would give a ConcurrentModificationException with in these cases - you need to copy the collection of listeners or use a concurrently modifiable collection.
Check out this tutorial. It goes through some of the Swing event handling stuff that you have come across in your searches, but the concepts are pretty general. In simple terms, event handlers maintain a collection of listeners (implementing an interface) and iterate over them when they fire an event, calling the method in the interface.
Currently, my level of understanding is below all the coding examples on the web about the Observer Pattern. I understand it simply as being almost a subscription that updates all other events when a change is made that the delegate registers. However, I'm very unstable in my true comprehension of the benefits and uses. I've done some googling, but most are above my level of understanding.
I'm trying to implement this pattern with my current homework assignment, and to truly make sense on my project need a better understanding of the pattern itself and perhaps an example to see what its use. I don't want to force this pattern into something just to submit, I need to understand the purpose and develop my methods accordingly so that it actually serves a good purpose. My text doesn't really go into it, just mentions it in one sentence. MSDN was hard for me to understand, as I'm a beginner on this, and it seems more of an advanced topic.
How would you describe this Observer pattern and its uses in C# to a beginner?
For an example, please keep code very simple so I can understand the purpose more than complex code snippets. I'm trying to use it effectively with some simple textbox string manipulations and using delegates for my assignment, so a pointer would help!
The best example I can come up with is that of a mailing list (as an example).
You, the observer, subscribe to a mailing list and you observe the list. When you are no longer interested in the list, you unsubscribe.
This concept is the observer pattern. Two or more classes are involved. One or more class, subscribes to a publisher class (there are different names) and then the first class (and every subscribing class) will get notified when ever the publisher desires.
This is how I explained it to my wife, who often listens to my rantings about programming and design theory. It made sense to her. I realize this might be too simple for you but is a good start...
Regards,
Frank
Check out "Head First: Design Patterns" for some really, smack-your-forehead easy to follow descriptions of the major patterns.
For Observer it is important to understand that it describes a one-to-many relationship and uses a subscription model for telling other classes when there has been a change. RSS, Atom, and Twitter work along these lines.
The Observer wants to know when anything changes, so it subscribes to the Subject. The Subject does not know the Observer. This is the important part. The Subject just defines the Interface (or delegate) the Observer needs to provide, and allows the registration.
In short: The Observer pattern allows your observer to be called from a subject, that does not care who the observer is and if it even exists.
There are two objects NOTIFIER and OBSERVER. NOTIFIER knows nothing about OBSERVER, while OBSERVER knows that NOTIFER implements a event.
OBSERVER uses the event to inform other objects that something happened. Simply spoken an event is a list of methods. Because OBSERVER wants to be notified if something happend, OBSERVER adds a method, that should be called if something happens, to the event of NOTIFER.
So if the thing happens, that NOTIFIER publishes with this event, NOTIFIER just walks over the list of methods and calls them. When the method added by OBSERVER is called, OBSERVER knows that the thing happend and can do what ever is required in this case.
Here is a example notifier class with a ValueChanged() event.
// Declare how a method must look in order to be used as an event handler.
public delegate void ValueChangedHandler(Notifier sender, Int32 oldValue, Int32 newValue);
public class Notifier
{
// Constructor with an instance name.
public Notifier(String name)
{
this.Name = name;
}
public String Name { get; private set; }
// The event that is raised when ChangeValue() changes the
// private field value.
public event ValueChangedHandler ValueChanged;
// A method that modifies the private field value and
// notifies observers by raising the ValueChanged event.
public void ChangeValue(Int32 newValue)
{
// Check if value really changes.
if (this.value != newValue)
{
// Safe the old value.
Int32 oldValue = this.value;
// Change the value.
this.value = newValue;
// Raise the ValueChanged event.
this.OnValueChanged(oldValue, newValue);
}
}
private Int32 value = 0;
// Raises the ValueChanged event.
private void OnValueChanged(Int32 oldValue, Int32 newValue)
{
// Copy the event handlers - this is for thread safty to
// avoid that somebody changes the handler to null after
// we checked that it is not null but before we called
// the handler.
ValueChangedHandler valueChangedHandler = this.ValueChanged;
// Check if we must notify anybody.
if (valueChangedHandler != null)
{
// Call all methods added to this event.
valueChangedHandler(this, oldValue, newValue);
}
}
}
Here a example observer class.
public class Observer
{
// Constructor with an instance name.
public Observer(String name)
{
this.Name = name;
}
public String Name { get; private set; }
// The method to be registered as event handler.
public void NotifierValueChanged(Notifier sender, Int32 oldValue, Int32 newValue)
{
Console.WriteLine(String.Format("{0}: The value of {1} changed from {2} to {3}.", this.Name, sender.Name, oldValue, newValue));
}
}
A small test application.
class Program
{
static void Main(string[] args)
{
// Create two notifiers - Notifier A and Notifier B.
Notifier notifierA = new Notifier("Notifier A");
Notifier notifierB = new Notifier("Notifier B");
// Create two observers - Observer X and Observer Y.
Observer observerX = new Observer("Observer X");
Observer observerY = new Observer("Observer Y");
// Observer X subscribes the ValueChanged() event of Notifier A.
notifierA.ValueChanged += observerX.NotifierValueChanged;
// Observer Y subscribes the ValueChanged() event of Notifier A and B.
notifierA.ValueChanged += observerY.NotifierValueChanged;
notifierB.ValueChanged += observerY.NotifierValueChanged;
// Change the value of Notifier A - this will notify Observer X and Y.
notifierA.ChangeValue(123);
// Change the value of Notifier B - this will only notify Observer Y.
notifierB.ChangeValue(999);
// This will not notify anybody because the value is already 123.
notifierA.ChangeValue(123);
// This will not notify Observer X and Y again.
notifierA.ChangeValue(1);
}
}
The output will be the following.
Observer X: The value of Notifier A changed from 0 to 123.
Observer Y: The value of Notifier A changed from 0 to 123.
Observer Y: The value of Notifier B changed from 0 to 999.
Observer X: The value of Notifier A changed from 123 to 1.
Observer Y: The value of Notifier A changed from 123 to 1.
To understand delegate types I am going to compare them with class types.
public class Example
{
public void DoSomething(String text)
{
Console.WriteLine(
"Doing something with '" + text + "'.");
}
public void DoSomethingElse(Int32 number)
{
Console.WriteLine(
"Doing something with '" + number.ToString() + "'.");
}
}
We defined a simple class Example with two methods. Now we can use this class type.
Example example = new Example();
While this works the following does not work because the types do not match. You get a compiler error.
Example example = new List<String>();
And we can use the variable example.
example.DoSomething("some text");
Now the same with a delegate type. First we define a delegate type - this is just a type definition like the class definition before.
public delegate void MyDelegate(String text);
Now we can use the delegate type, but we cannot store normal data in a delegate type variable, but a method.
MyDelegate method = example.DoSomething;
We have now stored the method DoSomething() of the object example. The following does not work because we defined MyDelegate as a delegate taking one string parameter and returning void. DoSomethingElse returns void but takes an integer parameter so you get a compiler error.
MyDelegate method = example.DoSomethingElse;
And finally you can use the variable method. You cannot perform data manipulation because the variable stores no data but a method. But you can call the method stored in the variable.
method("Doing stuff with delegates.");
This calls the method we stored in the variable - example.DoSomething().
The observer pattern is just like it sounds -
It's a means for some objects to watch an object, observing it for changes.
In C#, this becomes somewhat simple, since events are basically a language-specific means of implementing the observer pattern. If you've ever used events, you've used the observer pattern.
In other languages, this isn't built in, so there have been many attempts to formalize approaches to handling this.
Observer is like a direct line of communication. Rather than have all your relatives call you to find out how you are, when you get sick write a card and everyone who is interested gets it (or a copy). When you get better, you send out a card. When you stub your toe, you send out a card. When you get an A, you send out a card.
Anyone who cares gets on your mass mailing list and can respond however they see fit.
This dependency is great for UI. If I have a process that is slow (for example), it can fire an even when progress is made. A progress bar element could observe that and update its coverage. An OK button could observe that and become active at 100%. A cursor could observe that an animate until the progress is 100%. None of these observers needs to know about each other. Furthermore, none of these elements strictly needs to know what is driving them either.
This pattern is probably one of the most basic, if not the most basic pattern there is.
There are two "people" involved; the publisher and the subscriber/observer.
An observer simply asks the publisher to notify him when there is "news". News can be anything of importance here. It can be the temperature of the air, it can be a new post on a website, it can be the time of day.
Probably the thing you are having trouble with is defining the proper interfaces. The interface defines the interaction between the Subscriber and the Publisher.
First make a C# WinForms application
Setup Program.cs like this
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
static class Program
{
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
}
interface IObserver
{
void Refresh(List<string> DisplayList);
}
class ObserverList : List<IObserver>
{
public void Refresh(List<String> DisplayList)
{
foreach (IObserver tItem in this)
{
tItem.Refresh(DisplayList);
}
}
}
}
We are making two things here. The first the interface which the subscribers will implement. Then a list for the publisher to hold all the subscribers.
Then make form one with two buttons, one labeled Form 2 and the other Labeled Form 3. Then add a textbox, then another button labeled Add
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
private List<string> DataList= new List<string>();
private ObserverList MyObservers = new ObserverList();
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
Form2 frmNewForm = new Form2();
MyObservers.Add(frmNewForm);
frmNewForm.Show();
MyObservers.Refresh(DataList);
}
private void button2_Click(object sender, EventArgs e)
{
Form3 frmNewForm = new Form3();
MyObservers.Add(frmNewForm);
frmNewForm.Show();
MyObservers.Refresh(DataList);
}
private void Form1_Load(object sender, EventArgs e)
{
}
private void button3_Click(object sender, EventArgs e)
{
DataList.Add(textBox1.Text);
MyObservers.Refresh(DataList);
textBox1.Text = "";
}
}
}
I deliberately set up the Form2 button and the FOrm3 button to make multiple copies of each type of Form. For example, you can have twelve up at once.
You will notice that after creating each form I put it into the Observers list. I am able to do this because both Form2 and Form3 implement IObserver. After I show the Form I call refresh on the Observer list so the new form is updated with the latest data. Note I could have cast it to a variable of IObserver and updated just that form. I am trying to be as brief as possible.
Then for the Add button 'Button3' I pull the text from the textbox store it in my DataList and then refresh all the observers.
Then make Form2. Add a list box and the following code.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
public partial class Form2 : Form,IObserver
{
public Form2()
{
InitializeComponent();
}
private void Form2_Load(object sender, EventArgs e)
{
}
void IObserver.Refresh(List<string> DisplayList)
{
this.listBox1.Items.Clear();
foreach (string s in DisplayList)
{
this.listBox1.Items.Add(s);
}
this.listBox1.Refresh();
}
}
}
Then Add Form3, a combobox and add the following code.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
public partial class Form3 : Form,IObserver
{
public Form3()
{
InitializeComponent();
}
private void Form3_Load(object sender, EventArgs e)
{
}
void IObserver.Refresh(List<string> DisplayList)
{
this.comboBox1.Items.Clear();
foreach (string s in DisplayList)
{
this.comboBox1.Items.Add(s);
}
this.comboBox1.Refresh();
}
}
}
You will notice that each form implements the refresh method of the IObserver interface slightly different. One is for a listbox the other for a combo box. The use of interfaces is the key element here.
IN a real world application this example would be more complex. For example instead of passing the string list in the Refresh Interface. It would not have any parameters. Instead the Publisher (Form1 in this example) would implement a publisher interface and register itself with the Observers as they are being initialized. Each observer would be able to accept a publisher in it's initialization routine. Then when it is refreshed it would pull the string list out of the Publisher via a method exposed through the interface.
For more complex applications with multiple types of data this allows you customize what data the form implementing IObserver is pulling out of the publisher.
Of course if you ONLY want the Observer to be able to display a string list or specific data. Then pass it as part of the parameters. The Interface makes explicit what want each layer to do. This way 5 years from now you can look at the code and code "Oh that what it is doing."
(source: headfirstlabs.com)
As said Check out "Head First: Design Patterns" they also have some forums regarding the book and a design meditation.
Observer Pattern follow the Hollywood principle "Don't call us we call you"
Good site for patterns
http://www.dofactory.com/Patterns/PatternObserver.aspx
In it's very simplest terms, there are two components: Observer and Observed.
Externally, the Observed needs a way to add (register) and remove an Observer.
Internally, the Observed needs a list of registered Observers.
The observer needs a public method such as Notify() or Notify(params).
Any time a particular thing happens to the Observed, it will loop through the list and call Notify() on every registered observer.
In the simplest case, it's a simple notification that says "Hey, Observer, My Data Changed, come and refresh yourself"
In more complex versions, parameters can be past letting the observer know what has changed.
In a Model-View-Controller, the Observed is usually an entity object -- Something that holds data. The Controller is the Observer. It watches for changes in the Model, and tells the View to update itself if it is interested in the change.
Java event listeners are a real world implementation of this pattern.
Imagine that you have a object whose behavior (or state) you want to observe. For example, when field A hits value 10, you want to get informed on that event without actually getting coupled with the implementation details of this complex object you want to observe.
You define an interface, call it Observable and let your target implement this interface, it should have at least two methods to register and unregister an Observer, which in turn is the object which will get called by Observer when field A hits 10. Your Observer simply calls Observable to register (and unregister when done). Observable normally maintain a list of Observers and notifies them at once, or as you please. It can also be done synchronously or asynchronously, it's up to you. This is very simplistic explanation without writing code. Once you understand it, the implementations can differ in details to fit your particular needs.
Observer (Publish/Subscribe)
When an object changes state, it notifies other objects that have registered their interest at runtime.
The notifying object (publisher) sends an event (publication) to all its observers (subscribers).
In one sentence:
An object (the Subject) allows other objects (Observers) to sign up for notifications.
Practical example:
Let's say you've got an app and you want to let other devs build plugins.
You could create a PluginSubject class, and put a method on it called NotifyOrderCreated. Whenever a new order is created on your order screen, it calls PluginSubject.NotifyOrderCreated.
When that happens, the PluginSubject gets a list of PluginObservers and calls PluginObserver.Notify on each of them, passing in a message describing the event.
That enables some really neat functionality.
Way More Than You Want to Know:
I actually did this recently, so I will take the example one step deeper - if you require your Observers to implement a special interface, let's say IPluginObserver, you can use reflection to walk the types in your assembly and instantiate the plugins on the fly.
Then you can allow users to sign up their own assemblies (you have to store a list of assembly names somewhere and then walk it), and bam, you've got extensibility!
Observer is a means of decoupling, that is, loosening the connections between two objects. You want that because it makes your code neater and easier to maintain. That's pretty much the goal of all design patterns: easier to read, easier to maintain code.
In this pattern, you have two classes, two objects: publisher and observer. Publisher is a class that actually does some work, then it every so often will call methods on any observers to tell them about it. It knows which classes to call because it keeps a list of observers who subscribed.
So your Publisher might look something like this:
class Publisher
{
List<Observer> observers = new List<Observer>();
public Add(Observer o)
{
observers.Add(o);
}
private AlertObservers()
{
foreach(Observer o in observers)
{
o.Alert();
}
}
Publisher really does most of the work. All the Observer needs to do is get added to the list and implement the called method. Like so:
class Observer
{
public Observer(Publisher pub)
{
pub.Add(this);
}
public Alert()
{
System.Console.WriteLine("Oh no, stuff is happening!");
}
}
That's a pretty barebones idea of how it works. Now, why is that valuable? Looks pretty well coupled up huh? One reason for that is because I don't use an Interface, which would allow me to set up many classes with Observer functionality, and Publisher need never know anything more about them except that they can receive an Alert() call. Also note that Publisher will attempt to call Alert on any and all Observers it has, even if it has none.
Now, in the C# world, the language has a built in version of this pattern through it's Event objects. Events are very powerful and make use of Delegates, which is a way of passing a method as a parameter in another method call. They allow for some serious decoupling, but I'd save that for a new question.
Very few real time Examples:
Newspaper/Magazine/Mailing List
Subscription or any subscription in general
Tagging a colleague in MS Office
Communicator
Twitter
Those who've suggested that events in .NET really are an implementation of the Observer pattern aren't pulling your chain; it's true. As for how this actually works, both from a high level perspective and in terms of more implementation-specific details, I'll use an analogy.
Think of a newspaper publisher. In OOP terms we might think of a newspaper as an observable thing. But how does it work? Clearly the implementation details of the newspaper itself (that is, in this analogy, the journalists, writers, editors, etc. all working back at the office to put the newspaper together) are not publicly exposed. People (observers) do not gather together and watch the employees of the newspaper publisher doing their work. They can't just do that, because there is no protocol (or interface) in place for doing that.
This is how you observe (i.e., read) a newspaper: you subscribe to it. You get your name on a list of subscribers to that paper, and then the publisher knows to deliver one on your doorstep every morning. If you don't want to observe (read) it anymore, you unsubscribe; you get your name taken off that list.
Now, this might seem like an abstract analogy; but it's actually an almost perfect parallel to how .NET events work.
Given some class intended to be observable, its implementation in general need not be known to the public. However, it will expose a particular kind of interface to the public, and that interface is an event. Code that wants to observe this event essentially registers itself as a subscriber:
// please deliver this event to my doorstep
myObject.SomeEvent += myEventHandler;
When this same code decides it doesn't want to be notified of this event anymore, it unsubscribes:
// cancel my subscription
myObject.SomeEvent -= myEventHandler;
Now for a quick discussion of delegates and how this code actually works. A delegate, as you may or may not know, is essentially a variable that stores the address of a method. Typically, this variable has a type -- just like value variables declared as int, double, string, etc. all have types. In the case of delegate types, this type is defined by the method's signature; that is, its parameters and its return value. A delegate of a particular type can point to any method, that performs any action, as long as that method has the appropriate signature.
So to come back to the newspaper analogy: in order to successfully subscribe to a newspaper, you have to actually follow a particular pattern. Specifically, you need to provide a valid address where you want the newspaper delivered. You can't just say, "Yeah, send it to Dan." You can't say, "I'll have a bacon cheeseburger." You have to give the publisher information that they can meaningfully work with. In the world of .NET events, this translates to needing to supply an event handler of the correct signature.
In most cases, this signature ends up being some method like this:
public void SomeEventHandler(object sender, EventArgs e) {
// anything could go in here
}
The above is a method that could be stored in a delegate variable of type EventHandler. For more specific cases, there's the generic EventHandler<TEventArgs> delegate type, which desribes a method similar to the above, but with an e parameter of some type derived from EventArgs.
Keeping in mind that delegates are really variables pointing to methods, it isn't hard to make the final connection between .NET events and newspaper subscriptions. The way events are implemented is via a list of delegates, to/from which items may be added and removed. This is really just like a newspaper publisher's list of subscribers, each of whom receives a copy when the newspapers are distributed every morning.
Anyway, hopefully this has helped you get your head around the Observer pattern somewhat. There are many other kinds of implementations of this pattern, of course, but .NET events is a paradigm with which the majority of .NET developers are familiar, so I think it's a good starting point from which to develop one's understanding.