View got hidden below UINavigationBar iOS 7

42,524

Solution 1

Try navigationBar.translucent = NO;, It is YES by default in iOS7.

It is also good to take a look on this part of UINavigationBar documentation:

New behavior on iOS 7. Default is YES. You may force an opaque background by setting the property to NO. If the navigation bar has a custom background image, the default is inferred from the alpha values of the image—YES if it has any pixel with alpha < 1.0 If you send setTranslucent:YES to a bar with an opaque custom background image it will apply a system opacity less than 1.0 to the image. If you send setTranslucent:NO to a bar with a translucent custom background image it will provide an opaque background for the image using the bar's barTintColor if defined, or black for UIBarStyleBlack or white for UIBarStyleDefault if barTintColor is nil.

Edit:

Setting 'navigationBar.translucent' value causes exception if you run project in devices/simulators having older iOS versions.

So you can add a version check like this:

float systemVersion = [[[UIDevice currentDevice] systemVersion] floatValue];
if (systemVersion >= 7.0)
{
    navigationBar.translucent = NO;
}

Another option would be to set:

vc.edgesForExtendedLayout = UIRectEdgeNone;

Swift 3:

vc.edgesForExtendedLayout = []

Solution 2

You can stop your views going under the navigation bar, in your viewController:

self.edgesForExtendedLayout = UIRectEdgeNone;

Solution 3

Swift 3+:

self.edgesForExtendedLayout = []

Solution 4

If you do not need translucent navigation bar in your app you can fix this on iOS7 and iOS6 without code changes.

In storyboard select your navigation controller and then open "Attributes Inspector". Then under "Simulated Metrics" set "Top Bar" to some value but not to "translucent":

Setting Top Bar style

Now your views on iOS6 and iOS7 will have the same positioning as before.

Solution 5

Point #7 on this list does the trick. You still have to wrap it in iOS 7-checking code like @null's answer:

float systemVersion = [[[UIDevice currentDevice] systemVersion] floatValue];
if (systemVersion >= 7.0) {
    viewController.edgesForExtendedLayout = UIRectEdgeNone;
}

The whole article is useful to those transitioning to iOS 7.

Share:
42,524
Salman Zaidi
Author by

Salman Zaidi

Updated on September 28, 2020

Comments

  • Salman Zaidi
    Salman Zaidi over 3 years

    Earlier, I was using iOS 6.1 for my project. Recently I have switched to iOS 7. For, a lot of changes I knew, I updated my code.. But I have observed a strange behavior. My view on every screen gets hidden below navigation bar. Repositioning view solves the problem for iOS7, but creates problems for older iOS versions.

    Can anyone explain me, what is the reason and why does it happen?? What has been changed in iOS 7 that's causing this problem??

    Any help would be appreciated..

  • Salman Zaidi
    Salman Zaidi almost 11 years
    You have given answer for status bar appearance.. But I was asking for view hidden under UINavigationBar. +1 for your help btw.. :-)
  • Salman Zaidi
    Salman Zaidi almost 11 years
    Thanks for the solution.. It does have solved the problem.. and now I understand as well why it happens :-)
  • Guy Kogus
    Guy Kogus almost 11 years
    Oops, got too trigger happy with answering a question :p
  • Salman Zaidi
    Salman Zaidi almost 11 years
    if ([self.navigationBar respondsToSelector:@selector(setTranslucent:)]) does not work.. results in crash. I had tried this first..
  • PakitoV
    PakitoV over 10 years
    after many headaches this is it, this is the best way to go here. Thanks
  • SG1
    SG1 almost 10 years
    This also will stop a scrollView which has been programmatically added below (not beneath) the navigationbar/statusbar from automatically changing its content offset as if it were underneath the bars.
  • jchnxu
    jchnxu almost 10 years
    This is a life saver for those who wants to init the view controllers programmatically
  • Greeso
    Greeso over 9 years
    I think the edgesForExtendedLayout solution is probably better, at least in my case, due to the fact that it keeps the nav bar translucent yet the view is positioned correctly.
  • Ahsan Ebrahim
    Ahsan Ebrahim about 9 years
    self.edgesForExtendedLayout = UIRectEdgeNone; worked for me.. thanks a lot.. +1
  • Lohith Korupolu
    Lohith Korupolu almost 7 years
    any other solution? I have a problem with the View going underneath the status bar.