BroadcastReceiver - базовый класс для кода, который будет получать intent, отосланные с помощью метода sendBroadcast(). Рассмотрим использование этого класса с классом LocalBroadcastManager.
Есть два основных способа отсылки сообщений:
В некоторых ситуациях при передачи сообщения с помощью метода sendBroadcast система может вести себя как с методом sendOrderedBroadcast, то есть, доставка сообщения одному получателю за один раз. В частности, это будет происходить для слушателей, которые создают процесс для того чтобы избежать перегрузки системы.
В этой статье рассмотрим наиболее используемый метод - sendBroadcast. Для начала нам понадобится слушатель:
private BroadcastReceiver receiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
Log.d("lbr", "Message received: " + intent.getStringExtra("message") );
}
};
Слушатель должен расширять класс BroadcastReceiver и реализовывать метод onReceive. Методу onReceive передается context породившего объекта, что очень удобно, учитывая то, что с контекстом приходится работать очень часто. Второй параметр - intent - содержит информацию про сообщение, в том числе служебные данные. В нашем случае, единственными служебными данными является строка message, которую получаем, используя метод getStringExtra.
Слушатель создан, регистрируем его:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// some code
LocalBroadcastManager.getInstance(this).registerReceiver( receiver, new IntentFilter( "com.seostella.myaction" ) );
// some code
}
И убираем регистрацию, когда приложение завершается:
@Override
public void onDestroy() {
LocalBroadcastManager.getInstance(this).unregisterReceiver(receiver);
super.onDestroy();
}
Чтобы отправить событие слушателю receiver, необходимо воспользоваться следующим кодом:
Intent serviceStartedIntent = new Intent( "com.seostella.myaction" );
serviceStartedIntent.putExtra("message", "myaction message");
LocalBroadcastManager.getInstance( getBaseContext() ).sendBroadcast(serviceStartedIntent);
Приведем исходный код приложения, использующего BroadcastReceiver. Вам необходимо добавить в проект библиотеку android-support-v4.jar, которая находится по следующему пути /%ANDROID_SDK%/extras/android/support/v4
package com.seostella.broadcastexample;
import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Bundle;
import android.support.v4.content.LocalBroadcastManager;
import android.util.Log;
public class BroadcastExampleActivity extends Activity {
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
LocalBroadcastManager.getInstance(this).registerReceiver( receiver, new IntentFilter( "com.seostella.myaction" ) );
new Thread(){
@Override
public void run(){
Intent serviceStartedIntent = new Intent( "com.seostella.myaction" );
serviceStartedIntent.putExtra("message", "myaction message");
LocalBroadcastManager.getInstance( getBaseContext() ).sendBroadcast(serviceStartedIntent);
}
}.start();
}
private BroadcastReceiver receiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
Log.d("lbr", "Message received: " + intent.getStringExtra("message") );
}
};
@Override
public void onDestroy() {
LocalBroadcastManager.getInstance(this).unregisterReceiver(receiver);
super.onDestroy();
}
}
В IntentFilter также можно добавлять категории для конкретизации получателя.
Интересное поведение происходит при использовании dataType с IntentFilter. Слушатель, который подписался на dataType вида "audio/*", будет получать все сообщения, которые удовлетворяют это регулярное выражение, то есть, "audio/mpeg", "audio/aiff", "audio/*" и т.д.