Basically all you need is a Base VC that you will be subclassing in the VC's you want to control the status bar.
In there you will be subscribing for a given Notification, which when sent will control the status bar of the VC.
Here is the code:
extension Notification.Name {
static var statusBarShowHide: Notification.Name {
return .init(rawValue: "StatusBar.showHide")
}
}
class StatusBarControllableVC : UIViewController {
private var statusBarHidden = false
private func topViewController() -> UIViewController? {
var topController = UIApplication.shared.keyWindow?.rootViewController
while topController?.presentedViewController != nil {
topController = topController?.presentedViewController
}
return topController
}
override var prefersStatusBarHidden: Bool {
return statusBarHidden
}
@objc func statusBarShowHide(notification: NSNotification) {
guard let userInfo = notification.userInfo else {return}
let topController = topViewController()
if let hidden = userInfo["hidden"] as? Bool, self == topController {
statusBarHidden = hidden
self.setNeedsStatusBarAppearanceUpdate()
}
}
override func viewDidLoad() {
NotificationCenter.default.addObserver(self, selector: #selector(statusBarShowHide(notification:)), name: .statusBarShowHide, object: nil)
super.viewDidLoad()
}
}
Now whenever you need to show or hide the Status Bar, you will post a Notification like this:
NotificationCenter.default.post(name: .statusBarShowHide, object: nil, userInfo: ["hidden":true])
I believe this is the simplest approach.
In the code above I'm only showing/hiding the Status Bar on the Top Most View Controller, but obviously you can change that