Search code examples
swiftuistatusbar

UIStatusBarStyle doesn't change


I'm working on a swift app and I wanna change the UIStatusBarStyle according to the app's theme (there are 2 options - light and dark theme). I have set View controller-based status bar appearance to NO in the info.plist and in the UIViewController I tried to set it based on the current theme like so:

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

}

No result really. I tried to test it by returning only: return .lightContent but that didn't change the status bar either.

What am I doing wrong?

UPDATE:

Okay, so this is what I'm trying to do and it's not working.

    fileprivate func applyTheme() {

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

}

override var preferredStatusBarStyle: UIStatusBarStyle {
    return statusBarStyle
}

And it's not working. Despite changing the theme, the status bar always remain with the default style. applyTheme() is called in viewDidLoad() and viewWillAppear()


Solution

  • You need to call this method after any change

    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
        }
    
    }
    

    enter image description here