tvOS UITabBarController начать расфокусированный
у меня есть простое приложение tvOS, начинающееся с UITabBarController
и я хочу, чтобы основной вид имел Фокус при запуске приложения, а не панель вкладок.
Я пробовал играть с self.tabBarController.tabBar.userInteractionEnabled
временно удалить фокус, но напрасно. (Кроме того, мне не нравится такой обходной путь)
любой ключ?
спасибо заранее.
6 ответов
вышеуказанный подход в основном работает, но не позволяет выбрать элемент панели вкладок с помощью щелчка, поскольку он возвращает панель вкладок в том случае, когда он должен вернуть selectedItem. Вот улучшенная версия, которая решает это, возвращая [super preferredViewController] вместо tabBar в обычном случае. Эта версия также скрывает панель вкладок с Альфой при запуске, чтобы она не мерцала. Вероятно, есть более изящные способы прятаться.
@interface MWTabBarController ()
@property (nonatomic, assign) BOOL firstTime;
@end
@implementation MWTabBarController
- (void)viewDidLoad {
[super viewDidLoad];
self.firstTime = YES;
self.tabBar.alpha = 0;
[NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(unAlphaTabBar) userInfo:nil repeats:NO];
}
- (void) unAlphaTabBar
{
self.tabBar.alpha = 1;
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
- (UIView *)preferredFocusedView {
if (self.firstTime) {
self.firstTime = NO;
return self.selectedViewController.preferredFocusedView;
}
else {
return [super preferredFocusedView];
}
}
мое оригинальное решение больше не работает на tvOS 9.3, поэтому я нашел новый с подклассами UITabBarController
:
@interface TVTabBarController : UITabBarController
@property (nonatomic) BOOL useDefaultFocusBehavior;
@end
@implementation TVTabBarController
- (UIView *)preferredFocusedView {
return self.useDefaultFocusBehavior ? [super preferredFocusedView] : self.selectedViewController.preferredFocusedView;
}
- (void)didUpdateFocusInContext:(UIFocusUpdateContext *)context withAnimationCoordinator:(UIFocusAnimationCoordinator *)coordinator {
[super didUpdateFocusInContext:context withAnimationCoordinator:coordinator];
self.useDefaultFocusBehavior = YES;
}
@end
...
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.tabBarController.tabBar.hidden = YES; // or do it in storyboard
}
если вы используете раскадровки для начальной настройки пользовательского интерфейса, не забудьте установить пользовательский класс TVTabBarController
к контроллеру панели вкладок там.
оригинальное решение:
предлагаемый подход с наследованием от UITabBarController
не работает для меня, потому что на самом деле -preferredFocusedView
вызывается дважды при запуске, поэтому мне пришлось добавить счетчик, чтобы вернуться self.selectedViewController.preferredFocusedView
для первого 2 звонков. Но это действительно хакерское решение, и нет никакой гарантии, что оно не сломается в будущем.
поэтому я нашел гораздо лучшее решение: обновление Force focus в appdelegate -applicationDidBecomeActive:
по первому зову.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.tabBarController.tabBar.hidden = YES;
}
- (void)applicationDidBecomeActive:(UIApplication *)application {
static BOOL forceFocusToFirstTab = YES;
if (forceFocusToFirstTab) {
forceFocusToFirstTab = NO;
[self.tabBarController.selectedViewController updateFocusIfNeeded];
}
}
Я нашел решение, поэтому, если кто-то заинтересован, вам просто нужно подкласс UITabBarController
и переопределить preferredFocusedView
:
@interface ZTWTabBarController ()
@property (nonatomic, assign) BOOL firstTime;
@end
@implementation ZTWTabBarController
- (void)viewDidLoad {
[super viewDidLoad];
self.firstTime = YES;
}
- (UIView *)preferredFocusedView {
if (self.firstTime) {
self.firstTime = NO;
return self.selectedViewController.preferredFocusedView;
}
else {
return [super preferredFocusedView];
}
}
@end
Это самое простое и чистое решение, на мой взгляд:
override var preferredFocusedView: UIView? {
if tabBar.hidden {
return selectedViewController?.preferredFocusedView
}
return super.preferredFocusedView
}
я смог достичь этого эффекта очень просто с помощью isHidden
свойства UITabBar
.
override func viewDidLoad() {
super.viewDidLoad()
self.tabBar.isHidden = true
}
когда пользователь прокручивает вверх, чтобы отобразить панель вкладок,UITabBarController
будет отображать его автоматически.
С preferredFocusedView
устарел в tvOS, вы должны переопределить preferredFocusEnvironments
собственность вместо
Swift 4.0
override var preferredFocusEnvironments: [UIFocusEnvironment] {
if firsTime, let enviroments = selectedViewController?.preferredFocusEnvironments {
firsTime = false
return enviroments
}
return super.preferredFocusEnvironments
}