プログラムでiPhoneカレンダーにカスタムイベントを追加する


回答:


166

Apple Documentationに基づいて、これはiOS 6.0の時点で少し変更されました。

1) "requestAccessToEntityType:completion:"を介してユーザーのカレンダーへのアクセスをリクエストし、ブロック内でイベント処理を実行する必要があります。

2)ここでイベントをコミットするか、「コミット」パラメーターをsave / remove呼び出しに渡す必要があります

他はすべて同じままです...

EventKitフレームワークを#import <EventKit/EventKit.h>コードに追加します。

私の例では、NSString * savedEventIdインスタンスプロパティがあります。

イベントを追加するには:

    EKEventStore *store = [EKEventStore new];
    [store requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) {
        if (!granted) { return; }
        EKEvent *event = [EKEvent eventWithEventStore:store];
        event.title = @"Event Title";
        event.startDate = [NSDate date]; //today
        event.endDate = [event.startDate dateByAddingTimeInterval:60*60];  //set 1 hour meeting
        event.calendar = [store defaultCalendarForNewEvents];
        NSError *err = nil;
        [store saveEvent:event span:EKSpanThisEvent commit:YES error:&err];
        self.savedEventId = event.eventIdentifier;  //save the event id if you want to access this later
    }];

イベントを削除します。

    EKEventStore* store = [EKEventStore new];
    [store requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) {
        if (!granted) { return; }
        EKEvent* eventToRemove = [store eventWithIdentifier:self.savedEventId];
        if (eventToRemove) {
            NSError* error = nil;
            [store removeEvent:eventToRemove span:EKSpanThisEvent commit:YES error:&error];
        }
    }];

これにより、デフォルトのカレンダーにイベントが追加されます。複数のカレンダーがある場合は、どのカレンダーかがわかります

Swiftバージョン

EventKitフレームワークをインポートする必要があります

import EventKit

イベントを追加

let store = EKEventStore()
store.requestAccessToEntityType(.Event) {(granted, error) in
    if !granted { return }
    var event = EKEvent(eventStore: store)
    event.title = "Event Title"
    event.startDate = NSDate() //today
    event.endDate = event.startDate.dateByAddingTimeInterval(60*60) //1 hour long meeting
    event.calendar = store.defaultCalendarForNewEvents
    do {
        try store.saveEvent(event, span: .ThisEvent, commit: true)
        self.savedEventId = event.eventIdentifier //save event id to access this particular event later
    } catch {
        // Display error to user
    }
}

イベントを削除

let store = EKEventStore()
store.requestAccessToEntityType(EKEntityTypeEvent) {(granted, error) in
    if !granted { return }
    let eventToRemove = store.eventWithIdentifier(self.savedEventId)
    if eventToRemove != nil {
        do {
            try store.removeEvent(eventToRemove, span: .ThisEvent, commit: true)
        } catch {
            // Display error to user
        }
    }
}

6
私にはうまくいきません、すべてはエラーなしで行きますが、カレンダーにはイベントがありません
ボリスガフロフ2013年

すべてがekeventオブジェクトに保存されていますが、カレンダーには保存されていませんhlp me

1
@William T:(URLスキームを使用して)カレンダーアプリの[イベントの追加]画面を表示し、イベントの情報を渡して、[イベントの追加]画面が表示されたときにデータが事前に入力されるようにできますか?ユーザーはイベント追加ボタンを押すだけです。あなたの例では、ユーザーへの通知なしに追加されたイベント。
Ans

1
すべてが機能しているように見えてもカレンダーが表示されない場合は、Cloud VSローカルカレンダーに問題があるかどうかを確認してください。クラウドカレンダーとローカルカレンダーが混在している場合、クラウドカレンダーはローカルカレンダーを非表示にすることができます。
zonabi 2014年

2
@ReddyBashaイベントを追加するときは、eventIdentifierを保存して、将来使用するために保存する必要があります。削除するときは、そのイベントIDを使用する必要があります。
ウィリアムT.

154

これは、OS 4.0のEvent Kitフレームワークを使用して行うことができます。

ウィンドウの左側にあるグループとファイルナビゲーターで、FrameWorksグループを右クリックします。「追加」、「既存のFrameWorks」、「EventKit.Framework」の順に選択します。

その後、次のようなコードでイベントを追加できるはずです。

#import "EventTestViewController.h"
#import <EventKit/EventKit.h>

@implementation EventTestViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    EKEventStore *eventStore = [[EKEventStore alloc] init];

    EKEvent *event  = [EKEvent eventWithEventStore:eventStore];
    event.title     = @"EVENT TITLE";

    event.startDate = [[NSDate alloc] init];
    event.endDate   = [[NSDate alloc] initWithTimeInterval:600 sinceDate:event.startDate];

    [event setCalendar:[eventStore defaultCalendarForNewEvents]];
    NSError *err;
    [eventStore saveEvent:event span:EKSpanThisEvent error:&err];       
}

@end

18
これを投稿してくれてありがとう。これを読んだすべての人へのリマインダーです:メモリリークに注意してください。このコードサンプルにはいくつかあります。また、ベストプラクティスでは、saveEvent:span:errorの後に「err」の値を確認し、それに応じて処理するように指示します。
David Carney

繰り返しイベントを追加する方法を知っていますか?毎週月曜日のイベントのように?
Jay Vachhani

5
プログラムで繰り返しイベントを追加ます。これを確認するにはdeveloper.apple.com/library/ios/#documentation/EventKit/…をご覧ください。別のオプションは、イベントの追加/編集にデフォルトのフレームワークが提供するビューコントローラーを使用することです(Calendar At-A-Glanceアプリのbit.ly/cJq4Bhなど)。このオプションについては、developer.apple.com
library / ios /#documentation / EventKitUI /…を

:XCodeの4のフレームワークを追加するには、このSOの質問を参照stackoverflow.com/questions/3352664/...
ネイト

1
4.0?6で飛ぶつもりはない上記の答えを参照してください
ボリスガフロフ

13

はい(2.1)のAPIはまだありません。しかし、WWDCでは、多くの人が既に機能(私を含む)に興味を持っていたようで、以下のサイトにアクセスして機能のリクエストを作成することをお勧めしました。十分な関心がある場合、ICal.frameworkをパブリックSDKに移動する可能性があります。

https://developer.apple.com/bugreporter/


5
回答は古くなっています。これを削除することを検討してください
Jasper

12

カレンダーアクセスがiPhone OS 4.0で追加されています

カレンダーアクセス
アプリは、イベントキットを使用して、カレンダーアプリで直接イベントを作成および編集できるようになりました。
定期的な予定を作成し、開始時間と終了時間を設定して、デバイス上の任意のカレンダーに割り当てます。


1
あなたのリンクは今壊れています。
Adil Soomro

5

概説したTristanのようなEvent APIを使用してイベントを追加でき、iOSカレンダーに表示されるGoogleカレンダーイベントを追加することもできます。

使用して、GoogleのAPIのObjective-Cクライアントを

  - (void)addAnEvent {
  // Make a new event, and show it to the user to edit
  GTLCalendarEvent *newEvent = [GTLCalendarEvent object];
  newEvent.summary = @"Sample Added Event";
  newEvent.descriptionProperty = @"Description of sample added event";

  // We'll set the start time to now, and the end time to an hour from now,
  // with a reminder 10 minutes before
  NSDate *anHourFromNow = [NSDate dateWithTimeIntervalSinceNow:60*60];
  GTLDateTime *startDateTime = [GTLDateTime dateTimeWithDate:[NSDate date]
                                                    timeZone:[NSTimeZone systemTimeZone]];
  GTLDateTime *endDateTime = [GTLDateTime dateTimeWithDate:anHourFromNow
                                                  timeZone:[NSTimeZone systemTimeZone]];

  newEvent.start = [GTLCalendarEventDateTime object];
  newEvent.start.dateTime = startDateTime;

  newEvent.end = [GTLCalendarEventDateTime object];
  newEvent.end.dateTime = endDateTime;

  GTLCalendarEventReminder *reminder = [GTLCalendarEventReminder object];
  reminder.minutes = [NSNumber numberWithInteger:10];
  reminder.method = @"email";

  newEvent.reminders = [GTLCalendarEventReminders object];
  newEvent.reminders.overrides = [NSArray arrayWithObject:reminder];
  newEvent.reminders.useDefault = [NSNumber numberWithBool:NO];

  // Display the event edit dialog
  EditEventWindowController *controller = [[[EditEventWindowController alloc] init] autorelease];
  [controller runModalForWindow:[self window]
                          event:newEvent
              completionHandler:^(NSInteger returnCode, GTLCalendarEvent *event) {
                // Callback
                if (returnCode == NSOKButton) {
                  [self addEvent:event];
                }
              }];
}

5

Swift 4.0の実装:

ページ上部のインポートを使用する import EventKit

その後

@IBAction func addtoCalendarClicked(sender: AnyObject) {

    let eventStore = EKEventStore()

    eventStore.requestAccess( to: EKEntityType.event, completion:{(granted, error) in

        if (granted) && (error == nil) {
            print("granted \(granted)")
            print("error \(error)")

            let event = EKEvent(eventStore: eventStore)

            event.title = "Event Title"
            event.startDate = Date()
            event.endDate = Date()
            event.notes = "Event Details Here"
            event.calendar = eventStore.defaultCalendarForNewEvents

            var event_id = ""
            do {
                try eventStore.save(event, span: .thisEvent)
                event_id = event.eventIdentifier
            }
            catch let error as NSError {
                print("json error: \(error.localizedDescription)")
            }

            if(event_id != ""){
                print("event added !")
            }
        }
    })
}

uが同じ答え@Dashrathに関するGoogleカレンダーで私を助けることができる
ディリップTiwariさん

4

Dashrath回答のSwift 4の更新

import UIKit
import EventKit

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        let eventStore = EKEventStore()

        eventStore.requestAccess( to: EKEntityType.event, completion:{(granted, error) in

            if (granted) && (error == nil) {


                let event = EKEvent(eventStore: eventStore)

                event.title = "My Event"
                event.startDate = Date(timeIntervalSinceNow: TimeInterval())
                event.endDate = Date(timeIntervalSinceNow: TimeInterval())
                event.notes = "Yeah!!!"
                event.calendar = eventStore.defaultCalendarForNewEvents

                var event_id = ""
                do{
                    try eventStore.save(event, span: .thisEvent)
                    event_id = event.eventIdentifier
                }
                catch let error as NSError {
                    print("json error: \(error.localizedDescription)")
                }

                if(event_id != ""){
                    print("event added !")
                }
            }
        })
    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }


}

また、カレンダーの使用許可を追加することを忘れないでください プライベート設定の画像


2

Swift-4.2の作業コード

import UIKit
import EventKit
import EventKitUI

class yourViewController: UIViewController{

    let eventStore = EKEventStore()

    func addEventToCalendar() {

    eventStore.requestAccess( to: EKEntityType.event, completion:{(granted, error) in
        DispatchQueue.main.async {
            if (granted) && (error == nil) {
                let event = EKEvent(eventStore: self.eventStore)
                event.title = self.headerDescription
                event.startDate = self.parse(self.requestDetails.value(forKey: "session_time") as? String ?? "")
                event.endDate = self.parse(self.requestDetails.value(forKey: "session_end_time") as? String ?? "")
                let eventController = EKEventEditViewController()
                eventController.event = event
                eventController.eventStore = self.eventStore
                eventController.editViewDelegate = self
                self.present(eventController, animated: true, completion: nil)

            }
        }


       })
    }

}

これでイベント画面が表示され、ここで設定を変更することもできます。

ここに画像の説明を入力してください

次に、キャンセルを処理するデリゲートメソッドを追加し、イベント画面のイベントボタンアクションを追加します。

    extension viewController: EKEventEditViewDelegate {

    func eventEditViewController(_ controller: EKEventEditViewController, didCompleteWith action: EKEventEditViewAction) {
        controller.dismiss(animated: true, completion: nil)

    }
}

注:NSCalendarsUsageDescriptionキーをinfo plist に追加することを忘れないでください。


1

作成したイベントにendDateを設定することを忘れないでください。これは必須です。

それ以外の場合は、次のエラーで失敗します(ほとんど黙って):

"Error Domain=EKErrorDomain Code=3 "No end date has been set." UserInfo={NSLocalizedDescription=No end date has been set.}"

私にとって完全な作業コードは次のとおりです。

EKEventStore *store = [EKEventStore new];
[store requestAccessToEntityType:EKEntityTypeEvent completion:^(BOOL granted, NSError *error) {
    if (!granted) { return; }
    EKEvent *calendarEvent = [EKEvent eventWithEventStore:store];
    calendarEvent.title = [NSString stringWithFormat:@"CEmprendedor: %@", _event.name];
    calendarEvent.startDate = _event.date;
    // 5 hours of duration, we must add the duration of the event to the API
    NSDate *endDate = [_event.date dateByAddingTimeInterval:60*60*5];
    calendarEvent.endDate = endDate;
    calendarEvent.calendar = [store defaultCalendarForNewEvents];
    NSError *err = nil;
    [store saveEvent:calendarEvent span:EKSpanThisEvent commit:YES error:&err];
    self.savedEventId = calendarEvent.eventIdentifier;  //saving the calendar event id to possibly deleted them
}];

1
また、終了日は開始日以上にする必要があることも覚えておいてください。そうしないと、別のエラーが発生します。
ムーディーズ'26年

0

グーグルのアイデアはいいものですが、問題があります。

Googleカレンダーのイベント画面を正常に開くことができますが、メインのデスクトップバージョンのみで、iPhone Safariでは正しく表示されません。Safariで正しく表示されるGoogleモバイルカレンダーは、APIと連携してイベントを追加するようには見えません。

現時点では、これを解決する良い方法はありません。


0

シンプル.... Tapkuライブラリを使用....その単語をグーグルして使用できます...オープンソース...楽しんでください.....これらのコードを盗聴する必要はありません...



Tapku Libraryカレンダーをカレンダーアプリのイベントと同期できます
coder1010

私が知っているのは、Tapkuライブラリがデータソースと呼ばれるオプションを持つカレンダーコンポーネントコントロールであることです。だから、そのソースをどこから取得するかを書くのはその最大のロジックです... Happy Coding :)
Rajesh_Bangalore
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.