-
-
Notifications
You must be signed in to change notification settings - Fork 7
Events
Events are a core part of Domino-mvp, they play an important role in both navigation and communication between presenters, yet they are simple, so let's define an event and see how we can use it, how we can fire and listen to events, and understand the different types of events :
In Domino-mvp an event is a class that implements the interface DominoEvent
which is a generic interface that take one generic argument, which is a type that implement EventContex
each event has a context, the context is the object that holds the data the even is supposed to provide, example :
import org.dominokit.domino.api.shared.extension.DominoEvent;
import org.dominokit.domino.api.shared.extension.EventContext;
public class MessageReceivedEvent implements DominoEvent<MessageReceivedEvent.MessageContext> {
private final MessageContext context;
public MessageReceivedEvent(String message) {
this.context = new MessageContext(message);
}
@Override
public MessageContext context() {
return context;
}
public static class MessageContext implements EventContext {
private final String message;
public MessageContext(String message) {
this.message = message;
}
public String getMessage() {
return message;
}
}
}
In the above code we defined an event context MessageContext
and then we used that to create an event class MessageReceivedEvent
.
To fire an event in Domino-mvp we use the DominoEvents
class static method fire
passing the even class type and a new instance of the event or a subtype of the event, for example in a proxy we can do this :
import org.dominokit.domino.api.client.extension.DominoEvents;
@PresenterProxy(parent = "shell")
@AutoRoute
@Slot("notifications")
@AutoReveal
public class NotificationProxy extends ViewBaseClientPresenter<HomeView> implements HomeView.HomeUiHandlers {
public void publishMessage(String message){
DominoEvents.fire(MessageReceivedEvent.class, new MessageReceivedEvent(message));
}
}
We can fire events from any class in our application not just presenters, the only condition here is that the Domino-mvp application should be initialized and running - ClientApp.make().run() is already called -
Presenter has special methods to fire events without directly referencing the DominoEvents
class, we can directly call either fireEvent
of publishEvent
methods, the fireEvent
method will fire the event to all active listeners including the presenter firing the event, and publishEvent
will fire the event to all active listeners except the presenter firing the event.
We can manually register and remove event listeners from anywhere in the application using the ClientApp
registerEventListener
and removeEventListener
, example :
Registering event listener
ClientApp.make().registerEventListener(MessageReceivedEvent.class, (DominoEventListener<MessageReceivedEvent>) dominoEvent -> {
var eventMessage =dominoEvent.context().getMessage();
//do something with the message
});
Removing an event will require that we keep an instance of the registered event, once we have the instance we can manually remove it like the following example :
Removing event listener
DominoEventListener<MessageReceivedEvent> eventReference = dominoEvent -> {
var eventMessage = dominoEvent.context().getMessage();
//do something with the message
};
ClientApp.make().removeEventListener(MessageReceivedEvent.class, eventReference);
But when we are working with presenters there is a declarative way to register events in a proxy using the annotation @ListenTo
, the event listeners registered in a presenter will be coupled to the presenter life-cycle, so when the presenter is activated they will be automatically registered and when the presenter is deactivated then they will be removed, this means only active presenters can listen to events, to automatically register/remove events, you create a method annotated with @ListenTo
passing the event type as an argument to the annotation, the method will take one argument which the event context, example :
import org.dominokit.domino.api.client.annotations.presenter.ListenTo;
@PresenterProxy(parent = "shell")
@AutoRoute
@Slot("notifications")
@AutoReveal
public class NotificationProxy extends ViewBaseClientPresenter<HomeView> implements HomeView.HomeUiHandlers {
@ListenTo(event = MessageReceivedEvent.class)
public void onMessageReceived(MessageReceivedEvent.MessageContext context){
var message = context.getMessage();
//do something with the message
}
}
Global events are events that can be fired and received through different Domino-mvp applications, the context of those events should be something that we can be converted from/to strings, they are very useful when for example we include two or more Domino-mvp applications in the same web page, and we wanted to share some events between them, example :
import org.dominokit.domino.api.shared.extension.EventContext;
import org.dominokit.domino.api.shared.extension.GlobalEvent;
public class ApplicationReadyEvent extends GlobalEvent<ApplicationReadyEvent.ApplicationReadyContext> {
private final ApplicationReadyContext context;
public ApplicationReadyEvent(String name) {
this.context = new ApplicationReadyContext(name);
}
@Override
public String serialize() {
return context.getApplicationName();
}
@Override
public ApplicationReadyContext context() {
return null;
}
public static class ApplicationReadyContext implements EventContext {
private final String applicationName;
public ApplicationReadyContext(String applicationName) {
this.applicationName = applicationName;
}
public String getApplicationName() {
return applicationName;
}
}
}
Activation events are special type of global events that holds a boolean value, they can be used in presenter with onStateChanged
and DependsOn
to apply presenters dependency as we discussed in presenters documentation, example :
import org.dominokit.domino.api.shared.extension.ActivationEvent;
public class AuthenticationEvent extends ActivationEvent {
public AuthenticationEvent(boolean active) {
super(active);
}
public AuthenticationEvent(String serializedEvent) {
super(serializedEvent);
}
}