AlarmManager에 이미 알람이 설정되어 있는지 확인하는 방법은 무엇입니까?
내 앱이 시작되면 특정 알람 (AlarmManager를 통해 등록)이 이미 설정되어 실행 중인지 확인하고 싶습니다. 구글의 결과는 이것을 할 수있는 방법이 없다는 것을 나타냅니다. 여전히 맞습니까? 새 경보를 만들기 위해 조치를 취하기 전에 사용자에게 알리려면이 점검을 수행해야합니다.
ron에 대한 의견에 이어 자세한 해결책은 다음과 같습니다. 다음과 같이 보류중인 의도로 반복 알람을 등록했다고 가정 해 봅시다.
Intent intent = new Intent("com.my.package.MY_UNIQUE_ACTION");
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0,
intent, PendingIntent.FLAG_UPDATE_CURRENT);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.add(Calendar.MINUTE, 1);
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), 1000 * 60, pendingIntent);
활성화되어 있는지 확인하는 방법은 다음과 같습니다.
boolean alarmUp = (PendingIntent.getBroadcast(context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_NO_CREATE) != null);
if (alarmUp)
{
Log.d("myTag", "Alarm is already active");
}
여기서 핵심 FLAG_NO_CREATE
은 javadoc에 설명 된 것과 같습니다 if the described PendingIntent **does not** already exists, then simply return null
(새 것을 만드는 대신)
이것이 필요할 수도있는 다른 사람들을 위해 여기에 답이 있습니다.
사용하다 adb shell dumpsys alarm
알람이 설정되었고 알람이 울릴 시간과 간격을 알 수 있습니다. 또한이 알람이 몇 번이나 호출되었는지도 확인하십시오.
리시버를 사용한 작업 예 (가장 좋은 대답은 조치입니다).
//starting
AlarmManager alarmManager = (AlarmManager) getActivity().getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(getActivity(), MyReceiver.class);
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//my custom string action name
PendingIntent pendingIntent = PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_CANCEL_CURRENT);//used unique ID as 1001
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(), aroundInterval, pendingIntent);//first start will start asap
//and stopping
Intent intent = new Intent(getActivity(), MyReceiver.class);//the same as up
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//the same as up
PendingIntent pendingIntent = PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_CANCEL_CURRENT);//the same as up
alarmManager.cancel(pendingIntent);//important
pendingIntent.cancel();//important
//checking if alarm is working with pendingIntent
Intent intent = new Intent(getActivity(), MyReceiver.class);//the same as up
intent.setAction(MyReceiver.ACTION_ALARM_RECEIVER);//the same as up
boolean isWorking = (PendingIntent.getBroadcast(getActivity(), 1001, intent, PendingIntent.FLAG_NO_CREATE) != null);//just changed the flag
Log.d(TAG, "alarm is " + (isWorking ? "" : "not") + " working...");
언급 할 가치가 있습니다.
나중에 애플리케이션 작성 (프로세스)이 동일한 종류의 PendingIntent (동일한 작업 , 동일한 의도-조치, 데이터, 카테고리, 구성 요소, 플래그 )를 다시 검색하는 경우 여전히 유효한 경우 동일한 토큰을 나타내는 PendingIntent를 수신합니다. 따라서 cancel ()을 호출하여 제거 할 수 있습니다.
요컨대, PendingIntent는 제어 할 수있는 동일한 기능 (작업 및 의도의 구조)을 가져야합니다.
경보 관리자의 설정 방법에 대한 문서 의이 인용문 을 참고 하십시오 .
예약 된이 의도에 대한 경보가 이미있는 경우 (Intent.filterEquals에 의해 정의 된 두 의도가 동일 함) 경보가 제거되고이 경보로 대체됩니다.
알람 설정을 원하면 이미 존재하는지 여부를 확인하지 않아도됩니다. 앱이 부팅 될 때마다 만들면됩니다. 과거의 모든 알람을 같은 것으로 교체합니다 Intent
.
이전에 생성 된 알람에 남아있는 시간을 계산하거나 이러한 알람이 존재하는지 여부를 알아야하는 경우 다른 접근 방법이 필요합니다. 이러한 질문에 답하려면 알람을 만들 때 공유 준비 데이터를 저장하는 것이 좋습니다. 알람이 설정되는 순간, 알람이 울릴 것으로 예상되는 시간 및 반복 기간 (반복 알람을 설정 한 경우)에 시계 타임 스탬프를 저장할 수 있습니다.
알람이 2 개 있습니다. 이벤트를 식별하기 위해 조치 대신 엑스트라로 인 텐트를 사용하고 있습니다.
Intent i = new Intent(context, AppReciever.class);
i.putExtra("timer", "timer1");
문제는 diff extras를 사용하면 의도 (및 경보)가 고유하지 않을 것입니다. 따라서 어떤 알람이 활성화되어 있는지 확인하려면 diff requestCode
-s 를 정의해야했습니다 .
boolean alarmUp = (PendingIntent.getBroadcast(context, MyApp.TIMER_1, i,
PendingIntent.FLAG_NO_CREATE) != null);
다음은 경보가 생성 된 방법입니다.
public static final int TIMER_1 = 1;
public static final int TIMER_2 = 2;
PendingIntent pending = PendingIntent.getBroadcast(context, TIMER_1, i,
PendingIntent.FLAG_CANCEL_CURRENT);
setInexactRepeating(AlarmManager.RTC_WAKEUP,
cal.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pending);
pending = PendingIntent.getBroadcast(context, TIMER_2, i,
PendingIntent.FLAG_CANCEL_CURRENT);
setInexactRepeating(AlarmManager.RTC_WAKEUP,
cal.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pending);
다른 해결책을 찾았습니다.
Intent myIntent = new Intent(MainActivity.this, MyReceiver.class);
boolean isWorking = (PendingIntent.getBroadcast(MainActivity.this, 0, myIntent, PendingIntent.FLAG_NO_CREATE) != null);
if (isWorking) {Log.d("alarm", "is working");} else {Log.d("alarm", "is not working");}
if(!isWorking) {
pendingIntent = PendingIntent.getBroadcast(MainActivity.this, 0, myIntent, PendingIntent.FLAG_UPDATE_CURRENT);
alarmManager = (AlarmManager) getSystemService(ALARM_SERVICE);
int timeNotif = 5 * 60 * 1000;//time in ms, 7*24*60*60*1000 for 1 week
Log.d("Notif", "Notification every (ms): " + timeNotif);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), timeNotif, pendingIntent);
}
adb 쉘에서 long을 추출하여 타임 스탬프로 변환하여 빨간색으로 표시하는 간단한 (멍청한 또는 멍청한) bash 스크립트를 만들었습니다.
echo "Please set a search filter"
read search
adb shell dumpsys alarm | grep $search | (while read i; do echo $i; _DT=$(echo $i | grep -Eo 'when\s+([0-9]{10})' | tr -d '[[:alpha:][:space:]]'); if [ $_DT ]; then echo -e "\e[31m$(date -d @$_DT)\e[0m"; fi; done;)
시도 해봐 ;)
여기에있는 거의 모든 사람이 정답을 제시했지만, 경보가 작동하는 근거에 대해서는 아무도 설명하지 않았습니다.
실제로 여기에서AlarmManager
작동하는 방법에 대해 자세히 배울 수 있습니다 . 그러나 여기에 빠른 대답이 있습니다
당신은 AlarmManager
기본적으로 일정이 PendingIntent
미래에 언젠가 는 참조하십시오 . 따라서 예약 된 알람을 취소하려면을 취소해야합니다 PendingIntent
.
항상 두 가지를 기록해 두십시오. PendingIntent
PendingIntent.getBroadcast(context,REQUEST_CODE,intent, PendingIntent.FLAG_UPDATE_CURRENT);
- 요청 코드-고유 식별자로 작동
- 플래그-의 동작을 정의합니다
PendingIntent
이제 알람이 이미 예약되어 있는지 확인하거나 알람을 취소하려면 동일한 액세스 권한 만 있으면됩니다 PendingIntent
. 동일한 요청 코드를 사용하고 FLAG_NO_CREATE
아래와 같이 사용하면이 작업을 수행 할 수 있습니다
PendingIntent pendingIntent=PendingIntent.getBroadcast(this,REQUEST_CODE,intent,PendingIntent.FLAG_NO_CREATE);
if (pendingIntent!=null)
alarmManager.cancel(pendingIntent);
로 존재하지 않는 경우 FLAG_NO_CREATE
반환 null
됩니다 PendingIntent
. 이미 존재하는 경우 기존에 대한 참조를 반환합니다PendingIntent
Intent intent = new Intent("com.my.package.MY_UNIQUE_ACTION");
PendingIntent pendingIntent = PendingIntent.getBroadcast(
sqlitewraper.context, 0, intent,
PendingIntent.FLAG_NO_CREATE);
FLAG_NO_CREATE는 보류 의도를 작성하지 않으므로 부울 값 false를 제공합니다.
boolean alarmUp = (PendingIntent.getBroadcast(sqlitewraper.context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_NO_CREATE) != null);
if (alarmUp) {
System.out.print("k");
}
AlarmManager alarmManager = (AlarmManager) sqlitewraper.context
.getSystemService(Context.ALARM_SERVICE);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP,
System.currentTimeMillis(), 1000 * 60, pendingIntent);
AlarmManager가 Pending Intent의 값을 확인한 후에 AlarmManager가 Pending Intent의 플래그를 업데이트하므로 참이됩니다.
boolean alarmUp1 = (PendingIntent.getBroadcast(sqlitewraper.context, 0,
new Intent("com.my.package.MY_UNIQUE_ACTION"),
PendingIntent.FLAG_UPDATE_CURRENT) != null);
if (alarmUp1) {
System.out.print("k");
}
이 작업을 수행 할 수있는 방법이 없다는 인상을 받으면 좋을 것입니다.
Alarm_last_set_time을 어딘가에 기록하고 On_boot_starter BroadcastReciever : BOOT_COMPLETED를 사용하면 비슷한 결과를 얻을 수 있습니다.
참고 URL : https://stackoverflow.com/questions/4556670/how-to-check-if-alarmmanager-already-has-an-alarm-set
'IT story' 카테고리의 다른 글
Python 3 : ImportError“Setuptools라는 모듈 없음” (0) | 2020.04.25 |
---|---|
로컬 커밋을 한 후 파일을 다시 스테이지 해제하려면 어떻게해야합니까? (0) | 2020.04.25 |
jQuery를 사용하여 div에서 선택된 확인란 목록 가져 오기 (0) | 2020.04.25 |
정수 스트림에서 연속 중앙값 찾기 (0) | 2020.04.25 |
FileResult를 사용하여 Asp.Net MVC에서 모든 유형의 파일을 다운로드 하시겠습니까? (0) | 2020.04.25 |