Программно добавить пользовательское событие в календарь iPhone

Есть ли способ добавить событие iCal в календарь iPhone из пользовательского приложения?

Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
184
0
139 530
11
Перейти к ответу Данный вопрос помечен как решенный

Ответы 11

Да, для этого до сих пор нет API (2.1). Но казалось, что на WWDC многие люди уже интересовались функциональностью (включая меня), и порекомендовали перейти на сайт ниже и создать для этого запрос функции. Если будет достаточно интереса, они могут переместить ICal.framework в общедоступный SDK.

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

ответ устарел, рассмотрите возможность удаления этого

Jasper 22.04.2013 17:03

Идея Google хороша, но у нее есть проблемы.

Я могу успешно открыть экран событий календаря Google, но только в основной настольной версии, и он не отображается должным образом в iPhone Safari. Мобильный календарь Google, который правильно отображается в Safari, похоже, не работает с API для добавления событий.

На данный момент я не вижу хорошего выхода из этого.

Доступ к календарю добавлен в iPhone OS 4.0:

Calendar Access
Apps can now create and edit events directly in the Calendar app with Event Kit.
Create recurring events, set up start and end times and assign them to any calendar on the device.

Вы можете сделать это с помощью платформы Event Kit в OS 4.0.

Щелкните правой кнопкой мыши группу 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

Спасибо, что разместили это. Напоминаем всем, кто это читает: следите за утечками памяти. В этом примере кода есть пара. Кроме того, в соответствии с передовой практикой вы должны проверять значение 'err' после saveEvent: span: error и обрабатывать вещи соответствующим образом.

David Carney 07.07.2010 01:37

Вы знаете, как добавить событие повторения? как мероприятие на каждый понедельник?

Jay Vachhani 09.09.2010 11:45

Программно добавить событие повторения: проверьте это developer.apple.com/library/ios/#documentation/EventKit/…. Другой вариант - использовать стандартные контроллеры представлений, поставляемые фреймворком, для добавления / редактирования событий (например, приложение Calendar At-A-Glance bit.ly/cJq4Bh). Для этой опции см. developer.apple.com/library/ios/#documentation/EventKitUI/….

DenTheMan 06.12.2010 13:12

Чтобы добавить фреймворки в XCode 4, см. Этот вопрос SO: stackoverflow.com/questions/3352664/…

Nate 19.03.2011 04:45

4.0? не собираюсь летать через 6 см. ответ выше

Boris Gafurov 02.10.2013 19:32

Вы можете добавить событие, используя Event API, как обрисовал Тристан, а также можете добавить событие Календаря Google, которое отображается в календаре iOS.

используя Клиент 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];
                }
              }];
}

Просто .... используйте библиотеку tapku .... вы можете погуглить это слово и использовать его ... его открытый исходный код ... наслаждайтесь ..... не нужно искать ошибки с этими кодами ....

Может ли календарь библиотеки Tapku синхронизироваться с событиями приложения календаря

coder1010 30.01.2013 09:18

Все, что я знаю, это то, что библиотека Tapku - это элемент управления календаря, у которого есть опция под названием Источник данных. Таким образом, его логика заключается в том, чтобы написать, откуда этот источник вы получаете ... Удачного кодирования :)

Rajesh_Bangalore 05.02.2013 09:53
Ответ принят как подходящий

Основываясь на Документация Apple, это немного изменилось с iOS 6.0.

1) Вы должны запросить доступ к календарю пользователя через «requestAccessToEntityType: Завершение:» и выполнить обработку событий внутри блока.

2) Вам нужно зафиксировать свое событие сейчас или передать параметр "commit" в вызов сохранения / удаления.

Все остальное остается прежним ...

Добавьте в свой код фреймворк 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];
        }
    }];

Это добавляет события в ваш календарь по умолчанию, если у вас несколько календарей, вы узнаете, какой из них

Быстрая версия

Вам необходимо импортировать фреймворк 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
        }
    }
}

у меня не работает, все идет без ошибок, но в календаре нет события

Boris Gafurov 02.10.2013 19:30

Все хранится в объекте ekevent, но не в календаре hlp me

user2580666 28.01.2014 14:02

@William T: Могу ли я представить экран «Добавить событие» в приложении «Календарь» (используя схему URL) и передать информацию о событии, чтобы при появлении экрана «Добавить событие» в нем были предварительно заполнены данные. Пользователю просто нужно нажать кнопку добавления события. В вашем примере событие добавлено без указания пользователю.

Ans 17.05.2014 14:01

Если кажется, что все работает, но календарь не отображается, проверьте, не является ли проблема с локальными календарями Cloud VS. Если у вас есть сочетание облачных и локальных календарей, облачные календари могут принудительно скрывать локальные календари.

zonabi 09.06.2014 21:19

@ Уильям Это работает для меня. Здесь я сталкиваюсь с одной проблемой, если я добавляю более одного события в календарь и пытаюсь удалить событие из календаря. Это удаляет только последнее событие из календаря. Как получить идентификатор события при удалении из календаря.

Logger 29.09.2014 12:31

@ReddyBasha, когда вы добавляете событие, вам нужно сохранить eventIdentifier и сохранить его для будущего использования. Вы должны использовать этот идентификатор события, когда собираетесь его удалить.

William T. 03.11.2014 03:10

Реализация 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 !")
            }
        }
    })
}

не могли бы вы помочь мне с календарем Google относительно того же ответа @Dashrath

Dilip Tiwari 15.12.2017 16:02

Не забудьте установить 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
}];

Также помните, что дата окончания должна быть больше или равна дате начала. В противном случае вы получите еще одну ошибку.

moody 26.10.2017 15:49

Обновление для Swift 4 для ответа Dashrath

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.
    }


}

также не забудьте добавить разрешение на использование календаря image for privary setting

Рабочий код в 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)

            }
        }


       })
    }

}

Теперь мы получим экран события, и здесь вы также можете изменить свои настройки:

Теперь добавьте метод делегата для обработки Cancel и добавьте действие кнопки события экрана события:

    extension viewController: EKEventEditViewDelegate {

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

    }
}

Примечание: Не забудьте добавить ключ NSCalendarsUsageDescription в информационный лист.

Другие вопросы по теме