288

I know that currently the status bar (with the time, battery, and network connection) at the top of the iPhone/iPad is 20 pixels for non-retina screens and 40 pixels for retina screens, but to future proof my app I would like to be able to determine this without hard coding values. Is it possible to figure out the height of the status bar programmatically?

Kyr Dunenkoff
  • 8,090
  • 3
  • 23
  • 21
lehn0058
  • 19,977
  • 15
  • 69
  • 109

15 Answers15

517

[UIApplication sharedApplication].statusBarFrame.size.height. But since all sizes are in points, not in pixels, status bar height always equals 20.

Update. Seeing this answer being considered helpful, I should elaborate.

Status bar height is, indeed, equals 20.0f points except following cases:

  • status bar has been hidden with setStatusBarHidden:withAnimation: method and its height equals 0.0f points;
  • as @Anton here pointed out, during an incoming call outside of Phone application or during sound recording session status bar height equals 40.0f points.

There's also a case of status bar affecting the height of your view. Normally, the view's height equals screen dimension for given orientation minus status bar height. However, if you animate status bar (show or hide it) after the view was shown, status bar will change its frame, but the view will not, you'll have to manually resize the view after status bar animation (or during animation since status bar height sets to final value at the start of animation).

Update 2. There's also a case of user interface orientation. Status bar does not respect the orientation value, thus status bar height value for portrait mode is [UIApplication sharedApplication].statusBarFrame.size.height (yes, default orientation is always portrait, no matter what your app info.plist says), for landscape - [UIApplication sharedApplication].statusBarFrame.size.width. To determine UI's current orientation when outside of UIViewController and self.interfaceOrientation is not available, use [UIApplication sharedApplication].statusBarOrientation.

Update for iOS7. Even though status bar visual style changed, it's still there, its frame still behaves the same. The only interesting find about status bar I got – I share: your UINavigationBar's tiled background will also be tiled to status bar, so you can achieve some interesting design effects or just color your status bar. This, too, won't affect status bar height in any way.

Navigation bar tiled background is also tiled to status bar

Cœur
  • 37,241
  • 25
  • 195
  • 267
Kyr Dunenkoff
  • 8,090
  • 3
  • 23
  • 21
  • 6
    This method yields 1024 (iOS7) – Marc Aug 28 '13 at 08:42
  • @MarcMosby, it has nothing to do with iOS7. – Kyr Dunenkoff Aug 28 '13 at 10:42
  • Then what's the actual reason? – Marc Aug 28 '13 at 10:55
  • 1
    @MarcMosby, see my update. Remembered this issue - thanks to you. – Kyr Dunenkoff Aug 28 '13 at 11:26
  • 2
    Yes, as Marc pointed on iOS7 it yeilds 1024 sometimes and 20 sometimes. So this is no longer a fool proof way of determining the height. I doubt this is because of the transparent nature of the status bar on iOS 7. It could be that, it first goes to full screen and then resizes itself. So if you app queries during this transition, you might get the wrong value. May be calling this method with a delay might help on iOS 7. – Deepak G M Sep 19 '13 at 11:59
  • @DeepakGM, you should've probably check this before making assumptions. The UI rotation mechanics on iPad did not change for iOS7, this method still works, even in case of initially hidden status bar. – Kyr Dunenkoff Sep 19 '13 at 13:24
  • Doesn't it produce 40 due to retina displays? I think you always have to use view.contentScaleFactor to factor your sizes and points... – Todd Nov 14 '13 at 17:11
  • consider improve this answer with MattDiPasquale suggestion – mxb Aug 26 '14 at 07:41
  • The orientation issue appears to have been fixed in iOS 8, so no need to check the orientation on devices running iOS 8 and newer. – Isaac Overacker Oct 06 '14 at 21:22
  • @MarcMosby i bet you should have tested on iPad, in landscape mode. This methods always gives the right status bar frame **not depending on the orientation**. If the interface is in landscape mode, we would rather check the statusbar *width*. – Martin Oct 23 '14 at 14:31
  • 1
    There is a case where status bar height can be zero. If supportedInterfaceOrientations() return UIInterfaceOrientation (incorrect result but no compiler error) instead of UIInterfaceOrientationMask and a viewcontroller is presented and dismissed, status bar height will become zero. – Cymric Jul 04 '15 at 06:49
  • 5
    Also on iPhone X status bar will be higher. – pre Sep 13 '17 at 12:22
  • 2
    @pre Yep, iPhone X uses 44. – Sti Sep 20 '17 at 13:54
  • I'm always getting zero on iOS9 – webdevbyjoss May 08 '18 at 12:10
  • 1
    For newer iPad like iPad Pro 12.9" 3rd generation and iPad 11", the status bar height is 24 points (48 pixels). – CodeBrew May 17 '19 at 14:00
104

Go with Martin's suggestion to the question: Get iPhone Status Bar Height.

CGFloat AACStatusBarHeight()
{
    CGSize statusBarSize = [[UIApplication sharedApplication] statusBarFrame].size;
    return MIN(statusBarSize.width, statusBarSize.height);
}

And in Swift

func statusBarHeight() -> CGFloat {
    let statusBarSize = UIApplication.shared.statusBarFrame.size
    return Swift.min(statusBarSize.width, statusBarSize.height)
}

It seems like a hack, but it's actually pretty solid. Anyway, it's the only working solution.

Old Answer

The following code, which would go in your custom subclass of UIViewController, almost worked to support landscape. But, I noticed a corner case (when rotating from right > unsupported upside-down > left) for which it didn't work (switched height & width).

BOOL isPortrait = self.interfaceOrientation == UIInterfaceOrientationPortrait;
CGSize statusBarSize = [UIApplication sharedApplication].statusBarFrame.size;
CGFloat statusBarHeight = (isPortrait ? statusBarSize.height : statusBarSize.width);
Community
  • 1
  • 1
ma11hew28
  • 121,420
  • 116
  • 450
  • 651
  • This is not correct. The height of the status bar does not changes when you rotate the device. The width would, but the code above does not show that, nor was that the original question. – lehn0058 May 17 '13 at 01:16
  • 1
    You're right that "the height of the status bar does not changes when you rotate the device." But, as [Ash answered](http://stackoverflow.com/a/14692362/242933), "in landscape mode, you may find that width and height are swapped." The code above takes that into account. – ma11hew28 May 17 '13 at 11:43
  • This is an interesting issue I have been seeing now as well. It looks like a bug to me on Apple's side, but still needs to be accounted for. – lehn0058 Jan 02 '14 at 15:54
  • 2
    @lehn0058 It's not a bug, it's how Apple handles the bar internally. It is attached to a window and that window is rotated using a transform. The `statusBarFrame` is returned as the value before the transform. – Léo Natan Mar 08 '14 at 15:53
  • 1
    It looks better as a property :D `var statusBarHeight: CGFloat` – Pablo A. Oct 13 '17 at 23:16
23

Try this:

CGFloat statusBarHeight = [[UIApplication sharedApplication] statusBarFrame].size.height;
  • 1
    the height returned in different orientations is different. that's strange – atastrophic Dec 10 '13 at 12:20
  • 1
    Yes, if rotation is landscape - [[UIApplication sharedApplication] statusBarFrame].size.height and [[UIApplication sharedApplication] statusBarFrame].size.width values are switched. – Guntis Treulands May 10 '14 at 18:35
21

Swift 3 or Swift 4:

UIApplication.shared.statusBarFrame.height
iAj
  • 3,787
  • 1
  • 31
  • 34
Wilson
  • 9,006
  • 3
  • 42
  • 46
10

While the status bar is usually 20pt tall, it can be twice that amount in some situations:

  • when you're in the middle of a phone call (that's a pretty common scenario);
  • when the voice recorder, or Skype, or a similar app, is using the microphone in the background;
  • when Personal Hotspot is activated;

Just try it, and you'll see for yourself. Hardcoding the height to 20pt will usually work, until it doesn't.

So I second H2CO3's answer:

statusBarHeight = [[UIApplication sharedApplication] statusBarFrame].size.height;
Guntis Treulands
  • 4,764
  • 2
  • 50
  • 72
TotoroTotoro
  • 17,524
  • 4
  • 45
  • 76
10

EDIT The iOS 11 way to work out where to put the top of your view content is UIView's safeAreaLayoutGuide See UIView Documentation.

DEPRECATED ANSWER If you're targeting iOS 7+, The documentation for UIViewController advises that the viewController's topLayoutGuide property gives you the bottom of the status bar, or the bottom of the navigation bar, if it's also visible. That may be of use, and is certainly less hack than many of the previous solutions.

Joshua J. McKinnon
  • 1,696
  • 1
  • 18
  • 29
10

For iOS 13 you can use:

UIApplication.shared.keyWindow?.windowScene?.statusBarManager?.statusBarFrame.height
Eugene Lezov
  • 722
  • 7
  • 12
5

Don't forget that the status bar's frame will be in the screen's coordinate space! If you launch in landscape mode, you may find that width and height are swapped. I strongly recommend that you use this version of the code instead if you support landscape orientations:

CGRect statusBarFrame = [self.window convertRect:[UIApplication sharedApplication].statusBarFrame toView:view];

You can then read statusBarFrame's height property directly. 'View' in this instance should be the view in which you wish to make use of the measurements, most likely the application window's root view controller.

Incidentally, not only may the status bar be taller during phone calls, it can also be zero if the status bar has been deliberately hidden.

Ash
  • 9,064
  • 3
  • 48
  • 59
  • This didn't give me the correct height. But, I found different way that worked for me: http://stackoverflow.com/a/16598350/242933 – ma11hew28 May 16 '13 at 22:12
  • Yeah this is pretty old code now so is probably no longer a valid answer. Personally I no longer ever have any need to check the height of the status bar, thanks to auto layout. – Ash Jul 14 '16 at 14:21
4
    var statusHeight: CGFloat!
    if #available(iOS 13.0, *) {
         statusHeight = UIApplication.shared.keyWindow?.windowScene?.statusBarManager?.statusBarFrame.height
    } else {
        // Fallback on earlier versions
        statusHeight = UIApplication.shared.statusBarFrame.height
    }
Bassant Ashraf
  • 1,531
  • 2
  • 16
  • 23
3

UIApplication.shared.statusBarFrame.height was deprecated in iOS 13

'statusBarFrame' was deprecated in iOS 13.0: Use the statusBarManager property of the window scene instead.

You can retrieve status bar height in iOS 13 like follows:

let statusBarHeight = view.window?.windowScene?.statusBarManager?.statusBarFrame.height

NB! It's optional so make sure you have correct fallback.

fewlinesofcode
  • 3,007
  • 1
  • 13
  • 30
2

Here is a Swift way to get screen status bar height:

var screenStatusBarHeight: CGFloat {
    return UIApplication.sharedApplication().statusBarFrame.height
}

These are included as a standard function in a project of mine: https://github.com/goktugyil/EZSwiftExtensions

Esqarrouth
  • 38,543
  • 21
  • 161
  • 168
0

By default Status Bar height in iOS is 20 pt.

More info: http://www.idev101.com/code/User_Interface/sizes.html

António Almeida
  • 9,620
  • 8
  • 59
  • 66
Chris Alan
  • 1,426
  • 14
  • 14
0

I just found a way that allow you not directly access the status bar height, but calculate it.

Navigation Bar height - topLayoutGuide length = status bar height

Swift:

let statusBarHeight = self.topLayoutGuide.length-self.navigationController?.navigationBar.frame.height

self.topLayoutGuide.length is the top area that's covered by the translucent bar, and self.navigationController?.navigationBar.frame.height is the translucent bar excluding status bar, which is usually 44pt. So by using this method you can easily calculate the status bar height without worring about status bar height change due to phone calls.

Henry Ngan
  • 572
  • 1
  • 4
  • 24
0

Swift 5

UIApplication.shared.statusBarFrame.height

-6

Using following single line code you can get status bar height in any orientation and also if it is visible or not

#define STATUS_BAR_HIGHT (
    [UIApplicationsharedApplication].statusBarHidden ? 0 : (
        [UIApplicationsharedApplication].statusBarFrame.size.height > 100 ?
            [UIApplicationsharedApplication].statusBarFrame.size.width :
            [UIApplicationsharedApplication].statusBarFrame.size.height
    )
)

It just a simple but very useful macro just try this you don't need to write any extra code

António Almeida
  • 9,620
  • 8
  • 59
  • 66
Amol Hirkane
  • 75
  • 1
  • 11