web-dev-qa-db-ja.com

特定の曜日にアラームを繰り返すandroid

私のアプリケーションには、4つのセネリオでアラームをトリガーする機能があります。

  • ユーザーが選択した日時に対して1回のみ
  • 選択した時間の毎日
  • 選択した日時に応じて毎週
  • ユーザーが選択したカスタム曜日

以下を使用して、最初の3つのセネリオを正常に実装しました。

一度だけ:

Calendar calendar = Calendar.getInstance();

        calendar.set(Calendar.YEAR, Integer.parseInt(date[0]));
        calendar.set(Calendar.MONTH, (Integer.parseInt(date[1])) - 1);
        calendar.set(Calendar.DAY_OF_MONTH, Integer.parseInt(date[2]));
        calendar.set(Calendar.HOUR_OF_DAY, Integer.parseInt(time[0]));
        calendar.set(Calendar.MINUTE, Integer.parseInt(time[1]));
        calendar.set(Calendar.SECOND, 0);

        alarmManager.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pendingIntent);

毎日のスケジュールの場合:

Calendar calendar = Calendar.getInstance();
            calendar.setTimeInMillis(System.currentTimeMillis());
            calendar.set(Calendar.HOUR_OF_DAY, Integer.parseInt(time[0]));
            calendar.set(Calendar.MINUTE, Integer.parseInt(time[1]));
            calendar.set(Calendar.SECOND, 0);

            alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY, pendingIntent);

毎週のスケジュールの場合(システム日付による):

Calendar calendar = Calendar.getInstance();
        calendar.setTimeInMillis(System.currentTimeMillis());

        calendar.set(Calendar.DAY_OF_WEEK, dayOfWeek);
        calendar.set(Calendar.HOUR_OF_DAY, Integer.parseInt(time[0]));
        calendar.set(Calendar.MINUTE, Integer.parseInt(time[1]));
        calendar.set(Calendar.SECOND, 0);
        //long interval = calendar.getTimeInMillis() + 604800000L;
        alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY * 7, pendingIntent);

ユーザーが選択したカスタム平日(例:月曜日と金曜日のみ、毎週繰り返される)の場合、反復による毎週のスケジューリングに使用したのと同じコードを使用しています。ただし、月曜日(金曜日の前に設定)では機能せず、金曜日では機能しません。また、今日(システム日付)が月曜日または金曜日の場合、今日のアラームはトリガーされません。

では、カスタムの曜日に毎週のアラームスケジュールを実装するにはどうすればよいですか?

9
Dhruvil Patel

トリガーする日をアラームマネージャーに指示する方法はありません。

1つの解決策は、毎週繰り返しトリガーする曜日ごとにアラームを設定することです。

したがって、月曜日と金曜日のシナリオでは、月曜日に毎週繰り返しリマインダーを設定し、金曜日に毎週繰り返しリマインダーを設定します。

コード例:

private void scheduleAlarm(int dayOfWeek) {

    Calendar calendar = Calendar.getInstance();
    calendar.set(Calendar.DAY_OF_WEEK, dayOfWeek);

    // Check we aren't setting it in the past which would trigger it to fire instantly
    if(calendar.getTimeInMillis() < System.currentTimeMillis()) {
        calendar.add(Calendar.DAY_OF_YEAR, 7);
    }

    // Set this to whatever you were planning to do at the given time
    PendingIntent yourIntent; 

    AlarmManager alarmManager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
    alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY * 7, yourIntent);
}

private void setUpAlarms() {

    scheduleAlarm(Calendar.MONDAY);
    scheduleAlarm(Calendar.FRIDAY);
}
10
RobVoisey
1) sunday=1, moday=2;, tuesday=3,......saturday=7  
2)selectedDays.size()*(it will be which date you have selected , if you seleted monday , tues ,friday , then it will 3 size )*    

3) for time if we choose from datetimepicker  
 **String[] timespilt = tv_timepicker.getText().toString().split(":");**


     for (int i = 0; i < selectedDays.size(); i++) {

         // for alarm ...
           calNow = Calendar.getInstance();
           calSet = (Calendar) calNow.clone();

            int day = calSet.get(Calendar.DAY_OF_WEEK); 
        calSet.set(Calendar.HOUR_OF_DAY,Integer.parseInt(timespilt[0].trim()));
                                        calSet.set(Calendar.MINUTE, Integer.parseInt(timespilt[1].trim()));
                                        calSet.set(Calendar.SECOND, 0);
                                        calSet.set(Calendar.MILLISECOND, 0);
                                        calSet.set(Calendar.DAY_OF_WEEK,selectedDays.get(i));


                                    if (calSet.compareTo(calNow) <= 0) {
                                        //Today Set time passed, count to tomorrow
                                        calSet.add(Calendar.DATE,7);

                                    }



                            System.out.println("set time for alarmweekly==="+calSet.getTime());
                            AlarmManager alarmManager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
                            PendingIntent alarmPI = PendingIntent.getBroadcast(this, (int) insertedId+selectedDays.get(i), alarmIntent,  0);

                            alarmManager.set(AlarmManager.RTC_WAKEUP, calSet.getTimeInMillis(), alarmPI);

                            alarmManager.setRepeating(AlarmManager.RTC_WAKEUP,
                                    calSet.getTimeInMillis(), (DateUtils.DAY_IN_MILLIS) * 7,
                                    alarmPI);
}
1
priti

あなたは、毎週のスケジュールと同じコードを「反復によって」使用したと言いました。同じPendingIntentで複数のアラーム(例では2つ)を設定しようとしていることを理解している場合。

問題は、 ドキュメントによると

同じ保留中のインテントを使用する2番目のアラームを設定すると、元のアラームが置き換えられます。

これは、2番目のアラームのみがトリガーされる方法です。

したがって、問題を解決するには、スケジューリングごとに異なるPendingIntentを使用する必要があります。

0
GVillani82

これはあなたの問題を解決します。

private void scheduleAlarm(int dayOfWeek) {

        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.DAY_OF_WEEK, dayOfWeek);

        // Accept the change here at this line to avoid skipping of current week.
        if(calendar.getTimeInMillis() < System.currentTimeMillis()) {
             calendar.add(Calendar.DAY_OF_YEAR, new GregorianCalendar().get(Calendar.DAY_OF_WEEK)-1);
        }

        // Set this to whatever you were planning to do at the given time
        PendingIntent yourIntent; 

        AlarmManager alarmManager = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
        alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), AlarmManager.INTERVAL_DAY * 7, yourIntent);
    }

    private void setUpAlarms() {

        scheduleAlarm(Calendar.MONDAY);
        scheduleAlarm(Calendar.FRIDAY);
    }

今週をスキップしないように、ここに焦点を当てること。 :

calendar.add(Calendar.DAY_OF_YEAR, new GregorianCalendar().get(Calendar.DAY_OF_WEEK)-1);
0
Aimanzaki