在 tvOS 10 GM 上打开 UIAlertController 时焦点消失
Focus disappearing when opening a UIAlertController on tvOS 10 GM
我想在 UIViewController
的顶部显示一个 UIAlertController
,里面有一个 UICollectionView
。集合视图需要关注启动,所以我覆盖了preferredFocusableView
变量如下:
override var preferredFocusedView: UIView? {
return self.collectionView
}
使用 tvOS 9 一切正常:警报控制器正确打开,我可以选择显示的 UIAlertAction
之一。
在 tvOS 10 Golden Master 上,打开警报控制器并滚动到另一个操作后,焦点从屏幕上消失,我无法滚动到其他操作或点击 Siri Remote 的菜单按钮。该应用程序仍然停留在警报控制器中,当我尝试滚动到其他操作但屏幕上没有任何反应时,我可以听到滚动的声音。我必须强制退出应用程序并重新打开它。
这是应用程序的代码。我尝试将 preferredFocusableView
设置为 alertController.preferredFocusedView
或通过删除集合视图的焦点方法但没有结果。
var alertController : UIAlertController?
func showAlert() {
alertController = UIAlertController(title:"Example title", message: "Example description", preferredStyle: .Alert)
let action1 = UIAlertAction(title: "Option 1", style: .Default) { (action : UIAlertAction) -> Void in
//call to another method
}
// action2, action3, action4...
let action5 = UIAlertAction(title: "Option 5", style: .Default) { (action : UIAlertAction) -> Void in
//call to another method
}
let actionDismiss = UIAlertAction(title: "Dismiss", style: .Destructive) { (action : UIAlertAction) -> Void in
self.alertController!.dismissViewControllerAnimated(true, completion: nil)
}
alertController!.addAction(action1)
alertController!.addAction(action2)
alertController!.addAction(action3)
alertController!.addAction(action4)
alertController!.addAction(action5)
alertController!.addAction(actionDismiss)
alertController!.preferredAction = action1
self.presentViewController(alertController!, animated: true, completion: nil)
}
override var preferredFocusedView: UIView? {
if self.alertController != nil {
return self.alertController!.preferredFocusedView
} else {
return self.collectionView
}
}
您正在覆盖整个系统焦点引擎。试试这个:
// MARK: - Update Focus Helper
var viewToFocus: UIView? = nil {
didSet {
if viewToFocus != nil {
self.setNeedsFocusUpdate()
self.updateFocusIfNeeded()
}
}
}
override weak var preferredFocusedView: UIView? {
if viewToFocus != nil {
return viewToFocus
} else {
return super.preferredFocusedView
}
}
然后将您的警报设置为您希望焦点更改到它时的视图:
viewToFocus = someView
Apple 刚刚回复了我的雷达:
Inside the attached application, you’re overwriting the functionality
of UIScrollView
in an extension to return true
for
canBecomeFocused()
, which is the cause of these unexpected side
effects. The focus seems to be disappearing when moving to a second
UIAlertController
option; however, it is actually transferring focus
to the scroll view wrapped around the various components of the
UIAlertController
, since this is now allowed due to the extension
mentioned above.
To solve this, create a custom subclass of UIScrollView
to be used
only in the instances where canBecomeFocused()
must return true
.
我想在 UIViewController
的顶部显示一个 UIAlertController
,里面有一个 UICollectionView
。集合视图需要关注启动,所以我覆盖了preferredFocusableView
变量如下:
override var preferredFocusedView: UIView? {
return self.collectionView
}
使用 tvOS 9 一切正常:警报控制器正确打开,我可以选择显示的 UIAlertAction
之一。
在 tvOS 10 Golden Master 上,打开警报控制器并滚动到另一个操作后,焦点从屏幕上消失,我无法滚动到其他操作或点击 Siri Remote 的菜单按钮。该应用程序仍然停留在警报控制器中,当我尝试滚动到其他操作但屏幕上没有任何反应时,我可以听到滚动的声音。我必须强制退出应用程序并重新打开它。
这是应用程序的代码。我尝试将 preferredFocusableView
设置为 alertController.preferredFocusedView
或通过删除集合视图的焦点方法但没有结果。
var alertController : UIAlertController?
func showAlert() {
alertController = UIAlertController(title:"Example title", message: "Example description", preferredStyle: .Alert)
let action1 = UIAlertAction(title: "Option 1", style: .Default) { (action : UIAlertAction) -> Void in
//call to another method
}
// action2, action3, action4...
let action5 = UIAlertAction(title: "Option 5", style: .Default) { (action : UIAlertAction) -> Void in
//call to another method
}
let actionDismiss = UIAlertAction(title: "Dismiss", style: .Destructive) { (action : UIAlertAction) -> Void in
self.alertController!.dismissViewControllerAnimated(true, completion: nil)
}
alertController!.addAction(action1)
alertController!.addAction(action2)
alertController!.addAction(action3)
alertController!.addAction(action4)
alertController!.addAction(action5)
alertController!.addAction(actionDismiss)
alertController!.preferredAction = action1
self.presentViewController(alertController!, animated: true, completion: nil)
}
override var preferredFocusedView: UIView? {
if self.alertController != nil {
return self.alertController!.preferredFocusedView
} else {
return self.collectionView
}
}
您正在覆盖整个系统焦点引擎。试试这个:
// MARK: - Update Focus Helper
var viewToFocus: UIView? = nil {
didSet {
if viewToFocus != nil {
self.setNeedsFocusUpdate()
self.updateFocusIfNeeded()
}
}
}
override weak var preferredFocusedView: UIView? {
if viewToFocus != nil {
return viewToFocus
} else {
return super.preferredFocusedView
}
}
然后将您的警报设置为您希望焦点更改到它时的视图:
viewToFocus = someView
Apple 刚刚回复了我的雷达:
Inside the attached application, you’re overwriting the functionality of
UIScrollView
in an extension to returntrue
forcanBecomeFocused()
, which is the cause of these unexpected side effects. The focus seems to be disappearing when moving to a secondUIAlertController
option; however, it is actually transferring focus to the scroll view wrapped around the various components of theUIAlertController
, since this is now allowed due to the extension mentioned above.To solve this, create a custom subclass of
UIScrollView
to be used only in the instances wherecanBecomeFocused()
must returntrue
.