I really need help guys , i'm trying to make a toast appear at a specific time with the alarm manager from android . I made some research and i made this code , but i don't know what isn't ok ... I tried everything
public void start() {
AlarmManager manager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
Date dat = new Date();
Calendar cal_alarm = Calendar.getInstance();
Calendar cal_now = Calendar.getInstance();
cal_now.setTime(dat);
cal_alarm.setTime(dat);
cal_alarm.set(Calendar.HOUR_OF_DAY,12);
cal_alarm.set(Calendar.MINUTE,13);
cal_alarm.set(Calendar.SECOND,0);
if(cal_alarm.before(cal_now)){
cal_alarm.add(Calendar.DATE,1);
}
manager.set(AlarmManager.RTC_WAKEUP,cal_alarm.getTimeInMillis(),pendingIntent);
}
If i use cal_alarm - cal_now in manager.set it fires off after 5 seconds .
You need to add a Receiver to get the result
In your AndroidManifest.xml add this
<receiver android:name=".AlarmReceiver" />
Create this BroadcastReceiver AlarmReceiver.java
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.widget.Toast;
public class AlarmReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
Toast.makeText(context, "ALARM", Toast.LENGTH_LONG).show();
}
}
and finally, fix your method start
public void start() {
AlarmManager manager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
Date dat = new Date();
Calendar cal_alarm = Calendar.getInstance();
Calendar cal_now = Calendar.getInstance();
cal_now.setTime(dat);
cal_alarm.setTime(dat);
cal_alarm.set(Calendar.HOUR_OF_DAY,14);
cal_alarm.set(Calendar.MINUTE,18);
cal_alarm.set(Calendar.SECOND,0);
if(cal_alarm.before(cal_now)){
cal_alarm.add(Calendar.DATE,1);
}
Intent myIntent = new Intent(context, AlarmReceiver.class);
pendingIntent = PendingIntent.getBroadcast(context, 0, myIntent, 0);
manager.set(AlarmManager.RTC_WAKEUP,cal_alarm.getTimeInMillis(), pendingIntent);
}
Related
I want the AlarmManager to set an alarm at 2 am daily... So below setAlarm is called only the first time someone opens the apps. I have added alarmManager.setRepeating so that it occurs daily.
public class AlarmUtil {
public static void setAlarm(Context context) {
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
if (alarmManager != null) {
long start = System.currentTimeMillis();
Intent in = new Intent("ALARM_RECEIVER");
PendingIntent pi = PendingIntent.getBroadcast(context, 0, in, PendingIntent.FLAG_CANCEL_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.HOUR, 2);
calendar.set(Calendar.AM_PM, Calendar.AM);
DateFormat format = new SimpleDateFormat("MMMM dd , yyyy HH:mm:ss", Locale.ENGLISH);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pi);
}
}
}
The below class is what should get called at 2 am daily irrespective of whether app is active or inactive.
public class AlarmReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
context.startService(new Intent(context, AlarmService.class));
}
But my problem is the above AlarmReceiver gets called every 30 seconds or somewhat occurs randomly, but occurs many times, whereas I want it just to get called once a day. I don't understand where am I going wrong?
I'm setting up a daily alarm. It works if the app is running at alarm time, but does not work if the app is not running.
This is how I declare the receiver in the Manifest:
<receiver android:name="com.myAppPackage.alarm.AlarmReceiver"
android:enabled="true"
android:exported="true"/>
Studio warns me: Exported receiver does not require permission.
True I have not added an android:permission nor and Intent to the receiver and the application section doesn't have any permission tags.
And this is the broadcastreceiver:
package com.myAppPackage.alarm;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
public class AlarmReceiver extends BroadcastReceiver {
public AlarmReceiver(){}
#Override
public void onReceive(Context context, Intent intent) {
final Intent syncIntent = new Intent(context, AlarmActivity.class);
syncIntent.addFlags(FLAG_ACTIVITY_NEW_TASK);
context.startActivity(syncIntent);
}
}
The alarm is configured in the following method (in this example configured to set-off daily inexact at 13:48):
public static void configureDailySync(Context context) {
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
Intent alarmIntent = new Intent(context, AlarmReceiver.class);
PendingIntent alarmPendingIntent = PendingIntent.getBroadcast(context, 0, alarmIntent, 0);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
final int hourOfDay = 13;
final int minuteOfHour = 48;
calendar.set(Calendar.HOUR_OF_DAY, hourOfDay);
calendar.set(Calendar.MINUTE, minuteOfHour);
alarmManager.setInexactRepeating(
AlarmManager.RTC_WAKEUP,
calendar.getTimeInMillis(),
AlarmManager.INTERVAL_DAY,
alarmPendingIntent);
}
Any help is very welcome! Thank you!!
news: getting closer... if I copy the alarm-setting code in the MainActivity onCreate() method it works! This is the code I copied:
AlarmManager alarmManager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
Intent alarmIntent = new Intent(this, AlarmReceiver.class);
PendingIntent alarmPendingIntent = PendingIntent.getBroadcast(this, 0, alarmIntent, 0);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
final int hourOfDay = 13;
final int minuteOfHour = 48;
calendar.set(Calendar.HOUR_OF_DAY, hourOfDay);
calendar.set(Calendar.MINUTE, minuteOfHour);
alarmManager.setInexactRepeating(
AlarmManager.RTC_WAKEUP,
calendar.getTimeInMillis(),
AlarmManager.INTERVAL_DAY,
alarmPendingIntent);
When the alarm is created as above in the onCreate() of the MainActivity then it DOES trigger even when the app is closed...
But when I call the call the method from the MainActivity like this:
MyAppAccount.configureDailySync(this);
it doesn't work!
MyAppAccount is an plain class not extending anything... I've tried to have MyAppAccount extend AppCompatActivity in case it mattered but nothing...
Oh well... it seems that the above try of executing the alarm-setting in the onCreate() method of the MainActivity is not always working... what is most puzzling!!! :-(
SOLVED: It had nothing to do with coding!! The problem was the way I was closing the application. When closing the application using the stop button of Android Studio the alarm is NOT set. When closing the application from the phone, using the back button for instance and / or removing the application from the list of applications (with the square button), then the alarm works!
Why? No idea...
I have written this class to call reciver every 24 hours
I was trying to use same receiver for "SabahReceiver" then i added another receiver "MasaReceiver", all possibilities did not work for me!
anybody can tell me whats going wrong !?
import android.app.AlarmManager;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import com.mbh.test.receivers.MasaReciever;
import com.mbh.test.receivers.SabahReciever;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
/**
* Created by MBH on 17/12/15.
*/
public class SabahMasaAlarmManager {
public static final int MINUTE = 60000;
public static final int HOUR = 1000 * 60 * 60;
public static final int DAY = 86400000;
private PendingIntent mSabahPendingIntent;
private PendingIntent mMasaPendingIntent;
private Context mContext;
private void SetupAlarms() {
/* Retrieve a PendingIntent that will perform a broadcast */
Intent sabahAlarm = new Intent(mContext, SabahReciever.class);
// sabahAlarm.putExtra(SabahReciever.KEY_IS_SABAH, true);
mSabahPendingIntent = PendingIntent.getBroadcast(mContext, 100, sabahAlarm, 0);
/* Retrieve a PendingIntent that will perform a broadcast */
Intent masaAlarm = new Intent(mContext, MasaReciever.class);
// sabahAlarm.putExtra(SabahReciever.KEY_IS_SABAH, false);
mMasaPendingIntent = PendingIntent.getBroadcast(mContext, 101, masaAlarm, 0);
}
public void StartAlarm() {
SimpleDateFormat dateFormat = new SimpleDateFormat(
"yyyy-MM-dd HH:mm:ss" );
Date now = Calendar.getInstance().getTime();
Calendar sabahDate = Calendar.getInstance();
sabahDate.set(Calendar.HOUR_OF_DAY, 23);
sabahDate.set(Calendar.MINUTE, 47);
sabahDate.set(Calendar.SECOND, 0);
// sabahDate.set(Calendar.HOUR_OF_DAY, 6);
// sabahDate.set(Calendar.MINUTE, 0);
if(sabahDate.getTime().before(now)){
sabahDate.add(Calendar.DAY_OF_YEAR, 1);
}
Log.d("DATE", "Sabah: "+ dateFormat.format(sabahDate.getTime()));
Calendar masaDate = Calendar.getInstance();
masaDate.set(Calendar.HOUR_OF_DAY, 23);
masaDate.set(Calendar.MINUTE, 49);
// masaDate.set(Calendar.HOUR_OF_DAY, 20);
// masaDate.set(Calendar.MINUTE, 0);
masaDate.set(Calendar.SECOND, 0);
if(masaDate.getTime().before(now)){
masaDate.add(Calendar.DAY_OF_YEAR, 1);
}
Log.d("DATE", "Masa: "+ dateFormat.format(masaDate.getTime()));
AlarmManager manager = (AlarmManager) mContext.getApplicationContext().getSystemService(Context.ALARM_SERVICE);
manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, sabahDate.getTimeInMillis(), DAY, mSabahPendingIntent);
// manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()+10000, 86400000, mSabahPendingIntent);
manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, masaDate.getTimeInMillis(), DAY, mMasaPendingIntent);
// manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()+20000, 86400000, mMasaPendingIntent);
}
public void cancelAlarm() {
AlarmManager managerSabah = (AlarmManager) mContext.getSystemService(Context.ALARM_SERVICE);
managerSabah.cancel(mSabahPendingIntent);
AlarmManager managerMasa = (AlarmManager) mContext.getSystemService(Context.ALARM_SERVICE);
managerMasa.cancel(mMasaPendingIntent);
}
public SabahMasaAlarmManager(Context baseContext) {
mContext = baseContext;
SetupAlarms();
}
}
setInexactRepeating() is not bound to fire the alarm exactly after the mentioned time. There may be some delay or it may fire a bit early. Basically framework 'batch' the inexact alarms to fire all at one time. Use setExact. Also consider the deep sleep mode. See How to use CPU to perform any operation in deep sleep mode. As you want alarm to fire once in 24 hours, there are good chances that device will be in sleep mode when alarm fires.
I am implement a simple alarm function, which is used to trigger some function at the specific date time.
The problem is I have set the time already, but the receiver seems never called.
Here is how I implement:......
1) in manifest :
<uses-permission android:name="com.android.alarm.permission.SET_ALARM" />
and
<receiver android:name=".Listener.AlarmReceiver" />
2) in the main activity (I would like to trigger on 4th June 2014, 02:06 p.m.)
profilePic.setOnClickListener(new OnClickListener(){
#Override
public void onClick(View v) {
GregorianCalendar date = new GregorianCalendar(2014,6,4,14,6);
long dateTime = date.getTimeInMillis();
Log.d("test1",date.toString());
AlarmManager alarmManager = (AlarmManager) ctx.getSystemService(Context.ALARM_SERVICE);
Intent intentAlarm = new Intent(ctx, AlarmReceiver.class);
alarmManager.set(AlarmManager.RTC_WAKEUP, dateTime, PendingIntent.getBroadcast(ctx, 1, intentAlarm, PendingIntent.FLAG_UPDATE_CURRENT));
}
});
And I have also log the time
java.util.GregorianCalendar[time=1404453960000,areFieldsSet=true,lenient=true,zone=Asia/Hong_Kong,firstDayOfWeek=1,minimalDaysInFirstWeek=1,ERA=1,YEAR=2014,MONTH=6,WEEK_OF_YEAR=27,WEEK_OF_MONTH=1,DAY_OF_MONTH=4,DAY_OF_YEAR=185,DAY_OF_WEEK=6,DAY_OF_WEEK_IN_MONTH=1,AM_PM=1,HOUR=2,HOUR_OF_DAY=14,MINUTE=6,SECOND=0,MILLISECOND=0,ZONE_OFFSET=28800000,DST_OFFSET=0]
3) Receiver
public class AlarmReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
Log.d("test1", "alarm");
Toast.makeText(context, "Alarm Triggered", Toast.LENGTH_LONG).show();
}
}
I waited until the 02:06p.m. but nothing happened, and receiver is not called. How to fix the problem? Also, is it possible to set more than one alarm, is it all I need to do is to create another datetime and fire the alarmManager.set() again, will it overwrite the old timer? Thanks for helping.
Updated
For the AlarmReceiver in the mainifest ,
I changed to
<receiver android:name="com.example.antismoke.Listener.AlarmReceiver" />
And the class is
package com.example.antismoke.Listener;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
import android.widget.Toast;
public class AlarmReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
Log.d("test1", "alarm");
Toast.makeText(context, "Alarm Triggered", Toast.LENGTH_LONG).show();
}
}
so I think package name is not the root cause? Thanks for helping
Instead of using GregorianCalendar , try to use Calendar.
Try the following, it should work:
Intent i = new Intent(getApplicationContext(), AlarmReceiver.class);
PendingIntent sender = PendingIntent.getBroadcast(AlarmSample.this, 0, i, 0);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, hour); // set hour
calendar.set(Calendar.MINUTE, minuite); // set minute
calendar.set(Calendar.SECOND, 0); // set seconds
AlarmManager am = (AlarmManager)getSystemService(ALARM_SERVICE);
am.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), sender);
you should use package name correctly, if you have different package ,
receiver android:name="XXX.XXXXXXXXXXXXXXX.AlarmReceiver" />
check this out
1) You don't need this persmission (com.android.alarm.permission.SET_ALARM) to receive alarm.
2) Change this line:
<receiver android:name=".Listener.AlarmReceiver" />
to
<receiver android:name=".AlarmReceiver" />
replace alarmManager.set with alarmManager.setRepeating
or try to use this:
public static AlarmManager am = null;
public static PendingIntent sender;
Intent intent1 = new Intent(ctx, Reciver.class);
sender = PendingIntent.getBroadcast(ctx, 1, intent1, 0);
am = (AlarmManager) getSystemService(ALARM_SERVICE);
long l = new Date().getTime();
am.setRepeating(AlarmManager.RTC_WAKEUP, l, 1500, sender);
Ok , finally I figure out it is because the month start at 0 in GregorianCalendar. So June should use 5 instead of 6
I should have noticed the problem. Thanks for all you guys
I have a set of alarms that I need to keep after reboot. I've tried using on an boot receiver but they won't start again. I'm not sure if I understand the boot receiver and how to then restart all the alarms. I already have one receiver for my notifications, but don't know whether I can use the same receiver or if I need a new one?
Could anyone point me to any good tutorials or help me out?
Cheers
Code :
DatabaseHandler db = new DatabaseHandler(this);
List<UAlarm> alarms = db.getAllAlarms();
AlarmManager am = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
for (UAlarm ua : alarms) {
String programme = ua.getTitle();
String startTime = ua.getStart();
String endTime = ua.getEnd();
String nowPlaying = ua.getChannel();
db.addAlarm(new UAlarm(programme, startTime, endTime, nowPlaying, ""));
final UAlarm ut = new UAlarm();
ut.setTitle(programme);
ut.setStart(startTime);
ut.setEnd(endTime);
ut.setChannel(nowPlaying);
ut.setId(db.getLastEntered());
String [] bla = startTime.split(":");
int hour = Integer.parseInt(bla[0].trim());
int minute = Integer.parseInt(bla[1].trim());
minute -= 2;
Calendar cal = Calendar.getInstance();
cal.set(Calendar.HOUR_OF_DAY, hour);
cal.set(Calendar.MINUTE, minute);
Intent intenta = new Intent(this, NotificationMenu.class);
String name = programme;
intenta.putExtra("name", name);
intenta.putExtra("id", db.getLastEntered());
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, ua.getId(),
intenta, PendingIntent.FLAG_CANCEL_CURRENT);
am.set(AlarmManager.RTC_WAKEUP,
cal.getTimeInMillis(), pendingIntent);
}
}
with NotificationMenu being the notifications, which is why I'm using the AlarmManager
I'm not sure if I understand the boot receiver and how to then restart all the alarms.
Just call your code to call setRepeating() (or whatever) on AlarmManager.
For example, in this sample project, PollReceiver is set to receive BOOT_COMPLETED. In onReceive(), it reschedules the alarms:
package com.commonsware.android.schedsvc;
import android.app.AlarmManager;
import android.app.PendingIntent;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.SystemClock;
public class PollReceiver extends BroadcastReceiver {
private static final int PERIOD=5000;
#Override
public void onReceive(Context ctxt, Intent i) {
scheduleAlarms(ctxt);
}
static void scheduleAlarms(Context ctxt) {
AlarmManager mgr=
(AlarmManager)ctxt.getSystemService(Context.ALARM_SERVICE);
Intent i=new Intent(ctxt, ScheduledService.class);
PendingIntent pi=PendingIntent.getService(ctxt, 0, i, 0);
mgr.setRepeating(AlarmManager.ELAPSED_REALTIME,
SystemClock.elapsedRealtime() + PERIOD, PERIOD, pi);
}
}