Android equivalente a NSNotificationCenter
iphone ios (6)
Aquí hay algo similar a la respuesta de @Shiki, pero desde el ángulo de los desarrolladores de iOS y el centro de notificaciones.
Primero crea algún tipo de servicio NotificationCenter:
public class NotificationCenter {
public static void addObserver(Context context, NotificationType notification, BroadcastReceiver responseHandler) {
LocalBroadcastManager.getInstance(context).registerReceiver(responseHandler, new IntentFilter(notification.name()));
}
public static void removeObserver(Context context, BroadcastReceiver responseHandler) {
LocalBroadcastManager.getInstance(context).unregisterReceiver(responseHandler);
}
public static void postNotification(Context context, NotificationType notification, HashMap<String, String> params) {
Intent intent = new Intent(notification.name());
// insert parameters if needed
for(Map.Entry<String, String> entry : params.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
intent.putExtra(key, value);
}
LocalBroadcastManager.getInstance(context).sendBroadcast(intent);
}
}
Entonces, también necesitará algún tipo de enumeración para estar seguro de errores en la codificación con cadenas - (NotificationType):
public enum NotificationType {
LoginResponse;
// Others
}
Aquí está el uso (agregar / eliminar observadores) por ejemplo en actividades:
public class LoginActivity extends AppCompatActivity{
private BroadcastReceiver loginResponseReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
// do what you need to do with parameters that you sent with notification
//here is example how to get parameter "isSuccess" that is sent with notification
Boolean result = Boolean.valueOf(intent.getStringExtra("isSuccess"));
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
//subscribe to notifications listener in onCreate of activity
NotificationCenter.addObserver(this, NotificationType.LoginResponse, loginResponseReceiver);
}
@Override
protected void onDestroy() {
// Don''t forget to unsubscribe from notifications listener
NotificationCenter.removeObserver(this, loginResponseReceiver);
super.onDestroy();
}
}
y aquí está finalmente cómo publicamos notificaciones a NotificationCenter desde algún servicio de devolución de llamada o servicio de reposo o lo que sea:
public void loginService(final Context context, String username, String password) {
//do some async work, or rest call etc.
//...
//on response, when we want to trigger and send notification that our job is finished
HashMap<String,String> params = new HashMap<String, String>();
params.put("isSuccess", String.valueOf(false));
NotificationCenter.postNotification(context, NotificationType.LoginResponse, params);
}
eso es todo, ¡salud!
En el proceso de portar una aplicación de iPhone a Android, estoy buscando la mejor manera de comunicarme dentro de la aplicación. Los intentos parecen ser el camino a seguir, ¿es esta la mejor (única) opción? NSUserDefaults parece mucho más ligero que los Intents en rendimiento y codificación.
También debería agregar que tengo una subclase de aplicación para estado, pero necesito hacer que otra actividad tenga conocimiento de un evento.
Descubrí que el uso de EventBus de Guava lib es la forma más sencilla para la comunicación de publicación-suscripción entre los componentes sin que los componentes se registren explícitamente entre sí.
ver su muestra en https://code.google.com/p/guava-libraries/wiki/EventBusExplained
// Class is typically registered by the container.
class EventBusChangeRecorder {
@Subscribe public void recordCustomerChange(ChangeEvent e) {
recordChange(e.getChange());
}
// somewhere during initialization
eventBus.register(this);
}
// much later
public void changeCustomer() {
eventBus.post(new ChangeEvent("bla bla") );
}
puede agregar esta lib simplemente en Android Studio agregando una dependencia a su build.gradle:
compile ''com.google.guava:guava:17.0''
El mejor equivalente que encontré es LocalBroadcastManager que es parte del paquete de soporte de Android .
De la documentación de LocalBroadcastManager:
Ayudante para registrarse y enviar transmisiones de Intenciones a objetos locales dentro de su proceso. Esto tiene una serie de ventajas sobre el envío de transmisiones globales con sendBroadcast (Intento):
- Sabes que los datos que estás transmitiendo no saldrán de tu aplicación, por lo que no debes preocuparte por filtrar información privada.
- No es posible que otras aplicaciones envíen estas transmisiones a su aplicación, por lo que no debe preocuparse por tener agujeros de seguridad que puedan explotar.
- Es más eficiente que enviar una transmisión global a través del sistema.
Al usar esto, puede decir que un Intent
es equivalente a una NSNotification
. Aquí hay un ejemplo:
ReceiverActivity.java
Una actividad que busca notificaciones para el evento llamado "custom-event-name"
nombre de evento "custom-event-name"
.
@Override
public void onCreate(Bundle savedInstanceState) {
...
// Register to receive messages.
// This is just like [[NSNotificationCenter defaultCenter] addObserver:...]
// We are registering an observer (mMessageReceiver) to receive Intents
// with actions named "custom-event-name".
LocalBroadcastManager.getInstance(this).registerReceiver(mMessageReceiver,
new IntentFilter("custom-event-name"));
}
// Our handler for received Intents. This will be called whenever an Intent
// with an action named "custom-event-name" is broadcasted.
private BroadcastReceiver mMessageReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
// Get extra data included in the Intent
String message = intent.getStringExtra("message");
Log.d("receiver", "Got message: " + message);
}
};
@Override
protected void onDestroy() {
// Unregister since the activity is about to be closed.
// This is somewhat like [[NSNotificationCenter defaultCenter] removeObserver:name:object:]
LocalBroadcastManager.getInstance(this).unregisterReceiver(mMessageReceiver);
super.onDestroy();
}
SenderActivity.java
La segunda actividad que envía / difunde notificaciones.
@Override
public void onCreate(Bundle savedInstanceState) {
...
// Every time a button is clicked, we want to broadcast a notification.
findViewById(R.id.button_send).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
sendMessage();
}
});
}
// Send an Intent with an action named "custom-event-name". The Intent sent should
// be received by the ReceiverActivity.
private void sendMessage() {
Log.d("sender", "Broadcasting message");
Intent intent = new Intent("custom-event-name");
// You can also include some extra data.
intent.putExtra("message", "This is my message!");
LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
}
Con el código anterior, cada vez que se hace clic en el botón R.id.button_send
, Intent se transmite y lo recibe mMessageReceiver
en ReceiverActivity
.
La salida de depuración debería verse así:
01-16 10:35:42.413: D/sender(356): Broadcasting message
01-16 10:35:42.421: D/receiver(356): Got message: This is my message!
Podría usar referencias débiles.
De esta forma, podría administrar la memoria usted mismo y agregar y eliminar observadores a su gusto.
Cuando agregue Observer, agregue estos parámetros: eche ese contexto de la actividad en la que lo está agregando a la interfaz vacía, agregue un nombre de notificación y llame al método para ejecutar la interfaz.
El método para ejecutar la interfaz tendría una función que se llama ejecutar para devolver los datos que está pasando algo como esto
public static interface Themethodtorun {
void run(String notification_name, Object additional_data);
}
Cree una clase de observación que invoca una referencia con una interfaz vacía. También construya su interfaz Themethodtorun a partir del contexto que se pasa en addobserver.
Agregue la observación a una estructura de datos.
Llamarlo sería el mismo método; sin embargo, todo lo que necesita hacer es encontrar el nombre de notificación específico en la estructura de datos, use Themethodtorun.run (notification_name, data).
Esto enviará una devolución de llamada a donde quiera que haya creado un observador con un nombre de notificación específico. ¡No olvides eliminarlos cuando hayas terminado!
Esta es una buena referencia para referencias débiles.
http://learningviacode.blogspot.co.nz/2014/02/weak-references-in-java.html
Estoy en el proceso de cargar este código a github. Mantener los ojos abiertos!
Puede intentar esto: http://developer.android.com/reference/java/util/Observer.html
Puede usar esto: http://developer.android.com/reference/android/content/BroadcastReceiver.html , que proporciona un comportamiento similar.
Puede registrar receptores mediante programación a través de Context.registerReceiver (BroadcastReceiver, IntentFilter) y capturará los intentos enviados a través de Context.sendBroadcast (Intent).
Sin embargo, tenga en cuenta que un receptor no recibirá notificaciones si su actividad (contexto) ha sido pausada.