diff --git a/astrid/plugin-src/com/todoroo/astrid/repeats/RepeatTaskCompleteListener.java b/astrid/plugin-src/com/todoroo/astrid/repeats/RepeatTaskCompleteListener.java index 7911df5b9..50f729cf6 100644 --- a/astrid/plugin-src/com/todoroo/astrid/repeats/RepeatTaskCompleteListener.java +++ b/astrid/plugin-src/com/todoroo/astrid/repeats/RepeatTaskCompleteListener.java @@ -3,6 +3,7 @@ package com.todoroo.astrid.repeats; import java.text.ParseException; import java.util.Calendar; import java.util.Collections; +import java.util.Comparator; import java.util.Date; import java.util.List; import java.util.TimeZone; @@ -130,18 +131,40 @@ public class RepeatTaskCompleteListener extends BroadcastReceiver { private static long handleWeeklyRepeatAfterComplete(RRule rrule, Date original, DateValue startDateAsDV) { List byDay = rrule.getByDay(); - rrule.setByDay(Collections.EMPTY_LIST); + long newDate = original.getTime(); + newDate += DateUtilities.ONE_WEEK * (rrule.getInterval() - 1); Calendar date = Calendar.getInstance(); - date.setTimeInMillis(invokeRecurrence(rrule, original, startDateAsDV)); - outer: while(true) { - for(WeekdayNum weekdayNum : byDay) - if(weekdayNum.wday.javaDayNum == date.get(Calendar.DAY_OF_WEEK)) - break outer; + date.setTimeInMillis(newDate); + + Collections.sort(byDay, weekdayCompare); + WeekdayNum next = findNextWeekday(byDay, date); + + do { date.add(Calendar.DATE, 1); - } + } while (date.get(Calendar.DAY_OF_WEEK) != next.wday.javaDayNum); return date.getTimeInMillis(); } + private static Comparator weekdayCompare = new Comparator() { + @Override + public int compare(WeekdayNum object1, WeekdayNum object2) { + return object1.wday.javaDayNum - object2.wday.javaDayNum; + } + + }; + + private static WeekdayNum findNextWeekday(List byDay, + Calendar date) { + WeekdayNum next = byDay.get(0); + for (int i = 0; i < byDay.size(); i++) { + WeekdayNum weekday = byDay.get(i); + if (weekday.wday.javaDayNum > date.get(Calendar.DAY_OF_WEEK)) { + return weekday; + } + } + return next; + } + private static long invokeRecurrence(RRule rrule, Date original, DateValue startDateAsDV) { long newDueDate = -1; diff --git a/tests/src/com/todoroo/astrid/repeats/AdvancedRepeatTests.java b/tests/src/com/todoroo/astrid/repeats/AdvancedRepeatTests.java index b064e88bb..12d982de5 100644 --- a/tests/src/com/todoroo/astrid/repeats/AdvancedRepeatTests.java +++ b/tests/src/com/todoroo/astrid/repeats/AdvancedRepeatTests.java @@ -168,7 +168,8 @@ public class AdvancedRepeatTests extends TodorooTestCase { for(Weekday wday : Weekday.values()) { buildRRule(1, Frequency.WEEKLY, wday); computeNextDueDate(); - long expected = getDate(DateUtilities.now(), NEXT, wday.javaDayNum); + long expected = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, THIS, wday.javaDayNum); + nextDueDate = Task.createDueDate(Task.URGENCY_SPECIFIC_DAY, nextDueDate); assertDateEquals(nextDueDate, expected); } @@ -178,9 +179,10 @@ public class AdvancedRepeatTests extends TodorooTestCase { continue; buildRRule(1, Frequency.WEEKLY, wday1, wday2); - long nextOne = getDate(DateUtilities.now(), NEXT, wday1.javaDayNum); - long nextTwo = getDate(DateUtilities.now(), NEXT, wday2.javaDayNum); + long nextOne = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, THIS, wday1.javaDayNum); + long nextTwo = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, THIS, wday2.javaDayNum); computeNextDueDate(); + nextDueDate = Task.createDueDate(Task.URGENCY_SPECIFIC_DAY, nextDueDate); assertDateEquals(nextDueDate, Math.min(nextOne, nextTwo)); } } @@ -193,7 +195,8 @@ public class AdvancedRepeatTests extends TodorooTestCase { for(Weekday wday : Weekday.values()) { buildRRule(2, Frequency.WEEKLY, wday); computeNextDueDate(); - long expected = getDate(DateUtilities.now(), NEXT_NEXT, wday.javaDayNum); + long expected = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, NEXT, wday.javaDayNum); + nextDueDate = Task.createDueDate(Task.URGENCY_SPECIFIC_DAY, nextDueDate); assertDateEquals(nextDueDate, expected); } @@ -203,9 +206,10 @@ public class AdvancedRepeatTests extends TodorooTestCase { continue; buildRRule(2, Frequency.WEEKLY, wday1, wday2); - long nextOne = getDate(DateUtilities.now(), NEXT_NEXT, wday1.javaDayNum); - long nextTwo = getDate(DateUtilities.now(), NEXT_NEXT, wday2.javaDayNum); + long nextOne = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, NEXT, wday1.javaDayNum); + long nextTwo = getDate(DateUtilities.now() + DateUtilities.ONE_DAY, NEXT, wday2.javaDayNum); computeNextDueDate(); + nextDueDate = Task.createDueDate(Task.URGENCY_SPECIFIC_DAY, nextDueDate); assertDateEquals(nextDueDate, Math.min(nextOne, nextTwo)); } } diff --git a/tests/src/com/todoroo/astrid/repeats/NewRepeatTests.java b/tests/src/com/todoroo/astrid/repeats/NewRepeatTests.java index 842a1182f..89480821d 100644 --- a/tests/src/com/todoroo/astrid/repeats/NewRepeatTests.java +++ b/tests/src/com/todoroo/astrid/repeats/NewRepeatTests.java @@ -132,7 +132,7 @@ public class NewRepeatTests extends DatabaseTestCase { if (rrule == null) { rrule = new RRule(); rrule.setFreq(frequency); - int interval = 5; + int interval = 2; rrule.setInterval(interval); } t.setValue(Task.RECURRENCE, rrule.toIcal()); @@ -228,7 +228,7 @@ public class NewRepeatTests extends DatabaseTestCase { } if (fromCompletion) { - result += DateUtilities.ONE_WEEK * rrule.getInterval(); + result += DateUtilities.ONE_WEEK * (rrule.getInterval() - 1); } result += DateUtilities.ONE_DAY * daysToAdd; return result;