automatic initiation of service through broadcast receiver - android

I start a service using alarm manager using button click. It is working too. I have done it this way:
Intent scheduleSMS = new Intent(SMSProjectDatabase.this,SendSMS.class);
PendingIntent pendingIntent = PendingIntent.getService(SMSProjectDatabase.this,0, scheduleSMS,0);
AlarmManager alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.add(Calendar.SECOND,(int)GeneralUtil.calculateTimeDifference(getApplicationContext()));
Log.i("SMS is scheduled after ",""+GeneralUtil.calculateTimeDifference(getApplicationContext()));
alarmManager.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pendingIntent);
Here SendSMS is a service that will be started by the alarm manager. But this is not how i want to start a service in my code. I want to Use the Alarmmanager to trigger a broadcast for the Broadcastreceiver. The Broadcastreceiver then starts the Service for me.
My BroadCast Receiver is
public class MyReceiver extends BroadcastReceiver{
#Override
public void onReceive(Context context, Intent intent) {
//here i want to start the service through the alarm manager
}
}
But i donno how am i supposed to do this.Please provide the appropriate solution for me to solve this problelm.

You just simply need to put your stuff for calling Service using AlarmManager inside the onReceive()
#Override
public void onReceive(Context arg0, Intent arg1) {
// To get AlarmManager instance working you can use Context arg0
AlarmManager alarmManager = (AlarmManager)
arg0.getSystemService(ALARM_SERVICE);
// put your stuff to start Service using AlarmManager
}

You can use registerReceiver() function .
But y you want alaram mansger to trigger broadcast. Broadcastreceiver is used to receive broadcast when something is broadcast to the application.

Related

How to call onReceive from onReceive of another BroadcastReceiver in Android?

I am developing one android application, In which i need to call onReceive method of Alarmmanager from onReceive of another BroadcastReceiver i.e. Internet connectivity. Is it possible ? Or should i duplicate all my stuff in another BroadcastReceiver?
You can make a new intent from onReceive to trigger another broadcast receiver
#Override
public void onReceive(Context context, Intent intent) {
Intent newIntent = new Intent("com.domain.yourboardcastreceiver");
context.sendBroadcast(newIntent);
}
In OnReceive(..) method of Internet Connectivity broadcast receiver, you can set alarm and thats how alarm manager will get triggered, eg :
#Override
public void onReceive(Context context, Intent intent) {
Intent myIntent = new Intent(getBaseContext(), **AlarmReceiver**.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(getBaseContext(), 0, myIntent, 0);
AlarmManager alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
alarmManager.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pendingIntent);
}
Don't forget to register alarmmanager's receiver in your manifest file.
Hope it helps !

Stopping a repeating alarm from a BroadcastReceiver - is it possible?

I have an AlarmManager that sets a repeating alarm for the purpose of periodically querying a server.
private AlarmManager alarmManager;
private PendingIntent pendingIntent;
alarmManager = (AlarmManager) getApplicationContext().getSystemService(Context.ALARM_SERVICE);
Intent photosIntent = new Intent(this,AlarmReceiver.class);
//startService(photosIntent);
pendingIntent = PendingIntent.getBroadcast(getApplicationContext(),0,photosIntent,0);
alarmManager.setRepeating(AlarmManager.ELAPSED_REALTIME,
SystemClock.elapsedRealtime(),
10000, pendingIntent);
And I start an IntentService within the AlarmReceiver's onReceive() method. AlarmReceiver is a BroadcastReceiver. Here is the onReceive() method:
#Override
public void onReceive(Context context, Intent intent) {
Intent photosIntent = new Intent(context,JSONPhotosParser.class);
context.startService(photosIntent);
}
Now, this is something crazy I want to do, as it is not very practical. Is there any way I can stop my AlarmManager from within the BroadcastReceiver. I can also think of a practical scenario where such an action would be required. Say I am querying the status of a network connection using ConnectivityManager and if a connection exists I would start an IntentService that queries a server (which is my current scenario). If network status returns false, I would like to stop the repeating alarm set by the AlarmManager.
Is this possible within the BroadcastReceiver ? I understand that an AlarmManager can be removed using cancel(PendingIntent operation). But how do I create PendingIntent inside the BroadcastReceiver ?
Any help on this would be most appreciated. From an Android noob.
refer this link :
AlarmManager.cancel (PendingIntent operation)
http://developer.android.com/reference/android/app/AlarmManager.html#cancel%28android.app.PendingIntent%29

AlarmManager only lets one Service through when used with setRepeating in Android

I've been struggling with this for a couple of days. What I want to do is run a service periodically, about 2-3 minutes apart. I have an Activity that is responsible for the interface and setting up the first alarm.
The alarm is configured by a BroadcastReceiver which looks like this:
public class Receiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
String message = "Alarm worked";
Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
setAlarm(context);
}
public void setAlarm(Context context){
AlarmManager am = (AlarmManager) context.
getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, Receiver.class);
PendingIntent pi = PendingIntent.getBroadcast(context,
0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
Intent dailyUpdater = new Intent(context, DiscoveryService.class);
context.startService(dailyUpdater);
am.set(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()
+ (1000 * 30) , pi);
}
}
I've tried using setRepeating for AlarmManager, but it still has the same effect. What happens is that the AlarmManager works how it should, it fires an Intent which the receiver gets and executes onReceive periodically, as it should. However, it executes the service only the first time. After the first time, the alarms still go off, but the service is not executed.
I read some threads from people with similar problems, and one of them mentioned that PendingIntent lasts for only one send. Thus, I opted out to setting the alarm every time so I can set pendingIntent flag for updating every time.
I tried making my service an intentService, which is fine, but then my bluetooth scanner inside the service does not work because intentService thread terminates without waiting for my bluetooth discovery to finish.
Anyone have any idea what can help me?
Here is part of my service:
public class DiscoveryService extends Service {
public void onCreate() {
super.onCreate();
Toast.makeText(this, "MyAlarmService.onCreate()",
Toast.LENGTH_LONG).show();
findEverything();
}
}
EDIT: This is the code that I currently have.
public void onReceive(Context context, Intent intent) {
String message = "Alarm worked";
Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
Intent dailyUpdater = new Intent(context, DiscoveryService.class);
context.startService(dailyUpdater);
}
public void setAlarm(Context context){
// get a Calendar object with current time
AlarmManager am=(AlarmManager)context.
getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, Receiver.class);
PendingIntent pi = PendingIntent.getBroadcast(context, 0, intent,
PendingIntent.FLAG_UPDATE_CURRENT);
am.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(),
(1000 * 30) , pi);
}
What happens is that the AlarmManager works how it should, it fires an Intent which the reciever gets and executes onReceive periodically, as it should. However, it executes the service only the first time. After the first time, the alarms still go off, but the service is not executed.
You are calling startService() once when you are scheduling the alarm. You are not calling startService() at all from your BroadcastReceiver. Yet you are scheduling the alarm via the BroadcastReceiver. Hence, when the alarm goes off, the service will not be sent a command, because you are not sending it a command.
I read some threads from people with similar problems, and one of them mentioned that PendingIntent lasts for only one send.
That is only if you use FLAG_ONE_SHOT.
Anyone have any idea what can help me?
Call startService() from your onReceive() method, instead of from your setAlarm() method. Also, add in all the WakeLock management logic, since you are using a _WAKEUP alarm and you are not able to use my WakefulIntentService.

Update service on boot with timer/alarmclock

I have an update service that starts at boot. The thing is I want it to make a check and then wait for a period of time and restart itself. I did this with alarm clock when my service was tied to an application but now it is independent and I only use a broadcast receiver to start it at boot. The problem is that now for some reason I can't integrate my alarm clock with it.
I only have my UpdateService class and my broadcastreceiver class.My code so far in the broadcastreceiver is this, but I want to put the alarm clock here to say schedule the service to start every 30 seconds. I really need this.
#Override
public void onReceive(Context context, Intent intent) {
Intent startServiceIntent = new Intent(context, UpdateService.class);
context.startService(startServiceIntent);
}
Any suggestions are welcome. Thanks in advance.
I found the answer to my problem:
private boolean service_started=false;
private PendingIntent mAlarmSender;
#Override
public void onReceive(Context context, Intent intent) {
if(!service_started){
// Create an IntentSender that will launch our service, to be scheduled
// with the alarm manager.
mAlarmSender = PendingIntent.getService(context,
0, new Intent(context, UpdateService.class), 0);
//We want the alarm to go off 30 secs from now.
long firstTime = SystemClock.elapsedRealtime();
// Schedule the alarm!
AlarmManager am = (AlarmManager)context.getSystemService(context.ALARM_SERVICE);
am.setRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP,
firstTime,30*1000, mAlarmSender);
service_started=true;
}
}
Eventually,my problem was that I didn't get the context right as follows:
(AlarmManager)getSystemService(ALARM_SERVICE);
changed to
(AlarmManager)context.getSystemService(context.ALARM_SERVICE);

Android Alarm Manager with broadcast receiver registered in code rather than manifest

I want to use an alarm to run some code at a certain time. I have successfully implemented an alarm with the broadcast receiver registered in the manifest but the way i understand it, this method uses a separate class for the broadcast receiver.
I can use this method to start another activity but I cant use it to run a method in my main activity?
(how can I notify a running activity from a broadcast receiver?)
So I have been trying to register my broadcast receiver in my main activity as explained in the answer above.
private BroadcastReceiver receiver = new BroadcastReceiver(){
#Override
public void onReceive(Context context, Intent intent) {
Toast.makeText(context, "hello", Toast.LENGTH_SHORT).show();
uploadDB();
}
};
public void onResume() {
super.onResume();
IntentFilter filter = new IntentFilter();
filter.addAction(null);
this.registerReceiver(this.receiver, filter);
}
public void onPause() {
super.onPause();
this.unregisterReceiver(this.receiver);
}
However I have been unable to get this to work with alarm manager, I am unsure as to how i should link the alarm intent to the broadcast receiver. Could anyone point me to an example of registering an alarm manager broadcast receiver dynamically in the activity? Or explain how i would do this?
How about this?
Intent startIntent = new Intent("WhatEverYouWant");
PendingIntent startPIntent = PendingIntent.getBroadcast(context, 0, startIntent, 0);
AlarmManager alarm = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarm.set(AlarmManager.RTC_WAKEUP, triggerTime, startPIntent);
And then in your Manifest.xml file:
<receiver android:name="com.package.YourOnReceiver">
<intent-filter>
<action android:name="WhatEverYouWant" />
</intent-filter>
</receiver>
So as far as I know you still have to declare the receiver in the Manifest. I'm not sure if you can set it to a private instance inside of your activity. You could declare an onReceive inside of your activity and call that (if the BroadcastReceiver has an interface. I don't know if it does.)
Start a alarm intent from where you want to start alarm. write below code from where you want to start to listen the alarm
Intent myIntent = new Intent(getBaseContext(), **AlarmReceiver**.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(getBaseContext(), 0, myIntent, 0);
AlarmManager alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.add(Calendar.MINUTE, shpref.getInt("timeoutint", 30));
alarmManager.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pendingIntent);
And in broadcast receiver write the code you want to receive. And in menifest write below
<receiver android:name=".AlarmReceiver" android:process=":remote"/>
You can also put repetitive alarm also.
Hope it help!

Categories

Resources