]> err.no Git - sope/blob - sope-ical/NGiCal/NSCalendarDate+ICal.m
bugfixes for cycle calculation, modified implementations with future extensions in...
[sope] / sope-ical / NGiCal / NSCalendarDate+ICal.m
1 /*
2   Copyright (C) 2000-2005 SKYRIX Software AG
3
4   This file is part of SOPE.
5
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
9   later version.
10
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.
15
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
19   02111-1307, USA.
20 */
21
22 #include "NSCalendarDate+ICal.h"
23 #include "common.h"
24
25 static NSTimeZone *gmt = nil;
26 static inline void _setupGMT(void) {
27   if (gmt == nil)
28     gmt = [[NSTimeZone timeZoneWithAbbreviation:@"GMT"] retain];
29 }
30
31 @implementation NSCalendarDate(ICalValue)
32
33 /* represention */
34
35 static NSString *gmtcalfmt = @"%Y%m%dT%H%M00Z";
36
37 - (NSString *)icalStringInGMT {
38   NSTimeZone *oldtz;
39   NSString   *s;
40   _setupGMT();
41   
42   /* set GMT as timezone */
43   oldtz = [[self timeZone] retain];
44   if (oldtz == gmt) {
45     [oldtz release];
46     oldtz = nil;
47   }
48   else {
49     [self setTimeZone:gmt];
50   }
51   
52   /* calc string */
53   s = [self descriptionWithCalendarFormat:gmtcalfmt];
54   
55   /* restore old timezone */
56   if (oldtz) {
57     [self setTimeZone:oldtz];
58     [oldtz release];
59   }
60   
61   return s;
62 }
63
64 - (NSString *)icalStringWithTimeZone:(NSTimeZone *)_tz {
65   _setupGMT();
66   
67   if (_tz == gmt || _tz == nil)
68     return [self icalStringInGMT];
69   else if ([_tz isEqual:gmt])
70     return [self icalStringInGMT];
71   else {
72     /* not in GMT */
73     NSLog(@"WARNING(%s): arbitary timezones not supported yet: %@",
74           __PRETTY_FUNCTION__, _tz);
75     return [self icalStringInGMT];
76   }
77 }
78
79 - (NSString *)icalString {
80   _setupGMT();
81   return [self icalStringWithTimeZone:gmt];
82 }
83
84 @end /* NSDate(ICalValue) */
85
86
87 #ifndef ABS
88 #define ABS(a) ((a) < 0 ? -(a) : (a))
89 #endif
90
91 @implementation NSCalendarDate (iCalRecurrenceCalculatorExtensions)
92
93 - (unsigned)yearsBetweenDate:(NSCalendarDate *)_date {
94   return ABS([self yearOfCommonEra] - [_date yearOfCommonEra]);
95 }
96
97 - (unsigned)monthsBetweenDate:(NSCalendarDate *)_date {
98   NSCalendarDate     *start, *end;
99   NSComparisonResult order;
100   int                yDiff;
101   
102   order = [self compare:_date];
103   if (order == NSOrderedSame)
104     return 0;
105   else if (order == NSOrderedAscending) {
106     start = self;
107     end   = _date;
108   }
109   else {
110     start = _date;
111     end   = self;
112   }
113   yDiff = [end yearOfCommonEra] - [start yearOfCommonEra];
114   if (yDiff > 0) {
115     unsigned monthsRemaining, monthsToGo;
116     
117     monthsRemaining = 12 - [start monthOfYear];
118     monthsToGo      = [end monthOfYear];
119     yDiff          -= 1;
120     return monthsRemaining + monthsToGo + (12 * yDiff);
121   }
122   /* start and end in same year, calculate plain diff */
123   return [end monthOfYear] - [start monthOfYear];
124 }
125
126 - (unsigned)daysBetweenDate:(NSCalendarDate *)_date {
127   return ABS([self julianNumber] - [_date julianNumber]);
128 }
129 @end /* NSCalendarDate (iCalRecurrenceCalculatorExtensions) */