Я хочу получить все события из определенного календаря в моем приложении. Я создал календарь и тестовые события в своем приложении (для создания пользовательских календарей требуется iOS 5.0 или более поздняя версия). Если я запускаю приложение на своем устройстве и затем проверяю приложение системного календаря, тогда мой календарь и мои созданные события отображаются правильно.
Теперь я хочу, чтобы мое приложение считывало все эти события из этого пользовательского календаря. Мои события создаются с startDate и endDate, установленными в NOW (NSDate назначается без указания timeInterval).
NSDate *startDate = [NSDate dateWithTimeIntervalSinceNow:- 60 * 60 * 24 * (365 * 4 + 1)];
NSDate *endDate = [NSDate dateWithTimeIntervalSinceNow:60 * 60 * 24 * 365 * 25];
NSArray *calendarList = [NSArray arrayWithObjects:tmpCal, nil];
NSPredicate *datePredicate = [store predicateForEventsWithStartDate:startDate endDate:endDate calendars:calendarList];
NSArray *eventList = [store eventsMatchingPredicate:datePredicate];
Как видите, я указываю временной интервал, в котором должны быть результирующие события. Как вы можете видеть, дата окончания - через 25 лет, тогда как дата начала - 4 года (плюс один день для високосного года) в прошлом. Если я сделаю запрос в EKEventstore таким образом, я получу ранее добавленные события. Сложная часть начинается, если я хочу указать дату начала (или несколько дней или лет) в прошлом. Затем, внезапно, никакие события не возвращаются.
NSDate *startDate = [NSDate dateWithTimeIntervalSinceNow:- 60 * 60 * 24 * (365 * 4 + 2)];
Есть ли предел для отрицательных значений NSTimeInterval в NSPredicate? Я не нашел никаких задокументированных ограничений. У меня ушло около 2 часов, чтобы понять, почему я не получаю никаких событий (изначально я хотел диапазон 5 лет в прошлом и 5 лет в будущем). В чем причина этого любопытного поведения? Есть идеи?
/ редактировать 04/11/2012
После создания некоторых событий с начальной датой 31.03.2012 и 20.04.2012 кажется, что выборка событий по датам, определенным с интервалами с настоящего момента, ограничена интервалом в 4 года. Настроив дату начала (установив день начала на день раньше) в приведенном выше коде, я смог получать события до 31.03.2012, но не позже. Удаление этой корректировки привело к получению событий от 31.03.2012 и 04.01.2012 (но не от 20.04.2012). После второй корректировки (установив дату начала 20 дней спустя) я получил даже эти будущие события.
Я не могу указать, почему существует такое ограничение. Возможно, существуют некоторые внутренние расчеты, которые могут привести к переполнению хранилища использованных значений. Просто предположение.
Затем я направляюсь к Apple примерам. На первый взгляд я не хотел использовать данный код в Руководстве по программированию EKEvent от Apple. Он не выглядел таким маленьким и милым, как мой, но после стольких проблем я сделал ему попытку.
CFGregorianDate gregorianStartDate, gregorianEndDate;
CFTimeZoneRef timeZone = CFTimeZoneCopySystem();
gregorianStartDate.hour = 0;
gregorianStartDate.minute = 0;
gregorianStartDate.second = 0;
gregorianStartDate.day = 1;
gregorianStartDate.month = 4;
gregorianStartDate.year = 2008;
NSDateComponents *components = [[NSCalendar currentCalendar] components:NSDayCalendarUnit | NSMonthCalendarUnit | NSYearCalendarUnit fromDate:[NSDate date]];
gregorianEndDate.hour = 23;
gregorianEndDate.minute = 59;
gregorianEndDate.second = 59;
gregorianEndDate.day = [components day];
gregorianEndDate.month = [components month];
gregorianEndDate.year = [components year] + 1;
NSDate *startDate = [NSDate dateWithTimeIntervalSinceReferenceDate:CFGregorianDateGetAbsoluteTime(gregorianStartDate, timeZone)];
NSDate *endDate = [NSDate dateWithTimeIntervalSinceReferenceDate:CFGregorianDateGetAbsoluteTime(gregorianEndDate, timeZone)];
CFRelease(timeZone);
Таким образом, я получаю все события, начиная с 01.04.2008 до СЕЙЧАС () + 1 год. Что ж, оказалось, что здесь используется то же ограничение :( Корректировка даты начала привела к получению только части моих событий, пока последние события не были в диапазоне этих 4 лет.
Интенсивные исследования показали, что такое поведение существует очень долгое время: Извлечение всех событий из EventStore EventKit iOS