我正在使用 SiriKit 开发一个简单的照片搜索。我能够在主视图控制器上搜索和显示图像,但我无法使用 IntentsUI 框架在 Intents UI 上显示图像。我按照本教程进行操作,但它缺少 Intents UI 实现。这是我到目前为止所做的。
IntentHandler.swift
class IntentHandler: INExtension, INSearchForPhotosIntentHandling {
override func handler(for intent: INIntent) -> Any {
return self
}
// MARK: - INSearchForPhotosIntentHandling
func resolveDateCreated(forSearchForPhotos intent: INSearchForPhotosIntent, with completion: @escaping (INDateComponentsRangeResolutionResult) -> Void) {
if intent.dateCreated != nil {
completion(INDateComponentsRangeResolutionResult.success(with: intent.dateCreated!))
}
else{
completion(INDateComponentsRangeResolutionResult.needsValue())
}
}
func confirm(searchForPhotos intent: INSearchForPhotosIntent, completion: @escaping (INSearchForPhotosIntentResponse) -> Void) {
let response = INSearchForPhotosIntentResponse(code: .ready, userActivity: nil)
completion(response)
}
func handle(searchForPhotos intent: INSearchForPhotosIntent, completion: @escaping (INSearchForPhotosIntentResponse) -> Void) {
let response = INSearchForPhotosIntentResponse(code:.continueInApp,userActivity: nil)
if intent.dateCreated != nil {
let calendar = Calendar(identifier: .gregorian)
let startDate = calendar.date(from:(intent.dateCreated?.startDateComponents)!)
response.searchResultsCount = photoSearchFrom(startDate!)
}
completion(response)
}
// MARK: - Search Photos
func photoSearchFrom(_ startDate: Date) -> Int {
let fetchOptions = PHFetchOptions()
fetchOptions.predicate = NSPredicate(format: "creationDate >= %@", startDate as CVarArg)
let fetchResult = PHAsset.fetchAssets(with: PHAssetMediaType.image,
options: fetchOptions)
return fetchResult.count
}
}
AppDelegate.Swift
class AppDelegate: UIResponder, UIApplicationDelegate {
func application(_ application: UIApplication, continue userActivity: NSUserActivity, restorationHandler: @escaping ([Any]?) -> Void) -> Bool {
// implement to handle user activity created by Siri or by our SiriExtension
let viewController = self.window?.rootViewController as! PhotoViewController
viewController.handleActivity(userActivity)
return true
}
}
PhotoViewController.swift
class ViewController: UIViewController {
@IBOutlet weak var imageView: UIImageView!
override func viewDidLoad() {
super.viewDidLoad()
INPreferences.requestSiriAuthorization { (status) in
print(status)
}
}
func handleActivity(_ userActivity: NSUserActivity) {
let intent = userActivity.interaction?.intent as! INSearchForPhotosIntent
if (intent.dateCreated?.startDateComponents) != nil {
let calendar = Calendar(identifier: .gregorian)
let startDate = calendar.date(from:(intent.dateCreated?.startDateComponents)!)
self.displayPhoto(startDate!)
}
}
func displayPhoto(_ startDate: Date) {
let fetchOptions = PHFetchOptions()
fetchOptions.predicate = NSPredicate(format: "creationDate >= %@", startDate as CVarArg)
let fetchResult = PHAsset.fetchAssets(with:
PHAssetMediaType.image, options: fetchOptions)
let imgManager = PHImageManager.default()
imgManager.requestImage(for: fetchResult.firstObject! as PHAsset,
targetSize: view.frame.size,
contentMode: PHImageContentMode.aspectFill,
options: nil,
resultHandler: { (image, _) in
self.imageView.image = image
})
}
}
现在来了IntentViewController.swift
class IntentViewController: UIViewController, INUIHostedViewControlling {
@IBOutlet weak var imageView:UIImageView!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
INPreferences.requestSiriAuthorization { (status) in
print("From IntentViewController: \(status)")
}
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(true)
print("IntentViewController-> viewDidLoad")
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
// MARK: - INUIHostedViewControlling
// Prepare your view controller for the interaction to handle.
func configure(with interaction: INInteraction!, context: INUIHostedViewContext, completion: ((CGSize) -> Void)!) {
print("From configure")
let intent = interaction?.intent as! INSearchForPhotosIntent
if (intent.dateCreated?.startDateComponents) != nil {
let calendar = Calendar(identifier: .gregorian)
let startDate = calendar.date(from:(intent.dateCreated?.startDateComponents)!)
self.displayPhoto(startDate!)
}
if let completion = completion {
completion(self.desiredSize)
}
}
var desiredSize: CGSize {
return self.extensionContext!.hostedViewMaximumAllowedSize
}
func displayPhoto(_ startDate: Date) {
let fetchOptions = PHFetchOptions()
fetchOptions.predicate = NSPredicate(format: "creationDate >= %@", startDate as CVarArg)
let fetchResult = PHAsset.fetchAssets(with:
PHAssetMediaType.image, options: fetchOptions)
let imgManager = PHImageManager.default()
imgManager.requestImage(for: fetchResult.firstObject! as PHAsset,
targetSize: view.frame.size,
contentMode: PHImageContentMode.aspectFill,
options: nil,
resultHandler: { (image, _) in
self.imageView.image = image
})
}
}
我是否必须在IntentHandler.swift文件的句柄方法中编写任何额外的代码才能使用 Intents UI 显示图像?我不想在应用程序中继续,实际上我希望在 Intents UI 中得到结果。提前致谢。