この記事はSwift その2 Advent Calendar 2017 18日目のコンテンツです。
App Extensionとは
iOS8からある機能
四角から上に矢印伸びたボタンを出てくるアレ
App Extensionの基本的な使い方
if let extensionContext = self.extensionContext,
let item = extensionContext.inputItems.first as? NSExtensionItem,
let attachments = item.attachments as? [NSItemProvider],
let attachment = attachments.first {
let contentType = kUTTypeImage as String
attachment.loadFileRepresentation(forTypeIdentifier: contentType) { (url, error) in
// Do Something with url
// url -> Image, url -> Data
})
}
loadFileRepresentation()というメソッドを使って画像URLを取得 していました。URLあれば、なんでもできそうだったからです。URLからUIImageに変換したり、URLからDataに変換したり。
iOS10以前と11でのURLの違い。
if let extensionContext = self.extensionContext,
let item = extensionContext.inputItems.first as? NSExtensionItem,
let attachments = item.attachments as? [NSItemProvider],
let attachment = attachments.first {
let contentType = kUTTypeImage as String
attachment.loadFileRepresentation(forTypeIdentifier: contentType) { (url, error) in
// Do Something with url
// iOS10
// “file:///private/var/mobile/Containers/**/P105.PNG”
//
// iOS11
// “file:///private/var/mobile/Containers/**/image”
})
}
しかし、Screenshotを取った時にApp Extensionで取得できるURLが上記のように末尾が /image
なってしまいました。このURLをもとにUIImageやDataに変換しようとしてもエラーが出てしまいます。
そこで以下のように対処しました。
if let extensionContext = self.extensionContext,
let item = extensionContext.inputItems.first as? NSExtensionItem,
let attachments = item.attachments as? [NSItemProvider],
let attachment = attachments.first {
let contentType = kUTTypeImage as String
attachment.loadItem(forTypeIdentifier: contentType, options: nil) { (data, error) in
if type(of: data!) == UIImage.self {
// iOS 11 screenshot
} else if type(of: data!) == NSURL.self {
}
}
}
この方法にはいくつか欠点があります。
- 想定していないタイプが来たらどうする?
- ドキュメントは? -> 観測範囲ではない
最後に紹介した方法で動くは動くのですが、他になにかいい方法あったら教えてください。