我是iOS编程的新手,我正在开展一个简单的项目,列出来自特定城市的假期,并让用户能够将这些事件添加到iCal默认日历中。
问题是:如何检查用户日历中是否已存在具有相同属性(例如标题和开始日期)的事件。如果多次按下操作按钮(用于向iCal添加事件),则可能发生这种情况。在这种情况下,我不希望在iCal中创建两个或更多相同的事件。
我曾尝试使用NSPredicate,但我完全迷失了如何对它进行排序。
任何帮助都会受到赞赏! 提前致谢。
Bellow是我的事件添加代码,只是为了让事情变得清晰。在这种情况下,用户正在从列表中添加多个事件(例如,所有本地假日)。
for (int i = 0; i<[allHolidayNames count]; ++i) {
// ------ EVENT MANIPULATION ------
EKEventStore *eventStore = [[EKEventStore alloc] init];
EKEvent *addEvent = [EKEvent eventWithEventStore:eventStore];
addEvent.title = [allHolidayNames objectAtIndex:i];
addEvent.startDate = [allHolidayDates objectAtIndex:i];
addEvent.allDay = YES;
[addEvent setCalendar:[eventStore defaultCalendarForNewEvents]];
[eventStore saveEvent:addEvent span:EKSpanThisEvent commit:YES error:nil];
}
答案 0 :(得分:15)
在实例方法的某个时刻(可能在for循环期间),您需要创建一个基于[allHolidayDates objectAtIndex:i]
的NSPredicate来返回一个循环的数组,以检查[allHolidayNames objectAtIndex:i]
是否存在于返回的事件。
for (int i = 0; i<[allHolidayNames count]; ++i) {
// ------ EVENT MANIPULATION ------
EKEventStore *eventStore = [[EKEventStore alloc] init];
NSPredicate *predicateForEventsOnHolidayDate = [eventStore predicateForEventsWithStartDate:[allHolidayDates objectAtIndex:i] endDate:[allHolidayDates objectAtIndex:i] calendars:nil]; // nil will search through all calendars
NSArray *eventsOnHolidayDate = [eventStore eventsMatchingPredicate:predicateForEventsOnHolidayDate]
BOOL eventExists = NO;
for (EKEvent *eventToCheck in eventsOnHolidayDate) {
if ([eventToCheck.title isEqualToString:[allHolidayNames objectAtIndex:i]]) {
eventExists = YES;
}
}
if (eventExists == NO) {
EKEvent *addEvent = [EKEvent eventWithEventStore:eventStore];
addEvent.title = [allHolidayNames objectAtIndex:i];
addEvent.startDate = [allHolidayDates objectAtIndex:i];
addEvent.allDay = YES;
[addEvent setCalendar:[eventStore defaultCalendarForNewEvents]];
[eventStore saveEvent:addEvent span:EKSpanThisEvent commit:YES error:nil];
}
}
为了帮助可视化数据,尤其是数组和对象的内容,请尝试使用NSLog
。这会将对象的内容输出到控制台,以帮助您更好地理解数据结构。
NSLog(“eventsOnHolidayDate =%@”,eventsOnHolidayDate);
请注意,eventsMatchingPredicate
会在检索事件时block the main thread。如果您连续多次这样做,可能会影响用户体验。您应该考虑使用enumerateEventsMatchingPredicate:usingBlock:
(超出此问题的范围)。