【问题标题】:How can I force focus to change to a specific view in tvOS?如何强制焦点更改到 tvOS 中的特定视图?
【发布时间】:2015-09-24 13:36:27
【问题描述】:

我正在实现自定义代码来处理点击 Siri Remote 上的“菜单”按钮。 按下菜单按钮时如何强制焦点切换到我的自定义菜单?

【问题讨论】:

标签: objective-c tvos


【解决方案1】:

对于 ios 10,您应该使用 preferredFocusEnvironments 而不是 preferredFocusedView 。

在下面的示例中,如果您想关注button,请参见下面的代码。

@IBOutlet weak var button: UIButton!

override var preferredFocusEnvironments: [UIFocusEnvironment] {
    return [button]
}

override func viewDidLoad() {
    super.viewDidLoad()

    setNeedsFocusUpdate()
    updateFocusIfNeeded()
}

【讨论】:

  • 这应该是现在公认的答案,因为preferredFocusedView 正在被贬值。
【解决方案2】:

终于自己搞定了。您必须覆盖 UIViewUIViewControllerpreferredFocusedView 属性。

在 Swift 中它是这样工作的:

func myClickHandler() {
    someCondition = true
    self.setNeedsFocusUpdate()
    self.updateFocusIfNeeded()
    someCondition = false
}

override weak var preferredFocusedView: UIView? {
    if someCondition {
        return theViewYouWant
    } else {
        return defaultView
    }
}

我不太记得如何在 Objective-C 中覆盖 getter,所以如果有人想发布,我会编辑答案。

【讨论】:

  • 谢谢。我正在考虑这样做,但是将所有这些“someConditions”放在所有地方似乎太乱了。如果您可以设置PreferredFocusedView 会容易得多...
  • 但是,等等。当我想将焦点更改到另一个视图控制器时,这是如何工作的?
  • 我同意。希望他们会添加它。另外为了避免所有someConditions,我在我的viewController 中添加了一个viewToFocusUIView 属性。然后在 getter 中,我检查该视图是否不为零并将其返回。否则返回默认视图。
  • 关于您的 viewController 问题,如果 viewControllers 视图是父 viewController 层次结构的一部分(我假设这就是您的意思)然后在父 viewController 的 preferredFocusedView getter 中返回 viewController 的视图.
【解决方案3】:

这是基于上述 Slayters 答案的另一种实现。我认为它比使用条件布尔值稍微优雅一些​​。

把它放在你的视图控制器中

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 = myUIView;

【讨论】:

  • 这在 iOS 10 中已被弃用。建议使用 preferredFocusEnvironments
【解决方案4】:

这里是目标C

- (UIView *)preferredFocusedView
{
    if (someCondition) {
      // this is if your menu is a tableview
        NSIndexPath *ip = [NSIndexPath indexPathForRow:2 inSection:0];
        UITableViewCell * cell = [self.categoryTableView cellForRowAtIndexPath:ip];

        return cell;
    }

    return self.view.preferredFocusedView;

}

在您的 viewDidLoad 或视图中确实出现了这样的事情:

    UIFocusGuide *focusGuide = [[UIFocusGuide alloc]init];
    focusGuide.preferredFocusedView = [self preferredFocusedView];
    [self.view addLayoutGuide:focusGuide];

如果你想在它第一次启动时这样做

【讨论】:

  • 我的单元格越来越为零,我使用的是collectionview而不是tableview!知道为什么它是 nil 吗?
【解决方案5】:

@elu5ion 的答案,但在objective-c 首先声明:

@property (nonatomic) UIView *preferredView;

设置这些方法:

-(void)setPreferredView:(UIView *)preferredView{
      if (preferredView != nil) {
         _preferredView = nil;
         UIFocusGuide *focusGuide = [[UIFocusGuide alloc]init];
         [self.view addLayoutGuide:focusGuide];
         focusGuide.preferredFocusedView = [self preferredFocusedView];
         [self setNeedsFocusUpdate];
         [self updateFocusIfNeeded];
    }
    _preferredView = preferredView;
 }


 - (UIView *)preferredFocusedView {
     if (_preferredView) {
          return _preferredView;
     }
     return self.view.preferredFocusedView;
}

【讨论】:

    【解决方案6】:

    这是一个不错的小 Swift 2 复制/粘贴 sn-p:

    var myPreferredFocusedView: UIView?
    override var preferredFocusedView: UIView? {
        return myPreferredFocusedView
    }
    func updateFocus(to view: UIView) {
        myPreferredFocusedView = napDoneView
        setNeedsFocusUpdate()
        updateFocusIfNeeded()
    }
    

    像这样使用它:

    updateFocus(to: someAwesomeView)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-12-18
      • 2016-05-13
      • 2015-12-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多