如何在iOS 9中隐藏单个视图控制器的状态栏?

48

在一个我以模态方式呈现的 ViewController 中,我进行了以下操作:

override func prefersStatusBarHidden() -> Bool {
    return true
}

这曾经有效,但现在不再有效。如何最好地隐藏状态栏,仅针对此视图控制器


只是以编程方式检查此内容。 这里 - Rushi trivedi
它仍然可以正常工作。如果您想将该函数应用于所有视图控制器,则考虑使用继承。 - Tim
可能是如何在iOS中隐藏状态栏?的重复问题。 - Jake Chasan
1
只需转到info.plist并按照@lance所述将View controller-based status bar appearance更新为YES - Akshay Jadhav
15个回答

70

对于Swift 3和Swift 4,覆盖变量的方式已更改,如下所示:

override var prefersStatusBarHidden: Bool {
  return true
}
如果您希望在视图控制器已经显示后“更新”状态,您需要调用以下方法:

setNeedsStatusBarAppearanceUpdate()
请参考文档

1
在TabBarController中调用setNeedsStatusBarAppearanceUpdate()方法并不会触发prefersStatusBarHidden方法。 - famfamfam
@famfamfam 请确保您的info.plist中没有禁用基于控制器的状态栏外观。如果是这样,该属性将被完全忽略。此外,PrefersStatusBarHidden可能会在父控制器中调用。这取决于您如何组织您的视图控制器。 - Pochi

47

对于 Swift 3 和 Swift 4.2 版本,当视图将要出现时

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)

    UIApplication.shared.isStatusBarHidden = true
}

当视图要消失时

override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)

    UIApplication.shared.isStatusBarHidden = false
}

可能需要在您的 info.plist 文件中设置下一行:

View controller-based status bar appearance = NO

enter image description here


1
这是唯一一个在我的情况下完美运行的答案,太棒了! - XIII
我相信它能够工作,因为你搞乱了ViewController的层次结构,系统没有调用prefersStatusBarHidden。 - Paweł Brewczynski
这是我能做到的唯一方法,但我还必须在我的info.plist文件中添加<key>UIViewControllerBasedStatusBarAppearance</key><false/>。 - Guilherme Carvalho
isStatusBarHidden 在 iOS 9.0 中已被弃用。 - msmq

21

在您的UIViewController中:

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    UIApplication.shared.isStatusBarHidden = true
}

 override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    //It will show the status bar again after dismiss
    UIApplication.shared.isStatusBarHidden = false
}

override var prefersStatusBarHidden: Bool {
    return true
}

1
我刚刚使用了它,它完美地工作了!谢谢你。 - Drewgost
在iOS 9.0中,'isStatusBarHidden'的设置器已被弃用:请使用-[UIViewController prefersStatusBarHidden]。 - msmq

19

在iOS 9、Xcode 7、Swift 2.0中,它回到了以前的状态。

override func prefersStatusBarHidden() -> Bool {
        return true
}

实际上,Xcode会告诉你这一点

UIApplication.sharedApplication().setStatusBarHidden(true, withAnimation: .None) 

已被弃用,建议您使用prefersStatusBarHidden方法。


8
如果 prefersStatusBarHidden 方法没有做任何操作,就在你的 viewDidLoad 或 viewDidAppear 方法中添加 setNeedsStatusBarAppearanceUpdate()。这取决于你想要实现什么效果。 - Benjamin

16

对于 Swift 3,

override var prefersStatusBarHidden: Bool{
        return true
    }

并添加 viewDidLoad()

self.modalPresentationCapturesStatusBarAppearance = true

2
最佳答案 - Booharin

8
您可以通过简单地在您的ViewController中覆盖prefersStatusBarHidden属性来实现此目的,如下所示:
override var prefersStatusBarHidden: Bool {
   return true
}

添加了屏幕截图

此方法适用于Swift 3/4。


它对于推送的视图控制器不起作用。 - msmq

4
使用UIAnimation和存储属性,可以平滑地隐藏状态栏。 Swift 3+
  var statusBarState = false
    override var prefersStatusBarHidden: Bool{
        return statusBarState
    }

在viewWillAppear中

  override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)
        statusBarState = true
        UIView.animate(withDuration: 0.30) {
            self.setNeedsStatusBarAppearanceUpdate()
        }
    }

enter image description here


这是自iOS 9.0+以来正确的做事方式。 - JaredH

3

对于那些仍在苦苦挣扎的人,以下方法适用于iOS9。

通过从您的单个子/孙视图控制器调用它来更新rootViewController prefersStatusBarHidden函数。这适用于您直接将childViewControllers添加到rootViewController的情况。

您不需要在info.plist中设置任何内容,但是设置“statusBarIsInitiallyHidden”与下面的设置无关。

首先,在您的rootViewController中添加以下内容:

-(void)viewDidLoad {
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(updateStatusBarAppearance:) name:@"kStatusBarAppearance" object:nil]; 
}
-(void)updateStatusBarAppearance:(NSNotification *)n {
    statusBarIsHidden = [n.object boolValue];
    [self setNeedsStatusBarAppearanceUpdate];
}
-(UIStatusBarStyle)preferredStatusBarStyle {
    return UIStatusBarStyleLightContent; //optional
}
-(BOOL)prefersStatusBarHidden{
    return statusBarIsHidden;
}

接下来,在你想要隐藏状态栏的单个视图控制器中,调用以下代码:

-(void)viewDidLoad {
    [[NSNotificationCenter defaultCenter] postNotificationName:@"kStatusBarAppearance" object:[NSNumber numberWithBool:true]];
}
-(void)popSelf {
    [[NSNotificationCenter defaultCenter] postNotificationName:@"kStatusBarAppearance" object:[NSNumber numberWithBool:false]];
}

2

当其他方法都失败时(如我所遇到的情况),Swift 4.1

无需编辑 .plist 文件。并且 AppStore 将会批准它。

(UIApplication.shared.value(forKey: "statusBarWindow") as? UIWindow)?.isHidden = false

2
一个晚回答,但如果你需要另一种解决方案,你可以使用这个:
public func ShowStatusBar() {

    let statusBarWindow = UIApplication.shared.value(forKey: "statusBarWindow") as? UIWindow
    UIView.animate(withDuration: 0.3) {
        statusBarWindow?.alpha = 1
    }
}

public func HideStatusBar() {

    let statusBarWindow = UIApplication.shared.value(forKey: "statusBarWindow") as? UIWindow
    UIView.animate(withDuration: 0.3) {
        statusBarWindow?.alpha = 0
    }
}

StatusBarWindow 在 iOS 13 或更新版本中已不可用。 - Jesús Mateos Gomez

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接