]> err.no Git - sope/blobdiff - sope-ical/NGiCal/iCalRecurrenceCalculator.m
improved rrule parser
[sope] / sope-ical / NGiCal / iCalRecurrenceCalculator.m
index 6e048f7eff5387fef2cd0bdf2cf9898549da1a3d..d144efead70b613c7cb8a9b727896ced0033dd9b 100644 (file)
@@ -67,7 +67,7 @@ static Class yearlyCalcClass  = Nil;
 /* factory */
 
 + (id)recurrenceCalculatorForRecurrenceRule:(iCalRecurrenceRule *)_rrule
-         withFirstInstanceCalendarDateRange:(NGCalendarDateRange *)_range
+  withFirstInstanceCalendarDateRange:(NGCalendarDateRange *)_range
 {
   return [[[self alloc] initWithRecurrenceRule:_rrule
                         firstInstanceCalendarDateRange:_range] autorelease];
@@ -87,9 +87,9 @@ static Class yearlyCalcClass  = Nil;
   NSMutableArray           *exDates;
   unsigned                 i, count, rCount;
   
-  ranges = [NSMutableArray array];
-  count  = [_rRules count];
-  for (i = 0; i < count; i++) {
+  ranges = [NSMutableArray arrayWithCapacity:64];
+  
+  for (i = 0, count  = [_rRules count]; i < count; i++) {
     NSArray *rs;
 
     rule = [_rRules objectAtIndex:i];
@@ -102,12 +102,12 @@ static Class yearlyCalcClass  = Nil;
     [ranges addObjectsFromArray:rs];
   }
   
-  if (![ranges count])
+  if ([ranges count] == 0)
     return nil;
   
   /* test if any exceptions do match */
-  count = [_exRules count];
-  for (i = 0; i < count; i++) {
+  
+  for (i = 0, count = [_exRules count]; i < count; i++) {
     NSArray *rs;
 
     rule = [_exRules objectAtIndex:i];
@@ -120,14 +120,14 @@ static Class yearlyCalcClass  = Nil;
     [ranges removeObjectsInArray:rs];
   }
   
-  if (![ranges count])
+  if (![ranges isNotEmpty])
     return nil;
   
   /* exception dates */
 
-  count  = [_exDates count];
-  if (!count) return ranges;
-
+  if ((count = [_exDates count]) == 0)
+    return ranges;
+  
   /* sort out exDates not within range */
 
   exDates = [NSMutableArray arrayWithCapacity:count];
@@ -135,20 +135,19 @@ static Class yearlyCalcClass  = Nil;
     id exDate;
 
     exDate = [_exDates objectAtIndex:i];
-    if (![exDate isKindOfClass:NSCalendarDateClass]) {
+    if (![exDate isKindOfClass:NSCalendarDateClass])
       exDate = [NSCalendarDate calendarDateWithICalRepresentation:exDate];
-    }
+    
     if ([_r containsDate:exDate])
       [exDates addObject:exDate];
   }
 
   /* remove matching exDates from ranges */
 
-  count  = [exDates count];
-  if (!count) return ranges;
-
-  rCount = [ranges count];
-  for (i = 0; i < count; i++) {
+  if ((count = [exDates count]) == 0)
+    return ranges;
+  
+  for (i = 0, rCount = [ranges count]; i < count; i++) {
     NSCalendarDate      *exDate;
     NGCalendarDateRange *r;
     unsigned            k;
@@ -187,19 +186,24 @@ static Class yearlyCalcClass  = Nil;
     calcClass = monthlyCalcClass;
   else if (freq == iCalRecurrenceFrequenceYearly)
     calcClass = yearlyCalcClass;
-
-  [self autorelease];
+  else {
+    [self errorWithFormat:@"unsupported rrule frequency: %@", _rrule];
+    calcClass = Nil;
+    [self release];
+    return nil;
+  }
+  
+  [self autorelease]; // TODO: why autorelease?
   if (calcClass == Nil)
     return nil;
-
-  self = [[calcClass alloc] init];
-  ASSIGN(self->rrule, _rrule);
-  ASSIGN(self->firstRange, _range);
+  
+  if ((self = [[calcClass alloc] init]) != nil) {
+    self->rrule      = [_rrule retain];
+    self->firstRange = [_range retain];
+  }
   return self;  
 }
 
-/* dealloc */
-
 - (void)dealloc {
   [self->firstRange release];
   [self->rrule      release];
@@ -245,14 +249,17 @@ static Class yearlyCalcClass  = Nil;
     case 4:  weekDay = iCalWeekDayThursday;  break;
     case 5:  weekDay = iCalWeekDayFriday;    break;
     case 6:  weekDay = iCalWeekDaySaturday;  break;
-    default: weekDay = iCalWeekDaySunday;    break; /* keep compiler happy */
+    default: 
+      [self errorWithFormat:@"got unexpected weekday: %d", day];
+      weekDay = iCalWeekDaySunday;
+      break; /* keep compiler happy */
   }
   return weekDay;
 }
 
 /* calculation */
 
-- (NSArray *)recurrenceRangesWithinCalendarDateRange:(NGCalendarDateRange *)_r {
+- (NSArray *)recurrenceRangesWithinCalendarDateRange:(NGCalendarDateRange *)_r{
   return nil; /* subclass responsibility */
 }
 - (BOOL)doesRecurrWithinCalendarDateRange:(NGCalendarDateRange *)_range {