Top Banner
Copyright © Up-frontier, Inc. All rights reserved. New Notification API in iOS 10 1
50

New Notification API in iOS 10

Jan 08, 2017

Download

Mobile

Gaprot
Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.
Transcript
Page 1: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

New Notification API in iOS 10

1

Page 2: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

アジェンダ• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

2

Page 3: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

アジェンダ• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

3

Page 4: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ローカル通知⽅法1. コンテンツを作って

2. トリガーを設定して

3. センターにリクエスト

4

Page 5: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ローカル通知⽅法1. コンテンツを作って

2. トリガーを設定して

3. センターにリクエスト

5

Page 6: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

コンテンツlet content = UNMutableNotificationContent() content.title = "Title" content.subtitle = "Subtitle" content.body = "Body" content.categoryIdentifier = "sample-category"

6

Page 7: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

コンテンツlet content = UNMutableNotificationContent() content.title = "Title" content.subtitle = "Subtitle" content.body = "Body" content.categoryIdentifier = "sample-category"

7

Page 8: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

コンテンツlet content = UNMutableNotificationContent() content.title = "Title" content.subtitle = "Subtitle" content.body = "Body" content.categoryIdentifier = "sample-category"

8

Action や、カスタム UI など 識別に使⽤

Page 9: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ローカル通知⽅法1. コンテンツを作って

2. トリガーを設定して

3. センターにリクエスト

9

Page 10: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

トリガーUNNotificationTrigger

10

Page 11: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

トリガーUNNotificationTrigger

11

let intervalTrigger = UNTimeIntervalNotificationTrigger( timeInterval: 5, repeats: false)

Page 12: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リクエストlet id = "sample-\(Date().timeIntervalSince1970)"

let request = UNNotificationRequest( identifier: id, content: content, trigger: intervalTrigger

) center.add(request) { error in

if let error = error { print("Error on requesting notification: \(error)")

} print("Finish requesting notification: \(id)")

}

12

Page 13: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リクエストlet id = "sample-\(Date().timeIntervalSince1970)"

let request = UNNotificationRequest( identifier: id, content: content, trigger: intervalTrigger

) center.add(request) { error in

if let error = error { print("Error on requesting notification: \(error)")

} print("Finish requesting notification: \(id)")

}

13

トリガのセット

Page 14: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リクエストlet id = "sample-\(Date().timeIntervalSince1970)"

let request = UNNotificationRequest( identifier: id, content: content, trigger: intervalTrigger

) center.add(request) { error in

if let error = error { print("Error on requesting notification: \(error)")

} print("Finish requesting notification: \(id)")

}

14

identifier: 識別⼦、更新・削除に利⽤ contents: 通知本体

trigger: 発⽕タイミング

Page 15: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リクエストlet id = "sample-\(Date().timeIntervalSince1970)"

let request = UNNotificationRequest( identifier: id, content: content, trigger: intervalTrigger

) center.add(request) { error in

if let error = error { print("Error on requesting notification: \(error)")

} print("Finish requesting notification: \(id)")

}

15

Notification Centerに追加で完了

Page 16: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

アジェンダ• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

16

Page 17: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Media Attachment

• 通知領域で様々なメディアファイルを表⽰する

17

Page 18: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

メディア

18

画像jpg, png, gif

⾳声mp3, mp4

動画mp4, avi

Page 19: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

メディア1. 通知内容を作って

2. トリガーを設定して

3. センターにリクエスト

19

Page 20: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

メディア1. 通知内容を作って

2. トリガーを設定して

3. センターにリクエスト

20

Page 21: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

メディア1. 通知内容を作って

2. トリガーを設定して

3. センターにリクエスト

21

ここで設定する

Page 22: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

UNNotificationAttachment guard let imageURL = R.file.sampleJpg() else {

print("Could not instantiate file URL!”) return

} let content = defaultContent do {

let attachment = try UNNotificationAttachment( identifier: "sample-cat", url: imageURL, options: nil

) content.attachments = [attachment]

} catch(let error) { print("Could not instantiate attachment: \(error)")

}

22

Page 23: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

UNNotificationAttachment guard let imageURL = R.file.sampleJpg() else {

print("Could not instantiate file URL!”) return

} let content = defaultContent do {

let attachment = try UNNotificationAttachment( identifier: "sample-cat", url: imageURL, options: nil

) content.attachments = [attachment]

} catch(let error) { print("Could not instantiate attachment: \(error)")

}

23

画像の設定 UNNotificationAttachmentを使う

Page 24: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

UNNotificationAttachment guard let imageURL = R.file.sampleJpg() else {

print("Could not instantiate file URL!”) return

} let content = defaultContent do {

let attachment = try UNNotificationAttachment( identifier: "sample-cat", url: imageURL, options: nil

) content.attachments = [attachment]

} catch(let error) { print("Could not instantiate attachment: \(error)")

}

24

コンテンツに指定

Page 25: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

アジェンダ• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

25

Page 26: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Notification Content Extension

• オリジナルUIの通知を作成する

26

Page 27: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ターゲット• Notification Content Extension

27

Page 28: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

カスタム UI• Storyboard を使って UI を構築

28

Page 29: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationViewControllerclass NotificationViewController : UIViewController , UNNotificationContentExtension { @IBOutlet weak var mapView: MKMapView! override func viewDidLoad() { super.viewDidLoad() } func didReceive(_ notification: UNNotification) { let content = notification.request.content if let lat = content.userInfo["latitude"] as? Double, let lon = content.userInfo["longitude"] as? Double { putPin(into: CLLocationCoordinate2D(latitude: lat, longitude: lon)) } } }

29

Page 30: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationViewControllerclass NotificationViewController : UIViewController , UNNotificationContentExtension { @IBOutlet weak var mapView: MKMapView! override func viewDidLoad() { super.viewDidLoad() } func didReceive(_ notification: UNNotification) { let content = notification.request.content if let lat = content.userInfo["latitude"] as? Double, let lon = content.userInfo["longitude"] as? Double { putPin(into: CLLocationCoordinate2D(latitude: lat, longitude: lon)) } } }

30

MapViewを持った通知

Page 31: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationViewControllerclass NotificationViewController : UIViewController , UNNotificationContentExtension { @IBOutlet weak var mapView: MKMapView! override func viewDidLoad() { super.viewDidLoad() } func didReceive(_ notification: UNNotification) { let content = notification.request.content if let lat = content.userInfo["latitude"] as? Double, let lon = content.userInfo["longitude"] as? Double { putPin(into: CLLocationCoordinate2D(latitude: lat, longitude: lon)) } } }

31

通知が発⽕した時の処理

Page 32: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationViewControllerclass NotificationViewController : UIViewController , UNNotificationContentExtension { @IBOutlet weak var mapView: MKMapView! override func viewDidLoad() { super.viewDidLoad() } func didReceive(_ notification: UNNotification) { let content = notification.request.content if let lat = content.userInfo["latitude"] as? Double, let lon = content.userInfo["longitude"] as? Double { putPin(into: CLLocationCoordinate2D(latitude: lat, longitude: lon)) } } }

32

通知が発⽕した時の処理

通知内容を反映

Page 33: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Info.plist

<dict> <key>NSExtensionAttributes</key> <dict> <key>UNNotificationExtensionCategory</key> <array> <string>customUI</string>

</array> <key>UNNotificationExtensionInitialContentSizeRatio</key> <real>1</real> <key>UNNotificationExtensionDefaultContentHidden</key> <true/>

</dict> <key>NSExtensionMainStoryboard</key> <string>MainInterface</string> <key>NSExtensionPointIdentifier</key> <string>com.apple.usernotifications.content-extension</string>

</dict> 33

Page 34: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Info.plist

<dict> <key>NSExtensionAttributes</key> <dict> <key>UNNotificationExtensionCategory</key> <array> <string>customUI</string>

</array> <key>UNNotificationExtensionInitialContentSizeRatio</key> <real>1</real> <key>UNNotificationExtensionDefaultContentHidden</key> <true/>

</dict> <key>NSExtensionMainStoryboard</key> <string>MainInterface</string> <key>NSExtensionPointIdentifier</key> <string>com.apple.usernotifications.content-extension</string>

</dict> 34

categoryIdentifierと ⼀致している必要あり

Page 35: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Info.plist

<dict> <key>NSExtensionAttributes</key> <dict> <key>UNNotificationExtensionCategory</key> <array> <string>customUI</string>

</array> <key>UNNotificationExtensionInitialContentSizeRatio</key> <real>1</real> <key>UNNotificationExtensionDefaultContentHidden</key> <true/>

</dict> <key>NSExtensionMainStoryboard</key> <string>MainInterface</string> <key>NSExtensionPointIdentifier</key> <string>com.apple.usernotifications.content-extension</string>

</dict> 35

UIの縦横⽐

Page 36: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Info.plist

<dict> <key>NSExtensionAttributes</key> <dict> <key>UNNotificationExtensionCategory</key> <array> <string>customUI</string>

</array> <key>UNNotificationExtensionInitialContentSizeRatio</key> <real>1</real> <key>UNNotificationExtensionDefaultContentHidden</key> <true/>

</dict> <key>NSExtensionMainStoryboard</key> <string>MainInterface</string> <key>NSExtensionPointIdentifier</key> <string>com.apple.usernotifications.content-extension</string>

</dict> 36

デフォルトのタイトル、サブタイトル、コンテンツ

Page 37: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

アジェンダ• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

37

Page 38: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

Notification Service Extension

• オリジナルUIの通知を作成する

38

Page 39: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ターゲット• Notification Service Extension

39

Page 40: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationServiceclass NotificationService: UNNotificationServiceExtension { var contentHandler: ((UNNotificationContent) -> Void)? var bestAttemptContent: UNMutableNotificationContent? override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { self.contentHandler = contentHandler bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) if let bestAttemptContent = bestAttemptContent {

// Modify the notification content here... bestAttemptContent.title = "\(bestAttemptContent.title) [modified]" contentHandler(bestAttemptContent) } } override func serviceExtensionTimeWillExpire() {

// Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, // otherwise the original push payload will be used.

if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent {

bestAttemptContent.title = "\(bestAttemptContent.title) [Time Expired]" contentHandler(bestAttemptContent) } } }

40

Page 41: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationServiceclass NotificationService: UNNotificationServiceExtension { var contentHandler: ((UNNotificationContent) -> Void)? var bestAttemptContent: UNMutableNotificationContent? override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { self.contentHandler = contentHandler bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) if let bestAttemptContent = bestAttemptContent {

// Modify the notification content here... bestAttemptContent.title = "\(bestAttemptContent.title) [modified]" contentHandler(bestAttemptContent) } } override func serviceExtensionTimeWillExpire() {

// Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, // otherwise the original push payload will be used.

if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent {

bestAttemptContent.title = "\(bestAttemptContent.title) [Time Expired]" contentHandler(bestAttemptContent) } } }

41

通知内容を編集

Page 42: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationServiceclass NotificationService: UNNotificationServiceExtension { var contentHandler: ((UNNotificationContent) -> Void)? var bestAttemptContent: UNMutableNotificationContent? override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { self.contentHandler = contentHandler bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) if let bestAttemptContent = bestAttemptContent {

// Modify the notification content here... bestAttemptContent.title = "\(bestAttemptContent.title) [modified]" contentHandler(bestAttemptContent) } } override func serviceExtensionTimeWillExpire() {

// Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, // otherwise the original push payload will be used.

if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent {

bestAttemptContent.title = "\(bestAttemptContent.title) [Time Expired]" contentHandler(bestAttemptContent) } } }

42

処理が既定秒数(MAX30秒)を超えると呼ばれる

Page 43: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationServiceclass NotificationService: UNNotificationServiceExtension { var contentHandler: ((UNNotificationContent) -> Void)? var bestAttemptContent: UNMutableNotificationContent? override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { self.contentHandler = contentHandler bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) if let bestAttemptContent = bestAttemptContent {

// Modify the notification content here... bestAttemptContent.title = "\(bestAttemptContent.title) [modified]" contentHandler(bestAttemptContent) } } override func serviceExtensionTimeWillExpire() {

// Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, // otherwise the original push payload will be used.

if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent {

bestAttemptContent.title = "\(bestAttemptContent.title) [Time Expired]" contentHandler(bestAttemptContent) } } }

43

サーバからのリモートプッシュを変更する場合 mutable-contetの設定忘れないように

Page 44: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

NotificationServiceclass NotificationService: UNNotificationServiceExtension { var contentHandler: ((UNNotificationContent) -> Void)? var bestAttemptContent: UNMutableNotificationContent? override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) { self.contentHandler = contentHandler bestAttemptContent = (request.content.mutableCopy() as? UNMutableNotificationContent) if let bestAttemptContent = bestAttemptContent {

// Modify the notification content here... bestAttemptContent.title = "\(bestAttemptContent.title) [modified]" contentHandler(bestAttemptContent) } } override func serviceExtensionTimeWillExpire() {

// Called just before the extension will be terminated by the system. // Use this as an opportunity to deliver your "best attempt" at modified content, // otherwise the original push payload will be used.

if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent {

bestAttemptContent.title = "\(bestAttemptContent.title) [Time Expired]" contentHandler(bestAttemptContent) } } }

44

処理が終わったら速やかに呼ぶ

Page 45: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

ありそうな使い⽅• ペイロードにサーバにあるメディアの URL

• ダウンロードして

• Media Attachment

45

Page 46: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リモートコンテンツ 貼り付け

if let bestAttemptContent = bestAttemptContent { guard let urlString = bestAttemptContent.userInfo["remote-url"] as? String, let remoteURL = URL(string: urlString) else { contentHandler(bestAttemptContent) return } download(remoteURL) { url, error in guard let fileURL = url else { print(error) contentHandler(bestAttemptContent) return } do { let attachment = try UNNotificationAttachment( identifier: "remote", url: fileURL ) bestAttemptContent.attachments = [attachment] contentHandler(bestAttemptContent) } catch(let e) { print(e) contentHandler(bestAttemptContent) } } }

46

Page 47: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

リモートコンテンツ 貼り付け

if let bestAttemptContent = bestAttemptContent { guard let urlString = bestAttemptContent.userInfo["remote-url"] as? String, let remoteURL = URL(string: urlString) else { contentHandler(bestAttemptContent) return } download(remoteURL) { url, error in guard let fileURL = url else { print(error) contentHandler(bestAttemptContent) return } do { let attachment = try UNNotificationAttachment( identifier: "remote", url: fileURL ) bestAttemptContent.attachments = [attachment] contentHandler(bestAttemptContent) } catch(let e) { print(e) contentHandler(bestAttemptContent) } } }

47

画像のダウンロード 30秒超えるかも

Page 48: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

serviceExtensionTimeWillExpireoverride func serviceExtensionTimeWillExpire() { if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent { bestAttemptContent.title += " [頑張ったけれどダメだったよ]" contentHandler(bestAttemptContent) } }

48

Page 49: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

serviceExtensionTimeWillExpireoverride func serviceExtensionTimeWillExpire() { if let contentHandler = contentHandler, let bestAttemptContent = bestAttemptContent { bestAttemptContent.title += " [頑張ったけれどダメだったよ]" contentHandler(bestAttemptContent) } }

49

サーバからのリモートプッシュの内容を 変更しない場合

もとのペイロードのまま表⽰されてしまうので注意

Page 50: New Notification API in iOS 10

Copyright © Up-frontier, Inc. All rights reserved.

まとめ

• 新 API でローカル通知

• Media Attachment

• Notification Content Extension

• Notification Service Extension

50