Demo地址
一启绰、簡(jiǎn)介
Important:An iOS app linked on or after iOS 10.0 must include in itsInfo.plistfile the usage description keys for the types of data it needs to access or it will crash. To access Reminders and Calendar data specifically, it must includeNSRemindersUsageDescriptionandNSCalendarsUsageDescription, respectively.
To access the user’s Calendar data
提示:iOS 10 之后如果app 想要訪問日歷和提醒事項(xiàng),我們必須在 我們的app 的Info.plist文件中添加NSRemindersUsageDescription和NSCalendarsUsageDescription的key否則app會(huì)閃退。
The EventKit framework helps you access users’ Calendar and Reminders information. Although two different apps display users’ calendar and reminder data, the same framework manipulates the data. Similarly, the database that stores this data, called the Calendar database, holds both calendar and reminder information.
EventKit 可以幫助你訪問用戶的日歷和提醒事項(xiàng)的信息旬痹,日歷和提醒事項(xiàng)使用相同的框架來訪問一個(gè)叫做Calendar database 的數(shù)據(jù)庫。
EventKit not only allows your app to retrieve users’ existing calendar and reminder data, but it also lets your app create new events and reminders for any of their calendars. In addition, EventKit lets users edit and delete their events and reminders (collectively known as “calendar items”). More advanced tasks, such as adding alarms or specifying recurring events, can be achieved with EventKit as well. If a change to the Calendar database occurs from outside of your app, EventKit is able to detect the change by notification so your app can act appropriately. Changes made to calendar items with EventKit are automatically synced to the associated calendar (CalDAV, Exchange, and so on).
This document describes EventKit concepts and common programming tasks. You should read this document if you want to display or edit calendar events and/or reminder data from within your app. EventKit provides limited access to a user’s Calendar database; it does not include everything that would be desired for implementing a full-featured calendar or reminder app, such as adding attendees or accounts.
EventKit? 允許你的app 訪問已經(jīng)存在于日歷和提醒里面的事件弄诲,同時(shí)也允許你的app創(chuàng)建一個(gè)提醒事件添加到日歷或者提醒中菱鸥。用戶可以編輯刪除日歷和提醒里面的事件。EventKit 還可以添加鬧鈴抚垄,和重復(fù)提醒的事件蜕窿。
注意:EKEvent 和 EKReminder都繼承于EKCalendarItem, EKCalendarItem類是日歷事件和提醒的抽象超類,此類提供常用的屬性和方法來訪問日歷項(xiàng)的屬性糯崎,例如設(shè)置日歷的功能主到,標(biāo)題和位置,以及支持附加注釋阴挣,顯示與會(huì)者气堕,設(shè)置多個(gè)鬧鐘和指定重復(fù)規(guī)則。EKCalendarItem 的calendarItemIdentifier 是它唯一標(biāo)示屯吊,使用EKCalendarItem *item = [store calendarItemWithIdentifier:identifer];可以通過一個(gè)唯一標(biāo)示獲取一個(gè)EKCalendarItem對(duì)象送巡。
二、讀取日歷和提醒中已存在的事件
??注意:因?yàn)?EventStore 是 Calendar database 的數(shù)據(jù)庫引擎盒卸,所以應(yīng)該盡量少的對(duì)他進(jìn)行創(chuàng)建和銷毀骗爆,所以推薦使用EventStore的時(shí)候使用單例模式
You can fetch, create, edit, and delete events from a user’s Calendar database using theEKEventStoreclass. You can fetch a custom set of events that match a predicate you provide, or you can fetch an individual event by its unique identifier. After you fetch an event, you can access its associated calendar information with the properties of theEKEventclass. Like wise, you can modify its calendar information by setting the properties of theEKEventclass.?
你可以使用EKEventStoreclass進(jìn)行 查詢、創(chuàng)建蔽介、編輯和刪除 用戶存于 Calendar database 中的事件摘投,你可以使用謂詞來查詢出符合條件的事件集或者使用一個(gè)唯一標(biāo)示來查詢一個(gè)指定的事件。獲取事件之后你可以對(duì)他進(jìn)行一些操作虹蓄。
1犀呼、使用謂詞查詢?nèi)諝v里面的某個(gè)時(shí)間范圍內(nèi)的事件
It’s common to fetch events that fall within a date range. TheEKEventStoremethodeventsMatchingPredicate:fetches all events that fall within the date range specified in the predicate you provide.(EKEventStore 可以查詢謂詞所提供的日期范圍內(nèi)的事件)。?
示例代碼如下
+(NSArray*)fetchEventsWithStartDate:(NSDate*)startDate endDate:(NSDate*)enDate{
EKEventStore*store = [STCalendarReminderToolshareinstance];
NSPredicate*predicate = [storepredicateForEventsWithStartDate:startDateendDate:enDatecalendars:nil];
NSArray*events = [storeeventsMatchingPredicate:predicate];
NSIntegeri =1;
for(EKEvent*eventinevents) {
NSLog(@"第%zd個(gè)提醒%@",i,event);
i++;
}
returnevents;
}
2薇组、使用唯一標(biāo)示來查詢事件
Using Unique Identifiers
If you know the event’s unique identifier because you fetched it previously with a predicate, you can use theEKEventStoremethodeventWithIdentifier:to fetch the event. If it is a recurring event, this method will return the first occurrence of the event. You can get an event’s unique identifier with theeventIdentifierproperty.
??這種方式只能用來查詢?nèi)諝v里面的事件
?示例代碼:
+(EKEvent*)fetchEventWithIdentifer:(NSString*)eventidentifer{
EKEventStore*store = [STCalendarReminderToolshareinstance];
EKEvent*event = [storeeventWithIdentifier:eventidentifer];
returnevent;
}
三外臂、向日歷中添加一個(gè)新的事件
Create a new event with the eventWithEventStore: method of the EKEvent class.
You can edit the details of a new event or an event you previously fetched from the Calendar database by setting the event’s corresponding properties. Some of the details you can edit include:
The event’s title with the title property
The event’s start and end dates with the startDate and endDate properties
The calendar with which the event is associated with the calendar property
The alarms associated with the event with the alarms property (see Configuring Alarms for more details)
The event’s recurrence rule, if it is a repeating event, with the recurrenceRules property (see Creating Recurring Events for more details)
示例代碼如下:
/**
* STCalendarReminderToolSaveSuccessBlock
* eventIdentifier
*/
typedef void (^STCalendarReminderToolSaveSuccessBlock)(NSString* eventIdentifier);
typedef void (^STCalendarReminderToolSaveFailBlock)(NSError *err);
/** 向日歷添加一個(gè)事件
* title? 事件標(biāo)題
* notes? 事件備注
* location 事件地址
* startDate 開始日期
* endDate? 結(jié)束日期
* alarms 鬧鐘
* availability 事件調(diào)度
*/
+(void)saveEventWithTitle:(NSString *)title? ? ? ? ? ? ? ? ?
?? notes:(NSString *)notes? ? ? ? ? ? ?
?? location:(NSString *)location? ? ? ? ? ?
?? ? startDate:(NSDate *)startDate? ? ? ? ? ?
?? ? ? endDate:(NSDate *)endDate? ? ? ? ? ? ? ?
?? alarms:(NSArray*)alarms{
URL:(NSURL *)URL
availability:(EKEventAvailability)availability
successBlock:(STCalendarReminderToolSaveSuccessBlock)successBlock
failBlock:(STCalendarReminderToolSaveFailBlock)failBlock{
EKEventStore *store = [STCalendarReminderTool shareinstance];
[store requestAccessToEntityType:EKEntityTypeEvent
completion:
^(BOOL granted, NSError *error) {
dispatch_async(dispatch_get_main_queue(), ^{
if (error) {
//錯(cuò)誤信息
return;
}
if (!granted) {
//被用戶拒絕,不允許訪問日歷
return;
}
EKEvent *event = [EKEvent eventWithEventStore:store];
event.title = title;
event.notes = notes;
event.availability = availability;
event.startDate = startDate;
event.endDate = endDate;
event.location? = location;
event.alarms = alarms;
event.calendar = store.defaultCalendarForNewEvents;
event.URL = URL;
NSError *err = nil;
[store saveEvent:event span:EKSpanThisEvent error:&err];
if (!err) {
if (successBlock) {
successBlock(event.eventIdentifier);
}
}else{
if (failBlock) {
failBlock(err);
}
}
NSLog(@"eventIdentifier %@",event.eventIdentifier);
});
}];
}
四律胀、刪除事件
+(BOOL)deleteEventWithEventIdentifier:(NSString *)eventIdentifier{
EKEventStore *store = [STCalendarReminderTool shareinstance];
EKEvent *event = [store eventWithIdentifier:eventIdentifier];
// YES立即刪除事件;否則宋光,更改將批處理,直到調(diào)用commit:方法炭菌。
return? [store removeEvent:event span:EKSpanThisEvent commit:YES error:nil];
}
五罪佳、查詢提醒
5.1 使用謂詞查詢一個(gè)時(shí)間范圍里的提醒
EKEventStore *store = [STCalendarReminderTool shareinstance];
NSPredicate *predicate = [store predicateForIncompleteRemindersWithDueDateStarting:starDate
ending:endDate
calendars:[store calendarsForEntityType:EKEntityTypeReminder]];
[store fetchRemindersMatchingPredicate:predicate completion:^(NSArray *reminders) {
}];
5.2使用謂詞 查詢所有的提醒
EKEventStore *store? ? ? = [STCalendarReminderTool shareinstance];
NSPredicate? *predicate? = [store predicateForRemindersInCalendars:nil];
[store fetchRemindersMatchingPredicate:predicate completion:^(NSArray *reminders) {
NSInteger i = 1;
for (EKReminder *reminder in reminders) {
}
}];
5.3 使用唯一標(biāo)示查詢提醒
EKReminder 是繼承于EKCalendarItem的(??我這里也沒有查到用唯一標(biāo)示查詢返回EKReminder的方法相關(guān)資料,我的做法是查詢到EKCalendarItem然后把它強(qiáng)轉(zhuǎn)成EKReminder)黑低,使用這個(gè)方法也可以查詢?nèi)諝v里面的事件赘艳。
+(EKCalendarItem *)fetchReminderWithIdentier:(NSString *)identifer{
EKEventStore *store = [STCalendarReminderTool shareinstance];
EKCalendarItem *item = [store calendarItemWithIdentifier:identifer];
NSLog(@"item? item %@",item);
return item;
}
六、添加新的提醒和刪除提醒
6.1添加新的提醒
示例代碼:
/**
* STCalendarReminderToolSaveSuccessBlock
* eventIdentifier
*/
typedef void (^STCalendarReminderToolSaveSuccessBlock)(NSString* eventIdentifier);
typedef void (^STCalendarReminderToolSaveFailBlock)(NSError *err);
/*
* title? 事件標(biāo)題
* notes? 事件備注
* startDate 開始日期
* endDate? 結(jié)束日期
* alarms 鬧鐘
* priority 事件調(diào)度(1-4 高 5中? 6-9低? 0 不設(shè)置)
* completed
*/
+(void)saveEventIntoReminderWithTitle:(NSString *)title
notes:(NSString *)notes
startDate:(NSDate *)startDate
endDate:(NSDate *)endDate
alarm:(EKAlarm *)alarm
priority:(NSInteger)priority
completed:(BOOL)completed
successBlock:(STCalendarReminderToolSaveSuccessBlock)successBlock
failBlock:(STCalendarReminderToolSaveFailBlock)failBlock{
EKEventStore *store = [STCalendarReminderTool shareinstance];
[store requestAccessToEntityType:EKEntityTypeReminder
completion:
^(BOOL granted, NSError *error) {
dispatch_async(dispatch_get_main_queue(), ^{
if (error) {
if (failBlock) {
failBlock(error);
}
return;
}
if (!granted) {
//被用戶拒絕克握,不允許訪問提醒
return;
}
EKReminder *reminder = [EKReminder reminderWithEventStore:store];
[reminder setCalendar:[store defaultCalendarForNewReminders]];
reminder.title? ? ? = title;
reminder.notes? ? ? = notes;
reminder.completed? = completed;
reminder.priority? ? = priority;
[reminder addAlarm:alarm];
NSCalendar *calender = [NSCalendar currentCalendar];
[calender setTimeZone:[NSTimeZone systemTimeZone]];
NSInteger flags? ? ? = NSCalendarUnitYear | NSCalendarUnitMonth |
NSCalendarUnitDay |NSCalendarUnitHour | NSCalendarUnitMinute |
NSCalendarUnitSecond;
NSDateComponents* startDateComp = [calender components:flags fromDate:startDate];
startDateComp.timeZone = [NSTimeZone systemTimeZone];
reminder.startDateComponents = startDateComp;
NSDateComponents* endDateComp = [calender components:flags fromDate:startDate];
endDateComp.timeZone? = [NSTimeZone systemTimeZone];
reminder.dueDateComponents = endDateComp;
NSError *err;
[store saveReminder:reminder commit:YES error:&err];
if (!err) {
if (successBlock) {
successBlock(reminder.calendarItemIdentifier);
}
}else{
if (failBlock) {
failBlock(err);
}
}
});
}];
}
6.2 刪除一個(gè)提醒
+(BOOL)deleteReminderWithIdentifer:(NSString *)identifier{
EKEventStore *store = [STCalendarReminderTool shareinstance];
EKCalendarItem *item = [store calendarItemWithIdentifier:identifier];
EKReminder *reminder = (EKReminder *)item;
return? [store removeReminder:reminder commit:YES error:nil];
}
七蕾管、使用系統(tǒng)提供的視圖控制器添加、修改或刪除事件
先導(dǎo)入#import <EventKitUI/EventKitUI.h>
7.1添加一個(gè)事件
EKEventEditViewController *editVC = [[EKEventEditViewController alloc] init];
editVC.eventStore = [STCalendarReminderTool shareStoreinstance];
editVC.editViewDelegate = self;
[self presentViewController:editVC animated:YES completion:nil];
遵循EKEventEditViewDelegate 代理
實(shí)現(xiàn)代理方法
#pragma -mark EKEventEditViewDelegate
-(void)eventEditViewController:(EKEventEditViewController *)controller didCompleteWithAction:(EKEventEditViewAction)action{
[self dismissViewControllerAnimated:YES completion:^{
}];
}
7.2 修改事件
如果要修改一個(gè)事件直接把他傳給EKEventEditViewController菩暗,如下:
EKEventEditViewController *editVC = [[EKEventEditViewController alloc] init];
editVC.eventStore = [STCalendarReminderTool shareStoreinstance];
editVC.editViewDelegate = self;
editVC.event? ? ? = event;
[self presentViewController:editVC animated:YES completion:nil];
其他操作和新加一個(gè)事件的一致娇掏。
八、總結(jié)
寫的有不好的地方希望大家指出勋眯,我會(huì)修正的婴梧,大家有什么看不明白的也可以在評(píng)論里面提問下梢,我會(huì)盡力解答。