有不止一种方法可以做到这一点。
没有内容扩展
第一个甚至不需要通知内容扩展! UNTextInputNotificationAction 为您完成所有工作。初始化动作时,您为触发动作时将显示的文本字段指定参数。该操作在注册期间附加到您的通知类别(即在willFinishLaunchingWithOptions 内):
userNotificationCenter.getNotificationCategories { (categories) in
var categories: Set<UNNotificationCategory> = categories
let inputAction: UNTextInputNotificationAction = UNTextInputNotificationAction(identifier: "org.quellish.textInput", title: "Comment", options: [], textInputButtonTitle: "Done", textInputPlaceholder: "This is awesome!")
let category: UNNotificationCategory = UNNotificationCategory(identifier: notificationCategory, actions: [inputAction], intentIdentifiers: [], hiddenPreviewsBodyPlaceholder: "Placeholder", options: [])
categories.insert(category)
userNotificationCenter.setNotificationCategories(categories)
}
这将产生这样的体验:
请注意,默认情况下,“完成”按钮会关闭键盘和通知。
通过不止一个动作,你会得到:
无法返回与通知一起显示的操作按钮 - 通知无法做到这一点。要再次查看这些操作选择需要显示另一个通知。
带有内容扩展
首先,上述部分也适用于内容扩展。当用户完成输入文本并点击“textInputButton”时,会调用内容扩展的didReceive(_:completionHandler:) 方法。这是使用输入或关闭扩展的机会。 WWDC 2016 会议Advanced Notifications 描述了相同的用例并详细说明了可以进一步定制的方法。
这可能无法满足您的需求。您可能希望有一个自定义的文本输入用户界面等。在这种情况下,由您的扩展来处理显示和隐藏键盘。处理文本输入的响应者(例如 UITextField)应该在收到通知时成为第一响应者。这样做将显示键盘。辞职的第一响应者将隐藏它。这可以在 UITextField 委托方法中完成。
例如,这个:
override var canBecomeFirstResponder: Bool {
get {
return true
}
}
func didReceive(_ notification: UNNotification) {
self.label?.text = notification.request.content.body
self.textField?.delegate = self
self.becomeFirstResponder()
self.textField?.becomeFirstResponder()
return
}
// UITextFieldDelegate
func textFieldShouldReturn(_ textField: UITextField) -> Bool {
self.textField?.resignFirstResponder()
self.resignFirstResponder()
return true
}
产生这样的结果:
请记住,在 iOS 10 和 11 上,对通知本身的任何点击(例如在您的文本字段上)都可能导致通知被忽略!由于这个和许多其他原因,走这条路可能是不可取的。