Dynamically register/unregister a broadcast receiver in android

47,729

Solution 1

The LocalBroadcastManager class is used to register for and send broadcasts of Intents to local objects within your process. This is faster and more secure as your events don't leave your application.

The following example shows an activity which registers for a customer event called my-event.

@Override
public void onResume() {
super.onResume();

   // Register mMessageReceiver to receive messages.
   LocalBroadcastManager.getInstance(this).registerReceiver(mMessageReceiver,
     new IntentFilter("my-event"));
}

// handler for received Intents for the "my-event" event 
private BroadcastReceiver mMessageReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
   // Extract data included in the Intent
   String message = intent.getStringExtra("message");
   Log.d("receiver", "Got message: " + message);
 }
};

@Override
protected void onPause() {
   // Unregister since the activity is not visible
   LocalBroadcastManager.getInstance(this).unregisterReceiver(mMessageReceiver);
   super.onPause();
} 
// This method is assigned to button in the layout
// via the onClick property
public void onClick(View view) {
   sendMessage();
}

// Send an Intent with an action named "my-event". 
private void sendMessage() {
  Intent intent = new Intent("my-event");
  // add data
  intent.putExtra("message", "data");
  LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
} 

Solution 2

use the below methods to register/unregister your receiver:

registerReceiver(BroadcastReceiver receiver, new IntentFilter("android.net.wifi.STATE_CHANGE"));
unregisterReceiver(BroadcastReceiver receiver);

For reference have a look at this

Solution 3

Don't add dynamic broadcast receiver in onReceive on broadcast file. Add it on first activity or main activity of your application. If you needed it only when your application is open. But if you need it always received response just added it on manifest file

Register dynamic broadcast receiver on main activity

MyReceiver reciver;

@Override
protected void onResume() {
    super.onResume();
    IntentFilter intentFilter = new IntentFilter();
    intentFilter.addAction("android.net.wifi.WIFI_STATE_CHANGED");
    intentFilter.addAction("android.net.wifi.STATE_CHANGE");
    reciver = new MyReceiver();
    registerReceiver(reciver, intentFilter);
}

Unregister that broadcast receiver on activity stop or closed

@Override
protected void onStop() {
    super.onStop();
    unregisterReceiver(reciver);
}
Share:
47,729
Sid
Author by

Sid

Updated on August 10, 2022

Comments

  • Sid
    Sid almost 2 years

    I want to dynamically register and unregister my receiver class with the broadcast: "android.net.wifi.STATE_CHANGE" This works very well if I do this in the manifest. But this makes it static. I want to do it dynamically in the activity class. What is its correspondent command in the activity class?

    This is what my code is... and I am getting a problem because of registering and unregistering(multiple times) my receiver(which is starting a service).

    public class startScreen extends Activity {
        /** Called when the activity is first created. */
    
        private BroadcastReceiver receiver = new BroadcastReceiver() {    
    
            @Override
            public void onReceive(Context context, Intent intent) {
                Intent serviceIntent = new Intent();
                serviceIntent.setAction("com.example.MyService");
                context.startService(serviceIntent);    
            }    
        };
    
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.initial);
    
            final IntentFilter filter = new IntentFilter();
            filter.addAction("android.net.wifi.STATE_CHANGE");   
    
            Button button = (Button) findViewById(R.id.button1);
            final ToggleButton toggleButton = (ToggleButton) findViewById(R.id.toggleButton1);
    
            try {
                    ...some code...
                if (bool == true) {
                    toggleButton.setChecked(true);
                    this.registerReceiver(receiver, filter);
                } else
                    toggleButton.setChecked(false);
            } catch (Exception e) {
                Log.e("Error", "Database", e);
            } finally {
                    ...
            }
    
            toggleButton.setOnClickListener(new OnClickListener() {
                public void onClick(View v) {
                    if ((toggleButton.isChecked())) {
                        getBaseContext().registerReceiver(receiver, filter);
    
                    } else {
                        if (receiver != null) {
                            getBaseContext().unregisterReceiver(receiver);
                            receiver = null;
                        }
    
                    }
                }
            });
        }    
    
        @Override
        protected void onResume() {
            super.onResume();
            if (bool == true) {
                if (receiver == null)
                    this.registerReceiver(receiver, filter);
            }
        }
    
        @Override
        protected void onPause() {
            super.onPause();
            if (receiver != null) {
                this.unregisterReceiver(receiver);
                receiver = null;
            }
        }
    }
    
    • Urban
      Urban over 12 years
      Check this and this out, similar to what you want to achieve. Hope this helps.
    • Sush
      Sush over 12 years
    • Yinda Yin
      Yinda Yin over 12 years
      What is the "problem" that you are having? Stating that you have a problem without saying what it is is seldom helpful to those trying to answer your question. Are you getting an error message? What is the exact wording of the error message, and on what line of code are you getting it?
    • Sid
      Sid over 12 years
      I am sorry, i dint state the problem i am facing clearly... anyway, the problem is that: i have seen that the 'receiver' variable becomes NULL after once executing registerReceiver and unregisterReceiver commands... specifically, after I register and unregister and then again register the receiver, the receiver has NULL only, and hence, while unregistering it again, it gives an error! so basically, my app is not able to register a Receiver again after unregistering it once. why is that a problem?
  • Sid
    Sid over 12 years
    thanks a lot for your answer... but this does not seem to work properly(as compared to the static[manifest] version). It does not detect the change in the wifi state!
  • Sid
    Sid over 12 years
    i have seen that the 'receiver' variable becomes NULL after a few registerReceiver and unregisterReceiver commands... specifically, after I register and unregister and then again register the receiver, the receiver has NULL only, and hence, while unregistering it again, it gives an error!
  • Permita
    Permita over 12 years
    A BroadcastReceiver object is only valid for the duration of the call to onReceive(Context, Intent). Once your code returns from this function, the system considers the object to be finished and no longer active. For dynamically registering/unregistering of BroadcastReceivers, you have to remember to unregister the instance of your receiver in onPause() to register it again during onResume(). Here is a sample application
  • Sid
    Sid over 12 years
    pls check my answer... i put it as a separate answer since i could not put all the code in here... i would exceed the word limit here...
  • Nikhil Bhojani
    Nikhil Bhojani almost 8 years
    broadCastReceiver is name of your BroadcastReceiver.
  • Ajeet Shah
    Ajeet Shah over 7 years