Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java Listener Design Pattern for Subscribing

I am trying to design a Java system that is simliar to the concept of c# delegates.

Here is the basic functionality i wish to achieve:

public class mainform
{
   public delegate onProcessCompleted
//......
    processInformation()
    {
            onProcessCompleted(this);
    }

//......
}


//PLUGIN

public class PluginA
{
        public PluginA()
        {
            //somehow subscribe to mainforms onProcessingCompleted with callback myCallback()
        }

        public void myCallback(object sender)
        {
        }


}

I have read through this site: http://www.javaworld.com/javaqa/2000-08/01-qa-0804-events.html?page=1

They make reference to implementing the whole 'subscription list' manually. But the code is not a complete example, and I'm so used to c# that I'm having trouble grasping how I could do it in java.

Does anyone have a working examle of this that I could see?

thanks
Stephanie

like image 405
Without Me It Just Aweso Avatar asked Dec 05 '22 23:12

Without Me It Just Aweso


1 Answers

In Java you don't have function delegates (effectively method references); you have to pass an entire class implementing a certain interface. E.g.

class Producer {
  // allow a third party to plug in a listener
  ProducerEventListener my_listener;
  public void setEventListener(ProducerEventListener a_listener) {
    my_listener = a_listener;
  }

  public void foo() {
    ...
    // an event happened; notify the listener
    if (my_listener != null) my_listener.onFooHappened(new FooEvent(...));
    ...
  }
}


// Define events that listener should be able to react to
public interface ProducerEventListener {
  void onFooHappened(FooEvent e);
  void onBarOccured(BarEvent e);
  // .. as many as logically needed; often only one
}


// Some silly listener reacting to events
class Consumer implements ProducerEventListener {
  public void onFooHappened(FooEvent e) {
    log.info("Got " + e.getAmount() + " of foo");
  }
  ...
}

...
someProducer.setEventListener(new Consumer()); // attach an instance of listener

Often you have trivial listeners that you create via an anonymous classes in place:

someProducer.setEventListener(new ProducerEventListener(){
  public void onFooHappened(FooEvent e) {
    log.info("Got " + e.getAmount() + " of foo");
  }    
  public void onBarOccured(BarEvent e) {} // ignore
});

If you want to allow many listeners per event (as e.g. GUI components do), you manage a list which you usually want to be synchronized, and have addWhateverListener and removeWhateverListener to manage it.

Yes, this is insanely cumbersome. Your eyes don't lie to you.

like image 179
9000 Avatar answered Dec 08 '22 02:12

9000