Android Broadcast Receiver

android

Un Broadcast Receiver puede verse como un listener que atiende a eventos del sistema, esto es, lanzados por el sistema operativo, o bien a eventos lanzados por aplicaciones. Además, el evento puede incluir información adicional en un Intent. Nos encontramos por tanto ante un componente que nos permitirá integrar aplicaciones entre sí y/o con Android. En el presente tutorial veremos una introducción a las posibiliaddes que nos ofrece la utilización de este componente.

Atender un evento

En la documentación de la clase Intent se pueden ver los eventos lanzados por Android y que podemos recibir implementando un Broacast Receiver en nuestra aplicación. Para ello basta con heredar de la clase BroadcastReceiver. En el siguiente ejemplo se crea un Broadcast Receiver que será ejecutado cuando el teléfono realice una llamada. Para este evento en el intent se recibirá el número marcado.

package com.danielme.broadcastreceiver;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.widget.Toast;


public class OutgoinCallBroadcastReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {

        String phoneNumber = intent.getStringExtra(Intent.EXTRA_PHONE_NUMBER);
        Toast.makeText(context, phoneNumber, Toast.LENGTH_LONG).show();
    }
}

Nota: para el envío y recepción de Broadcast Receiver dentro de una única aplicación, es más eficiente utilizar LocalBroadcastManager.

Para que el Broadcast Receiver sea invocado debe “registrarse” en el sistema operativo. Este registro puede realizarse de dos formas en función del comportamiento que necesitamos:

  1. En el AndroidManifest.xml. Los Broadcast Receiver que se registren de esta forma son llamados siempre aunque la aplicación no esté en ejecución. La única restricción que se aplica es que por seguridad la aplicación debe haber sido ejecutada al menos una vez. Indicaremos la clase y las acciones que se atenderán (en este ejemplo concreto es necesario añadir un permiso):

    <?xml version="1.0" encoding="utf-8"?>
    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
        package="com.danielme.broadcastreceiver" >
        <uses-permission android:name="android.permission.PROCESS_OUTGOING_CALLS" /> 
        <application
            android:allowBackup="true"
            android:icon="@mipmap/ic_launcher"
            android:label="@string/app_name"
            android:theme="@style/AppTheme" >
            <activity
                android:name=".MainActivity"
                android:label="@string/app_name" >
                <intent-filter>
                    <action android:name="android.intent.action.MAIN" />
    
                    <category android:name="android.intent.category.LAUNCHER" />
                </intent-filter>
            </activity>
            <receiver android:name=".OutgoinCallBroadcastReceiver" >
                <intent-filter>
                    <action android:name="android.intent.action.NEW_OUTGOING_CALL" >
                    </action>
                </intent-filter>
            </receiver>
        </application>
    
    </manifest>
    
    
  2. De forma programática. El Broadcast Receiver se puede registrar directamente en el contexto de la aplicación de tal modo que esté activo mientras la aplicación esté en ejecución:
            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_NEW_OUTGOING_CALL);
            getApplicationContext().registerReceiver(new OutgoinCallBroadcastReceiver(), filter);
    

    también puede ser asociado a una Activity en concreto:

            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_NEW_OUTGOING_CALL);
            registerReceiver(new OutgoinCallBroadcastReceiver(), filter);
    

    en este último caso es imprescindible “desregistrar” el Broadcast Receiver mediante el método unregisterReceiver antes de que la Activity sea destruída por Android ya que de lo contrario obtendremos el error has leaked IntentReceiver.

    Otra posibilidad es hacer que el Broadcast Receiver esté activo sólo mientras una Activity se esté mostrando en pantalla. En este caso, una posible estrategia a seguir es realizar el registro en el onResume y el “desregistro” en onPause.

     private OutgoinCallBroadcastReceiver outgoinCallBroadcastReceiver = new OutgoinCallBroadcastReceiver();
    
        @Override
        protected void onResume() {
            super.onResume();
            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_NEW_OUTGOING_CALL);
            registerReceiver(outgoinCallBroadcastReceiver, filter);
        }
    
        @Override
        protected void onPause() {
            super.onPause();
            unregisterReceiver(outgoinCallBroadcastReceiver);
        }
    

Enviar un evento

Se puede enviar un Broadcast al sistema para que sea atendido por los Broadcast Receiver que hayan sido configurados para ello. Tendremos que invocar el método sendBroadcast con un Intent que tendrá el nombre del evento al que corresponde el Broadcast (el valor Action) y todos los parámetros que se quieran añadir.

Intent intent = new Intent();
intent.setAction("com.danielme.blog.ACTION_EVENTO");
sendBroadcast(intent);

Existe una versión del método sendBroadcast que permite especificar el permiso que deben tener las aplicaciones que quieran escuchar el Broadcast enviado. Por ejemplo:

sendBroadcast(intent, "com.danielme.blog.permission.EVENTO");

Este permiso que hemos “inventado” debe declarase en el AndroidManifest.xml de la aplicación que envía el Broadcast.

<permission android:name="com.danielme.blog.permission.EVENTO" 
        android:label="evento" 
        android:protectionLevel="dangerous"/>

Se solicitará la posesión de dicho permiso en el AndroidManifest.xml de las aplicaciones que deban escuchar nuestro mensaje de Broadcast

 <uses-permission android:name="com.danielme.blog.permission.EVENTO" />

Es muy recomendable utilizar este control de permisos siempre que sea posible si implementamos un mecanismo de broadcast que puede ser utilizado desde fuera de nuestra aplicación.

One Response to Android Broadcast Receiver

  1. Pingback: Android: Integración con Chrome (Custom Tabs) | danielme.com

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s

A %d blogueros les gusta esto: