2 Copyright (C) 2004-2005 SKYRIX Software AG
4 This file is part of SOPE.
6 SOPE is free software; you can redistribute it and/or modify it under
7 the terms of the GNU Lesser General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
11 SOPE is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
14 License for more details.
16 You should have received a copy of the GNU Lesser General Public
17 License along with SOPE; see the file COPYING. If not, write to the
18 Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA
22 #include "iCalRepeatableEntityObject.h"
23 #include <NGExtensions/NGCalendarDateRange.h>
24 #include "iCalRecurrenceRule.h"
25 #include "iCalRecurrenceCalculator.h"
28 @implementation iCalRepeatableEntityObject
31 return [super version] + 0 /* v1 */;
34 NSAssert2([super version] == 1,
35 @"invalid superclass (%@) version %i !",
36 NSStringFromClass([self superclass]), [super version]);
40 [self->rRules release];
41 [self->exRules release];
42 [self->exDates release];
48 - (id)copyWithZone:(NSZone *)_zone {
49 iCalRepeatableEntityObject *new;
51 new = [super copyWithZone:_zone];
53 new->rRules = [self->rRules copyWithZone:_zone];
54 new->exRules = [self->exRules copyWithZone:_zone];
55 new->exDates = [self->exDates copyWithZone:_zone];
62 - (void)removeAllRecurrenceRules {
63 [self->rRules removeAllObjects];
65 - (void)addToRecurrenceRules:(id)_rrule {
66 if (_rrule == nil) return;
67 if (self->rRules == nil)
68 self->rRules = [[NSMutableArray alloc] initWithCapacity:1];
69 [self->rRules addObject:_rrule];
71 - (void)setRecurrenceRules:(NSArray *)_rrules {
72 if (_rrules == self->rRules)
74 [self->rRules release];
75 self->rRules = [_rrules mutableCopy];
77 - (BOOL)hasRecurrenceRules {
78 return [self->rRules count] > 0 ? YES : NO;
80 - (NSArray *)recurrenceRules {
84 - (void)removeAllExceptionRules {
85 [self->exRules removeAllObjects];
87 - (void)addToExceptionRules:(id)_rrule {
88 if (_rrule == nil) return;
89 if (self->exRules == nil)
90 self->exRules = [[NSMutableArray alloc] initWithCapacity:1];
91 [self->exRules addObject:_rrule];
93 - (void)setExceptionRules:(NSArray *)_rrules {
94 if (_rrules == self->exRules)
96 [self->exRules release];
97 self->exRules = [_rrules mutableCopy];
99 - (BOOL)hasExceptionRules {
100 return [self->exRules count] > 0 ? YES : NO;
102 - (NSArray *)exceptionRules {
103 return self->exRules;
106 - (void)removeAllExceptionDates {
107 [self->exDates removeAllObjects];
109 - (void)setExceptionDates:(NSArray *)_exDates {
110 if (_exDates == self->exDates)
112 [self->exDates release];
113 self->exDates = [_exDates mutableCopy];
115 - (void)addToExceptionDates:(id)_date {
116 if (_date == nil) return;
117 if (self->exDates == nil)
118 self->exDates = [[NSMutableArray alloc] initWithCapacity:4];
119 [self->exDates addObject:_date];
121 - (BOOL)hasExceptionDates {
122 return [self->exDates count] > 0 ? YES : NO;
124 - (NSArray *)exceptionDates {
125 return self->exDates;
130 - (BOOL)isRecurrent {
131 return [self hasRecurrenceRules] ? YES : NO;
136 - (BOOL)isWithinCalendarDateRange:(NGCalendarDateRange *)_range
137 firstInstanceCalendarDateRange:(NGCalendarDateRange *)_fir
141 ranges = [self recurrenceRangesWithinCalendarDateRange:_range
142 firstInstanceCalendarDateRange:_fir];
143 return [ranges count] > 0;
146 - (NSArray *)recurrenceRangesWithinCalendarDateRange:(NGCalendarDateRange *)_r
147 firstInstanceCalendarDateRange:(NGCalendarDateRange *)_fir
149 return [iCalRecurrenceCalculator recurrenceRangesWithinCalendarDateRange:_r
150 firstInstanceCalendarDateRange:_fir
151 recurrenceRules:self->rRules
152 exceptionRules:self->exRules
153 exceptionDates:self->exDates];
157 /* this is the outmost bound possible, not necessarily the real last date */
158 - (NSCalendarDate *)lastPossibleRecurrenceStartDateUsingFirstInstanceCalendarDateRange:(NGCalendarDateRange *)_r
160 NSCalendarDate *date;
163 count = [self->rRules count];
168 for (i = 0; i < count; i++) {
169 iCalRecurrenceRule *rule;
170 iCalRecurrenceCalculator *calc;
171 NSCalendarDate *rdate;
173 rule = [self->rRules objectAtIndex:i];
174 if ([rule isInfinite])
175 return nil; /* rule is not bound, hence no limit */
176 calc = [iCalRecurrenceCalculator recurrenceCalculatorForRecurrenceRule:rule
177 withFirstInstanceCalendarDateRange:_r];
178 rdate = [[calc lastInstanceCalendarDateRange] startDate];
179 if (date == nil || [date compare:rdate] == NSOrderedAscending)