I'm new to iOS programming and I am working on a easy project that lists holidays from a given city and gives users the ability to add those events to the iCal default calendar.
The issue is: how to check if there is already an event with same properties (title and start date for example) in the user's calendar. This could happen if the action button (used to add an event to iCal) is pressed more than once. In such a situation, I don't want two or more identical events being created in iCal.
I have tried to use NSPredicate but I am totally lost on how to get it sorted.
Any help would come be appreciated! Thanks in advance.
Bellow is my event-adding code just to make things clear. In this case a user is adding multiple events from a list (all local holidays for example).
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];
}
Summary
At some point in your instance method (probably during the for loop) you will want to create an NSPredicate based on [allHolidayDates objectAtIndex:i]
to return an array that you loop through to check if [allHolidayNames objectAtIndex:i]
is present in the returned events.
Example code
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];
}
}
Tips
To help visualise the data, especially the contents of arrays and objects, try using
NSLog
. This will output the contents of an object to the console to help you understand the data structures a bit better.NSLog("eventsOnHolidayDate = %@",eventsOnHolidayDate);
Note that
eventsMatchingPredicate
will block the main thread whilst retrieving events. If your doing this multiple times in a row it could impact on the user experience. You should consider usingenumerateEventsMatchingPredicate:usingBlock:
(outside the scope of this question).
来源:https://stackoverflow.com/questions/9333886/checking-for-duplicated-items-before-adding-new-event-in-ios-ekeventstore