返回 导航

Swift

hangge.com

Swift - 使用EventKit获取系统日历事件,添加事件

作者:hangge | 2015-03-04 14:46
通过 EventKit 可以对 iOS 日历事件进行读取,添加等操作。但网上找到的都是使用 Objective-C 来编写的。
下面提供一个 Swift 版的样例,演示如何添加一个事件以及获取所有的事件列表。

1,首先配置info.plist
从 iOS10 起,苹果增强对用户的安全和隐私的保护。在申请很多私有权限的时候都需要添加描述。我们这里需要访问日历,那就需要在 info.plist 添加日历相关的描述字段。
字段名:NSCalendarsUsageDescription 。描述随便,我这里就写“App需要您的同意,才能访问日历”。

2,代码如下(已升级至Swift3)
import UIKit
import EventKit

class ViewController: UIViewController {
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        let eventStore = EKEventStore()
        
        // 'EKEntityType.reminder' or 'EKEntityType.event'
        eventStore.requestAccess(to: .event, completion: {
            granted, error in
            if (granted) && (error == nil) {
                print("granted \(granted)")
                print("error  \(error)")
                
                // 新建一个事件
                let event:EKEvent = EKEvent(eventStore: eventStore)
                event.title = "新增一个测试事件"
                event.startDate = Date()
                event.endDate = Date()
                event.notes = "这个是备注"
                event.calendar = eventStore.defaultCalendarForNewEvents
                
                do{
                    try eventStore.save(event, span: .thisEvent)
                    print("Saved Event")
                }catch{}
                
                // 获取所有的事件(前后90天)
                let startDate = Date().addingTimeInterval(-3600*24*90)
                let endDate = Date().addingTimeInterval(3600*24*90)
                let predicate2 = eventStore.predicateForEvents(withStart: startDate,
                                                               end: endDate, calendars: nil)
                
                print("查询范围 开始:\(startDate) 结束:\(endDate)")
                
                if let eV = eventStore.events(matching: predicate2) as [EKEvent]! {
                    for i in eV {
                        print("标题  \(i.title)" )
                        print("开始时间: \(i.startDate)" )
                        print("结束时间: \(i.endDate)" )
                    }
                }
            }
        })
    }
    
    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
    }
}
运行结果:
      

3,功能改进:只查询本地日历中的事件
从上面的运行结果可以看出,我们把系统中所有的日历事件都查询出来了,不管是本地日历事件(如果有iCloud同步则是iCloud日历),还是系统自带的节假日、生日日历事件。如果我们只关注本地日历事件,可以在查询的时候添加个日历参数即可。代码如下。
import UIKit
import EventKit

class ViewController: UIViewController {
    
    let eventStore = EKEventStore()
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        // 请求日历事件
        eventStore.requestAccess(to: .event, completion: {
            granted, error in
            if (granted) && (error == nil) {
                print("granted \(granted)")
                print("error  \(error)")
                
                //获取本地日历(剔除节假日,生日等其他系统日历)
                let calendars = self.eventStore.calendars(for: .event).filter({
                    (calender) -> Bool in
                    return calender.type == .local || calender.type == .calDAV
                })
                
                // 获取所有的事件(前后90天)
                let startDate = Date().addingTimeInterval(-3600*24*90)
                let endDate = Date().addingTimeInterval(3600*24*90)
                let predicate2 = self.eventStore.predicateForEvents(withStart: startDate,
                                                               end: endDate, calendars: calendars)
                
                print("查询范围 开始:\(startDate) 结束:\(endDate)")
                
                if let eV = self.eventStore.events(matching: predicate2) as [EKEvent]! {
                    for i in eV {
                        print("标题  \(i.title)" )
                        print("开始时间: \(i.startDate)" )
                        print("结束时间: \(i.endDate)" )
                    }
                }
            }
        })
    }
    
    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
    }
}
运行结果:

评论

全部评论(3)

回到顶部