UIStatusBarStyle 不会改变

Posted

技术标签:

【中文标题】UIStatusBarStyle 不会改变【英文标题】:UIStatusBarStyle doesn't change 【发布时间】:2018-08-11 12:02:49 【问题描述】:

我正在开发一个 swift 应用程序,我想根据应用程序的主题更改 UIStatusBarStyle(有 2 个选项 - 浅色和深色主题)。我在info.plistUIViewController 中将View controller-based status bar appearance 设置为NO,我尝试根据当前主题设置它,如下所示:

override var preferredStatusBarStyle: UIStatusBarStyle 
    return Theme.current.statusBarStyle



protocol ThemeProtocol  
    // Status Bar
    var statusBarStyle: UIStatusBarStyle  get  


class Theme 
    static var current: ThemeProtocol = LightTheme()


class LightTheme: ThemeProtocol 
    // Status Bar 
    var statusBarStyle: UIStatusBarStyle = .default



class DarkTheme: ThemeProtocol 
    // Status Bar 
    var statusBarStyle: UIStatusBarStyle = .lightContent


真的没有结果。我试图通过只返回来测试它:return .lightContent 但这也没有改变状态栏。

我做错了什么?

更新:

好的,这就是我正在尝试做的,但它不起作用。

    fileprivate func applyTheme() 

    statusBarStyle = UserDefaults.standard.bool(forKey: SelectedThemeKey) ? .default : .lightContent
    self.setNeedsStatusBarAppearanceUpdate()



override var preferredStatusBarStyle: UIStatusBarStyle 
    return statusBarStyle

而且它不起作用。尽管更改了主题,但状态栏始终保持默认样式。 applyTheme()viewDidLoad()viewWillAppear() 中被调用

【问题讨论】:

【参考方案1】:

你需要在任何改变后调用这个方法

setNeedsStatusBarAppearanceUpdate()

//

class ViewController: UIViewController 

    var current = UIStatusBarStyle.default

    @IBAction func changeClicked(_ sender: Any) 
        current = current == .default ? .lightContent : .default
        self.setNeedsStatusBarAppearanceUpdate()
    
    override func viewDidLoad() 
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
    
    override  var preferredStatusBarStyle: UIStatusBarStyle 
        return current
    


【讨论】:

我正在尝试复制您共享的内容,但由于某种原因它无法正常工作。你能看看我上面帖子中的更新代码吗? 这是在默认项目设置上创建的,所以回滚到您在 info.plist 中所做的每一项更改 是的,我刚刚从info.plist 中删除了View controller-based status bar appearance,现在一切正常。谢谢! 当你想完全隐藏它时设置为否 写 current = current == .default 是什么意思? .lightContent:.default? ....我知道 current == .default 意味着 current 的值等于 .default 但我正在尝试理解其余部分。【参考方案2】:

首先,您的代码毫无意义。你说

我已在 info.plist 中将基于视图控制器的状态栏外观设置为 NO,并在 UIViewController 中尝试设置它

所以一方面你告诉运行时,不要听我的视图控制器。然后当运行时不听你的视图控制器时你会抱怨!

其次,请记住,您的视图控制器在状态栏外观中没有发言权,除非它是***视图控制器(或者***视图控制器故意服从它)。例如,如果您的视图控制器位于导航控制器内部,则其 statusBarStyle 是完全不相关的。

【讨论】:

我实际上读到您需要将View controller-based status bar appearance 设置为NO 才能工作,这对我来说毫无意义,但这是非常错误的。谢谢你指出。以及更多信息【参考方案3】:

第一

如果您尝试将StatusBarStyle 更改为UIApplication.shared.statusBarStyle = .default,那么您应该设置 View controller-based status bar appearance 变为 NO

这样,UIApplication.shared.statusBarStyle处处需要你自己控制;例如viewWillAppear / viewWillDisappear

但此方法在 ios 9 之后已弃用。

现在我建议你学习新方法:

请将View controller-based status bar appearance 设置为YES,并且

覆盖UIViewControllerpreferredStatusBarStyle 来处理它。

override var preferredStatusBarStyle: UIStatusBarStyle 
    return .default

但还是不行,为什么?

在你的情况下,我猜UIViewControllerviewControllersUINavigationController 之一。

如果您使用了UINavigationController,则应在UINavigationController 中覆盖preferredStatusBarStyle

也许你会说我需要用不同的视图控制器设置不同的状态栏样式,没关系。

只需像这样在UINavigationController 中覆盖childForStatusBarStyle

override var childForStatusBarStyle: UIViewController? 
    return topViewController

然后在UIViewController 中覆盖您要更改的preferredStatusBarStyle

您也可以像这样通过extension 制作它

extension UINavigationController 
    override open var childForStatusBarStyle: UIViewController? 
        return topViewController
    

【讨论】:

以上是关于UIStatusBarStyle 不会改变的主要内容,如果未能解决你的问题,请参考以下文章

改变状态栏颜色

如何在带有导航栏的模态视图中更改 iOS 7 中的 UIStatusBarStyle?

如何使用导航栏在模态视图中更改iOS 7中的UIStatusBarStyle?

用户使用 UISearchBar 时更改 UIStatusBarStyle

改变status bar的状态

Swift 3 UIStatusBarStyle 不适用于 UINavigationController 中的单独 ViewController