when i was programming in c# i was making very often use of events. Now I would like to achieve something similar in Java. I know both languages are diffrent and there are some diffrences in implementing such mechanism. Well to give better picture maybe i will describe a little what i want to get, because i might confuse some of terminology:
MyClass contains code that handles launching MyEvent and some code that in certain situations launches that event.
MyEventArgs is class that transports data from MyClass and is sent along with event launch, so function that handles MyEvent has some additional information about state of MyClass instance.
And there is MyApp class that in main method contains instance of MyClass and code handling MyEvent and when event is raised inside MyClass certain actions are performed in code that listens to MyEvent.
If it’s still unclear, what i mean to achieve is exactly like c# mechanism that is behind button click, just instead of button there is my class, there are my event arguments instead of mouse event args and there is behaviour designed by me instead of click.
I’ve tried to google some answers to my problem and for example i found sites like:
http://javarevisited.blogspot.com/2011/12/observer-design-pattern-java-example.html http://www.javaworld.com/javaworld/javaqa/2002-03/01-qa-0315-happyevent.html
And either im just lost and I’m looking in bad places/using bad keywords, or what more possible i can’t understand anything out of these examples/i can’t transform them to work in way I need.
What im asking for, is some example, or atleast some draft of code handling such mechanism with use of MyClass, MyEvent, MyEventArgs, names, pointing code i should use in my class to raise event and some sample use of class and handling of event in Main method, so it would help me wrap my mind around this problem.
==========Edit========
Maybe there are some things like that avaliable for android developers? As my goal is to get to get into mobile apps development after i dust off java.
==========Edit========
If anyone still interested, here is some sample code, it doesn’t use names i metioned, just shows in general what im looking for:
And is there no exact solution, maybe somone would suggest something similar to thing im looking for?
frmTest.cs
namespace SampleApp
{
public partial class frmTest : Form
{
CountdownTimer ctmrTest;
public frmTest()
{
InitializeComponent();
ctmrTest = new CountdownTimer(100);
ctmrTest.CountdownTimerTick += new CountdownTimer.CountdownTimerTickEventHandler(ctmrTest_CountdownTimerTick);
}
void ctmrTest_CountdownTimerTick(object sender, CountdownTimerEventArgs ea)
{
lblTimer.Text = ea.timeString;
if (ea.countdownFinished) countdownEnd();
}
private void btnStart_Click(object sender, EventArgs e)
{
ctmrTest.Reset();
ctmrTest.Start();
}
void countdownEnd()
{
MessageBox.Show("Finish");
}
}
}
CountdownTimer.cs
namespace SampleApp
{
public class CountdownTimer
{
Timer tmrTicks = new Timer();
int secondsLeft = 0;
int numberOfSecondsToCountdown = 0;
public bool IsWorking
{
get { return tmrTicks.Enabled; }
}
public CountdownTimer(int seconds)
{
...
}
void tmrTicks_Tick(object sender, EventArgs e)
{
...
WhenCountdownTimerTick(new CountdownTimerEventArgs(secondsLeft, numberOfSecondsToCountdown, true));
}
public void Reset()
{
...
WhenCountdownTimerTick(new CountdownTimerEventArgs(secondsLeft, numberOfSecondsToCountdown, false));
}
public void Stop()
{
tmrTicks.Enabled = false;
}
public void Start()
{
,,,
}
public delegate void CountdownTimerTickEventHandler(object sender, CountdownTimerEventArgs ea);
public event CountdownTimerTickEventHandler CountdownTimerTick;
protected virtual void WhenCountdownTimerTick(CountdownTimerEventArgs ea)
{
if (CountdownTimerTick != null)
{
CountdownTimerTick(this, ea);
}
}
}
}
CountdownTimerEventArgs.cs
namespace SampleApp
{
public class CountdownTimerEventArgs : EventArgs
{
public string timeString = "";
public bool countdownFinished = false;
public CountdownTimerEventArgs(int secondsLeft, int SecondsToCountdown, bool isfinished)
{
countdownFinished = isfinished;
timeString = string.Format("{0:00}:{1:00}", secondsLeft / 60, secondsLeft % 60);
}
}
}
If i understand you correctly (i’m just starting learning C#), the normal way to do it in Java is to use the observer pattern (listener pattern):
You create a listener interface with a method to be called when your event happens.
That method can take some event-arguments and a sender as parameter, if you like.
For example:
A class which is to respond to your kind of event, needs to implement the above interface.
(see an example a little below (MyListeningClass))
Ok, so then you need a class (or more classes) which fires your event: MyClass.
Usually MyClass has some way for other classes, who wants to respond to MyClass‘ event, to register
themselves with MyClass. (Or more precisely, register themselves with a specific object of MyClass). This allows the MyClass-object to know which other objects it should inform about when the event happens.
This is usually done by creating a method called “add[ListenerName]” in the class firing the event – in this case “addMyListener” in MyClass.
To make this example simpler, let’s just assume there can only ever be one listener, so we will call it “setMyListener” instead:
(To support more than one listener, just have a list of listeners
List<MyListener> listenersinstead of theMyListener listenerinstance variable, and create an addListener and removeListener method instead of the setListener method. In the Android API they usually only allow one listener, so i thought i would show that version)So now we just need the class which wants to listen for the event. I.e. the class implementing the MyListener interface. (This class is thus a listener). A simple example:
(Of course you don’t actually have to create the interface if you don’t want to. You could of course just hardcode the MyListeningClass in MyClass instead, but it’s better style to use interfaces, to decouple MyClass and MyListeningClass from each other. And it’ll also be more extendable later, to allow other classes than MyListeningClass to listen for the events too.)
There are many examples of this in the Java API. For example SWING makes heavy use of listeners – for example for button-clicks, as you mention. And of course the Android API too.
I’ll see if i can find some examples of this later, but it’s very late and i’m very tired, so maybe tomorrow 😀 (and fix any spelling mistakes :D). Hope it helped a bit.
To Recap:
MyClass (the class producing the events) needs some way to tell other classes about that the event has happened, when the event happens.
It does that by calling a method in these classes when the event happens.
For MyClass to be able to call a method in these other classes, they have to implement some interface.
The classes which want to be told when the event happens, needs a way to tell MyClass that they want to
be told about it. This is the reason we need the MyClass.setMyListener method.
(or if we had allowed more than one listener: the MyClass.addMyListener method)
(So there is nothing magical about this. It’s just simple method calling.)
(Note that, a listener interface is usually named “[name of the event]Listener”. So instead of “MyListener” i should have called it “MyEventListener”, according to the naming convention, if we say that the event is called “MyEvent”. But for this post i think it looked too long and less simple. UPDATE: Now that i think about it, you actually usually omit “Event” from the name, so “MyListener” is right. For example if you have an event you call “OnClickEvent”, you call the interface “OnClickListener”.)