diff --git a/SOPE/NGCards/iCalDailyRecurrenceCalculator.m b/SOPE/NGCards/iCalDailyRecurrenceCalculator.m index 8626359f6..c6ab5a6ff 100644 --- a/SOPE/NGCards/iCalDailyRecurrenceCalculator.m +++ b/SOPE/NGCards/iCalDailyRecurrenceCalculator.m @@ -3,17 +3,17 @@ Copyright (C) 2006-2010 Inverse inc. This file is part of SOPE. - + SOPE is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2, or (at your option) any later version. - + SOPE is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. - + You should have received a copy of the GNU Lesser General Public License along with SOPE; see the file COPYING. If not, write to the Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA @@ -38,20 +38,20 @@ @implementation iCalDailyRecurrenceCalculator - /** - * TODO : Unsupported conditions for DAILY recurrences : - * - * BYYEAR - * BYYEARDAY - * BYWEEKNO - * BYMONTH - * BYMONTHDAY - * BYHOUR - * BYMINUTE - * - * There's no GUI to defined such conditions, so there's no - * problem for now. - */ +/** + * TODO : Unsupported conditions for DAILY recurrences : + * + * BYYEAR + * BYYEARDAY + * BYWEEKNO + * BYMONTH + * BYMONTHDAY + * BYHOUR + * BYMINUTE + * + * There's no GUI to defined such conditions, so there's no + * problem for now. + */ - (NSArray *) recurrenceRangesWithinCalendarDateRange: (NGCalendarDateRange *) _r { @@ -66,48 +66,48 @@ endDate = [_r endDate]; dayMask = nil; repeatCount = 0; - + if ([endDate compare: firStart] == NSOrderedAscending) // Range ends before first occurrence return nil; - + interval = [rrule repeatInterval]; if ([[rrule byDay] length]) dayMask = [rrule byDayMask]; - + // If rule is bound, check the bounds if (![rrule isInfinite]) { NSCalendarDate *until, *lastDate; - + lastDate = nil; until = [rrule untilDate]; if (until) - { - lastDate = until; - } + { + lastDate = until; + } else - { - repeatCount = [rrule repeatCount]; - if (dayMask == nil) - // If there's no day mask, we can compute the date of the last - // occurrence of the recurrent rule. - lastDate = [firStart dateByAddingYears: 0 months: 0 - days: (interval - * (repeatCount - 1))]; - } - + { + repeatCount = [rrule repeatCount]; + if (dayMask == nil) + // If there's no day mask, we can compute the date of the last + // occurrence of the recurrent rule. + lastDate = [firStart dateByAddingYears: 0 months: 0 + days: (interval + * (repeatCount - 1))]; + } + if (lastDate != nil) - { - if ([lastDate compare: startDate] == NSOrderedAscending) - // Range starts after last occurrence - return nil; - - if ([lastDate compare: endDate] == NSOrderedAscending) - // Range ends after last occurence; adjust end date - endDate = lastDate; - } + { + if ([lastDate compare: startDate] == NSOrderedAscending) + // Range starts after last occurrence + return nil; + + if ([lastDate compare: endDate] == NSOrderedAscending) + // Range ends after last occurence; adjust end date + endDate = lastDate; + } } currentStartDate = [firStart copy]; @@ -115,9 +115,9 @@ ranges = [NSMutableArray array]; i = 1; count = 0; - + while ([currentStartDate compare: endDate] == NSOrderedAscending || - [currentStartDate compare: endDate] == NSOrderedSame) + [currentStartDate compare: endDate] == NSOrderedSame) { BOOL wrongDay, isFirStart; @@ -125,26 +125,26 @@ isFirStart = NO; if (i == 1) - { - isFirStart = YES; - count++; - } + { + isFirStart = YES; + count++; + } else if (repeatCount > 0 && dayMask) - { - // If the rule count is defined, stop once the count is reached. - if ([dayMask occursOnDay: [currentStartDate dayOfWeek]]) - count++; - else - wrongDay = YES; - - if (count > repeatCount) - break; - } - + { + // If the rule count is defined, stop once the count is reached. + if ([dayMask occursOnDay: [currentStartDate dayOfWeek]]) + count++; + else + wrongDay = YES; + + if (count > repeatCount) + break; + } + if (wrongDay == NO) { currentEndDate = [currentStartDate addTimeInterval: [firstRange duration]]; - if ([startDate compare: currentStartDate] == NSOrderedAscending || + if ([startDate compare: currentStartDate] == NSOrderedAscending || [startDate compare: currentStartDate] == NSOrderedSame || [startDate compare: currentEndDate] == NSOrderedAscending) { @@ -155,7 +155,7 @@ if (![dayMask occursOnDay: [currentStartDate dayOfWeek]]) wrongDay = YES; } - + if (isFirStart == YES || wrongDay == NO) { r = [NGCalendarDateRange calendarDateRangeWithStartDate: currentStartDate @@ -163,20 +163,20 @@ [ranges addObject: r]; } } - } - + } + currentStartDate = [firStart dateByAddingYears: 0 months: 0 - days: (interval * i)]; - + days: (interval * i)]; + if (repeatCount > 0 && count == repeatCount) - // The count variable is only usefull when a BYDAY constraint is - // defined; when there's no BYDAY constraint, the endDate has been - // adjusted to match the repeat count, if defined. - break; - + // The count variable is only usefull when a BYDAY constraint is + // defined; when there's no BYDAY constraint, the endDate has been + // adjusted to match the repeat count, if defined. + break; + i++; } - + return ranges; } @@ -185,27 +185,27 @@ NSCalendarDate *firStart, *lastInstanceStartDate; NGCalendarDateRange *r; NSArray *instances; - + lastInstanceStartDate = nil; - if ([rrule repeatCount] > 0) + if ([rrule repeatCount] > 0) { firStart = [firstRange startDate]; if ([rrule hasByMask]) - { - // Must perform the complete calculation - r = [NGCalendarDateRange calendarDateRangeWithStartDate: firStart - endDate: [NSCalendarDate distantFuture]]; - instances = [self recurrenceRangesWithinCalendarDateRange: r]; - if ([instances count]) - lastInstanceStartDate = [(NGCalendarDateRange *)[instances lastObject] startDate]; - } + { + // Must perform the complete calculation + r = [NGCalendarDateRange calendarDateRangeWithStartDate: firStart + endDate: [NSCalendarDate distantFuture]]; + instances = [self recurrenceRangesWithinCalendarDateRange: r]; + if ([instances count]) + lastInstanceStartDate = [(NGCalendarDateRange *)[instances lastObject] startDate]; + } else - { - // No BYxxx mask - lastInstanceStartDate = [firStart dateByAddingYears: 0 months: 0 - days: ([rrule repeatInterval] - * ([rrule repeatCount] - 1))]; - } + { + // No BYxxx mask + lastInstanceStartDate = [firStart dateByAddingYears: 0 months: 0 + days: ([rrule repeatInterval] + * ([rrule repeatCount] - 1))]; + } } else lastInstanceStartDate = [super lastInstanceStartDate]; diff --git a/SOPE/NGCards/iCalWeeklyRecurrenceCalculator.m b/SOPE/NGCards/iCalWeeklyRecurrenceCalculator.m index f1ecfae1c..25af97e5e 100644 --- a/SOPE/NGCards/iCalWeeklyRecurrenceCalculator.m +++ b/SOPE/NGCards/iCalWeeklyRecurrenceCalculator.m @@ -1,19 +1,19 @@ /* Copyright (C) 2004-2005 SKYRIX Software AG Copyright (C) 2006-2012 Inverse inc. - + This file is part of SOPE. - + SOPE is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2, or (at your option) any later version. - + SOPE is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. - + You should have received a copy of the GNU Lesser General Public License along with SOPE; see the file COPYING. If not, write to the Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA @@ -21,6 +21,7 @@ */ #import +#import #import "iCalRecurrenceCalculator.h" @@ -38,28 +39,28 @@ - (unsigned) offsetFromSundayForJulianNumber: (long) _jn; - (unsigned) offsetFromSundayForWeekDay: (iCalWeekDay) _weekDay; - (unsigned) offsetFromSundayForCurrentWeekStart; - + - (iCalWeekDay) weekDayForJulianNumber: (long) _jn; @end @implementation iCalWeeklyRecurrenceCalculator - /** - * TODO : Unsupported conditions for WEEKLY recurrences : - * - * BYYEAR - * BYYEARDAY - * BYWEEKNO - * BYMONTH - * BYMONTHDAY - * BYHOUR - * BYMINUTE - * WKST - * - * There's no GUI to defined such conditions, so there's no - * problem for now. - */ +/** + * TODO : Unsupported conditions for WEEKLY recurrences : + * + * BYYEAR + * BYYEARDAY + * BYWEEKNO + * BYMONTH + * BYMONTHDAY + * BYHOUR + * BYMINUTE + * WKST + * + * There's no GUI to defined such conditions, so there's no + * problem for now. + */ - (NSArray *) recurrenceRangesWithinCalendarDateRange: (NGCalendarDateRange *) _r { NSMutableArray *ranges; @@ -68,6 +69,8 @@ unsigned interval; iCalByDayMask *dayMask; + [self logWithFormat: @"Weekly %@", rrule]; + firStart = [firstRange startDate]; startDate = [_r startDate]; endDate = [_r endDate]; @@ -77,9 +80,9 @@ if ([endDate compare: firStart] == NSOrderedAscending) // Range ends before first occurrence return nil; - + interval = [rrule repeatInterval]; - + if ([[rrule byDay] length]) dayMask = [rrule byDayMask]; @@ -87,33 +90,33 @@ if (![rrule isInfinite]) { NSCalendarDate *until, *lastDate; - + lastDate = nil; until = [rrule untilDate]; if (until) - lastDate = until; + lastDate = until; else - { - repeatCount = [rrule repeatCount]; - if (dayMask == nil) - // When there's no BYxxx mask, we can find the date of the last - // occurrence. - lastDate = [firStart dateByAddingYears: 0 months: 0 - days: (interval - * (repeatCount - 1) * 7)]; - } - + { + repeatCount = [rrule repeatCount]; + if (dayMask == nil) + // When there's no BYxxx mask, we can find the date of the last + // occurrence. + lastDate = [firStart dateByAddingYears: 0 months: 0 + days: (interval + * (repeatCount - 1) * 7)]; + } + if (lastDate != nil) - { - if ([lastDate compare: startDate] == NSOrderedAscending) - // Range starts after last occurrence - return nil; - if ([lastDate compare: endDate] == NSOrderedAscending) - // Range ends after last occurence; adjust end date - endDate = lastDate; - } + { + if ([lastDate compare: startDate] == NSOrderedAscending) + // Range starts after last occurrence + return nil; + if ([lastDate compare: endDate] == NSOrderedAscending) + // Range ends after last occurence; adjust end date + endDate = lastDate; + } } - + currentStartDate = [firStart copy]; [currentStartDate autorelease]; ranges = [NSMutableArray array]; @@ -123,74 +126,77 @@ { i = 0; while ([currentStartDate compare: endDate] == NSOrderedAscending || - [currentStartDate compare: endDate] == NSOrderedSame) - { + [currentStartDate compare: endDate] == NSOrderedSame) + { currentEndDate = [currentStartDate addTimeInterval: [firstRange duration]]; - if ([startDate compare: currentStartDate] == NSOrderedAscending || - [startDate compare: currentStartDate] == NSOrderedSame || + if ([startDate compare: currentStartDate] == NSOrderedAscending || + [startDate compare: currentStartDate] == NSOrderedSame || [startDate compare: currentEndDate] == NSOrderedAscending) - { - NGCalendarDateRange *r; - - r = [NGCalendarDateRange calendarDateRangeWithStartDate: currentStartDate - endDate: currentEndDate]; + { + NGCalendarDateRange *r; + + r = [NGCalendarDateRange calendarDateRangeWithStartDate: currentStartDate + endDate: currentEndDate]; [ranges addObject: r]; - } - i++; - currentStartDate = [firStart dateByAddingYears: 0 - months: 0 - days: (interval * i * 7)]; - } + } + i++; + currentStartDate = [firStart dateByAddingYears: 0 + months: 0 + days: (interval * i * 7)]; + } } else { NGCalendarDateRange *r; - + i = [currentStartDate dayOfWeek]; // Set the first day of the week as Sunday and ignore WKST while ([currentStartDate compare: endDate] == NSOrderedAscending || - [currentStartDate compare: endDate] == NSOrderedSame) - { - BOOL isRecurrence = NO; - NSInteger week; + [currentStartDate compare: endDate] == NSOrderedSame) + { + BOOL isRecurrence = NO; + NSInteger week; - if (repeatCount > 0 || - [startDate compare: currentStartDate] == NSOrderedAscending || - [startDate compare: currentStartDate] == NSOrderedSame) - { - // If the rule count is defined, stop once the count is reached. - if ([currentStartDate compare: firStart] == NSOrderedSame) - { - // Always add the start date of the recurring event if within - // the lookup range. - isRecurrence = YES; - } - else - { - week = i / 7; - - if ((week % interval) == 0 && - [dayMask occursOnDay: [currentStartDate dayOfWeek]]) - isRecurrence = YES; - } + if (repeatCount > 0 || + [startDate compare: currentStartDate] == NSOrderedAscending || + [startDate compare: currentStartDate] == NSOrderedSame) + { + // If the rule count is defined, stop once the count is reached. + if ([currentStartDate compare: firStart] == NSOrderedSame) + { + // Always add the start date of the recurring event if within + // the lookup range. + isRecurrence = YES; + } + else + { + week = i / 7; - if (isRecurrence) - { - count++; - if (repeatCount > 0 && count > repeatCount) - break; - currentEndDate = [currentStartDate addTimeInterval: [firstRange duration]]; - r = [NGCalendarDateRange calendarDateRangeWithStartDate: currentStartDate - endDate: currentEndDate]; + if ((week % interval) == 0 && + [dayMask occursOnDay: [currentStartDate dayOfWeek]]) + isRecurrence = YES; + } - if ([_r doesIntersectWithDateRange: r]) - [ranges addObject: r]; - } - } - currentStartDate = [currentStartDate dateByAddingYears: 0 - months: 0 - days: 1]; - i++; - } + if (isRecurrence) + { + count++; + if (repeatCount > 0 && count > repeatCount) + break; + currentEndDate = [currentStartDate addTimeInterval: [firstRange duration]]; + r = [NGCalendarDateRange calendarDateRangeWithStartDate: currentStartDate + endDate: currentEndDate]; + + if ([_r doesIntersectWithDateRange: r]) + { + [ranges addObject: r]; + [self logWithFormat: @"Add range %@ - %@", [r startDate], [r endDate]]; + } + } + } + currentStartDate = [currentStartDate dateByAddingYears: 0 + months: 0 + days: 1]; + i++; + } } return ranges; @@ -207,10 +213,10 @@ { firStart = [firstRange startDate]; r = [NGCalendarDateRange calendarDateRangeWithStartDate: firStart - endDate: [NSCalendarDate distantFuture]]; + endDate: [NSCalendarDate distantFuture]]; instances = [self recurrenceRangesWithinCalendarDateRange: r]; if ([instances count]) - lastInstanceStartDate = [(NGCalendarDateRange *)[instances lastObject] startDate]; + lastInstanceStartDate = [(NGCalendarDateRange *)[instances lastObject] startDate]; } else lastInstanceStartDate = [super lastInstanceStartDate];