iOS 7的状态栏回到iPhone 6应用程序的默认样式?

在iOS 7中, UIStatusBardevise方式就是像这样与视图合并:

GUI由TinaTavčar设计 (由TinaTavčardevise的GUI)

  • 这很酷,但是当你在视图顶部有一些东西的时候,它会让你的视图变得有些混乱,并且会和状态栏重叠。

  • 有没有一个简单的解决scheme(如在info.plist中设置属性),可以改变它的工作方式[不重叠]回到它在iOS6中的方式?

  • 我知道一个更简单的解决scheme是每个单一的视图控制器有self.view.center.x + 20点,但改变它们会拧紧其他尺寸(有一个不同的self.view.center.x会导致问题,自定义赛格等等),突然间变成了一个乏味的工作,最好避免。

  • 如果有人能为我提供一个单线解决scheme,我真的很高兴。

PS我知道我可以隐藏状态栏做事情就像有

 [[UIApplication sharedApplication] setStatusBarHidden:YES withAnimation:UIStatusBarAnimationNone]; 

didFinishLaunchingWithOptions方法中,但这是一个解决方法,避免了问题的捷径,所以我不认为这是一个真正的解决scheme。

这是从我写的博客文章交叉发布的,但这里是iOS 7上的状态栏,导航栏和容器视图控制器的完整概要:

  1. 没有办法保留iOS 6风格的状态栏布局。 状态栏将始终与iOS 7上的应用程序重叠

  2. 不要将状态栏外观与状态栏布局混淆。 外观(亮或默认)不会影响状态栏的布局(框架/高度/重叠)。 系统状态栏不再有任何背景色,这一点很重要。 当API引用UIStatusBarStyleLightContent时,它们表示在清晰背景上的白色文本。 UIStatusBarStyleDefault是清晰背景上的黑色文本。

  3. 状态栏的外观是通过两个互斥的基础path之一来控制的:你可以用传统的方式编程设置它们,或者UIKit会根据UIViewController的一些新属性来更新外观。 后面的选项默认是打开的。 检查你的应用程序的“基于ViewController的状态栏外观”的plist值,看看你正在使用哪一个。 如果将此值设置为YES,则应用中的每个顶级视图控制器(除标准UIKit容器视图控制器外)都需要覆盖preferredStatusBarStyle,并返回默认样式或样式。 如果将plist值编辑为NO,则可以使用熟悉的UIApplication方法来pipe理状态栏外观。

  4. UINavigationController会将其UINavigationBar的高度更改为44点或64点,这取决于一个相当奇怪的和没有logging的约束。 如果UINavigationController检测到其视图的框架的顶部与UIWindow的顶部相邻,则绘制其导航栏,高度为64点。 如果它的顶端与UIWindow的顶端不相连(即使只closures了一个点),那么它将以44的高度以“传统”方式绘制其导航栏。 即使在应用程序的视图控制器层次结构中存在多个子项,UINavigationController也会执行此逻辑。 没有办法阻止这种行为。

  5. 如果您提供的自定义导航栏背景图像的高度仅为44(88像素),并且UINavigationController的视图边界与UIWindow的边界相匹配(如#4所述),则UINavigationController将在框架中绘制图像(0,20,320 ,44),在自定义图像上留下20个不透明的黑色空间。 这可能会让你觉得自己是一个聪明的开发者,他忽略了规则1,但是你错了。 导航栏仍然是64点高。 将UINavigationControllerembedded到幻灯片显示风格的视图层次结构中,使其非常清晰。

  6. 注意UIViewController的混淆命名的edgesForExtendedLayout属性。 在大多数情况下调整edgesForExtendedLayout不做任何事情。 UIKit使用此属性的唯一方法是,如果将视图控制器添加到UINavigationController,则UINavigationController使用edgesForExtendedLayout来确定其子视图控制器是否应在导航栏/状态栏区域下方可见。 在UINavigationController上设置edgesForExtendedLayout本身不会改变UINavigationController是否有44或64点的高导航栏区域。 请参阅#4的逻辑。 使用工具栏或UITabBarController时,类似的布局逻辑适用于视图的底部。

  7. 如果你所要做的就是在UINavigationController中防止你的自定义的子视图控制器在导航条的下面,那么将edgesForExtendedLayout设置为UIRectEdgeNone(或者至less是一个不包括UIRectEdgeTop的遮罩)。 在视图控制器的生命周期中尽可能早地设置此值。

  8. UINavigationController和UITabBarController也将尝试在其子视图层次结构中填充表视图和集合视图的contentInsets。 它以类似于#4的状态栏逻辑的方式执行此操作。 有一种防止这种情况的编程方式,通过为表视图和集合视图自动设置“调整滚动视图集”为NO(默认为YES)。 这给Whisper和Riposte带来了一些严重的问题,因为我们使用contentInset调整来控制表视图的布局以响应工具栏和键盘的移动。

  9. 重申:没有办法返回到iOS 6风格的状态栏布局逻辑。 为了逼近这个,你必须把你的应用程序的所有视图控制器移动到一个容器视图,从屏幕顶部偏移20点,在状态栏后留下一个故意的黑色视图来模拟旧的外观。 这是我们最终在Riposte和Whisper中使用的方法。

  10. 苹果正在努力确保你不会去做#9。 他们希望我们重新devise所有我们的应用程序,以低于状态栏。 然而,对于用户体验和技术原因,有许多有力的论据,为什么这并不总是一个好主意。 你应该为用户做最好的事情,而不是简单地遵循平台的奇思妙想。

2013年9月19日更新:

通过添加self.window.bounds = CGRectMake(0, 20, self.window.frame.size.width, self.window.frame.size.height);修复缩放错误self.window.bounds = CGRectMake(0, 20, self.window.frame.size.width, self.window.frame.size.height);

纠正了在NSNotificationCenter语句中的拼写错误

2013年9月12日更新:

UIViewControllerBasedStatusBarAppearance更正为NO

为屏幕旋转的应用程序添加了解决scheme

添加了一个方法来改变状态栏的背景颜色。

显然,没有办法将iOS7状态栏恢复到它在iOS6中的工作方式。

但是,我们总是可以编写一些代码,并将状态栏变成iOS6状态,这是我能想到的最短的方式:

  1. info.plist中将UIViewControllerBasedStatusBarAppearance设置为NO (要退出视图控制器调整状态栏样式,以便我们可以使用UIApplicationstatusBarStyle方法设置状态栏样式。)

  2. 在AppDelegate的application:didFinishLaunchingWithOptions ,调用

     if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_1) { [application setStatusBarStyle:UIStatusBarStyleLightContent]; self.window.clipsToBounds =YES; self.window.frame = CGRectMake(0,20,self.window.frame.size.width,self.window.frame.size.height-20); //Added on 19th Sep 2013 self.window.bounds = CGRectMake(0, 20, self.window.frame.size.width, self.window.frame.size.height); } return YES; 

为了:

  1. 检查它是否是iOS 7。

  2. 将状态栏的内容设置为白色,而不是UIStatusBarStyleDefault。

  3. 避免子框架超出可见边界的子视图显示出来(对于从顶部到主视图的animation视图)。

  4. 通过移动和调整应用程序的窗口框架,创build状态栏占用空间的错觉,就像iOS 6中的情况一样。

对于屏幕旋转的应用程序,

使用NSNotificationCenter通过添加检测方向更改

 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationDidChangeStatusBarOrientation:) name:UIApplicationDidChangeStatusBarOrientationNotification object:nil]; 

if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_1)并在AppDelegate中创build一个新的方法:

 - (void)applicationDidChangeStatusBarOrientation:(NSNotification *)notification { int a = [[notification.userInfo objectForKey: UIApplicationStatusBarOrientationUserInfoKey] intValue]; int w = [[UIScreen mainScreen] bounds].size.width; int h = [[UIScreen mainScreen] bounds].size.height; switch(a){ case 4: self.window.frame = CGRectMake(0,20,w,h); break; case 3: self.window.frame = CGRectMake(-20,0,w-20,h+20); break; case 2: self.window.frame = CGRectMake(0,-20,w,h); break; case 1: self.window.frame = CGRectMake(20,0,w-20,h+20); } } 

所以当方向改变时,它会触发一个switch语句来检测应用程序的屏幕方向(纵向,倒置,左侧横向或右侧横向),并分别更改应用程序的窗口框架,以创buildiOS 6状态栏错觉。

要更改状态栏的背景颜色,请执行以下操作:

  @property (retain, nonatomic) UIWindow *background; 

AppDelegate.h中使background成为你的类的一个属性,并防止ARC释放它。 (如果您不使用ARC,则不必这样做。)

之后你只需要在if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_1)创buildUIWindow:

 background = [[UIWindow alloc] initWithFrame: CGRectMake(0, 0, self.window.frame.size.width, 20)]; background.backgroundColor =[UIColor redColor]; [background setHidden:NO]; 

不要忘记@synthesize background;@implementation AppDelegate

更新(新解决scheme)

此更新是iOS 7导航栏问题的最佳解决scheme。您可以设置导航栏颜色示例:FakeNavBar.backgroundColor = [UIColor redColor];

注意:如果您使用默认导航控制器,请使用旧的解决scheme。

AppDelegate.m

 - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { if(NSFoundationVersionNumber >= NSFoundationVersionNumber_iOS_7_0) { UIView *FakeNavBar = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 320, 20)]; FakeNavBar.backgroundColor = [UIColor whiteColor]; float navBarHeight = 20.0; for (UIView *subView in self.window.subviews) { if ([subView isKindOfClass:[UIScrollView class]]) { subView.frame = CGRectMake(subView.frame.origin.x, subView.frame.origin.y + navBarHeight, subView.frame.size.width, subView.frame.size.height - navBarHeight); } else { subView.frame = CGRectMake(subView.frame.origin.x, subView.frame.origin.y + navBarHeight, subView.frame.size.width, subView.frame.size.height); } } [self.window addSubview:FakeNavBar]; } return YES; } 

老解决scheme – 如果您使用以前的代码,请忽略下面的代码和图像

这是iOS 7导航栏解决scheme的旧版本。

我用下面的代码解决了这个问题。 这是为了添加一个状态栏。 didFinishLaunchingWithOptions

 if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0) { UIView *addStatusBar = [[UIView alloc] init]; addStatusBar.frame = CGRectMake(0, 0, 320, 20); addStatusBar.backgroundColor = [UIColor colorWithRed:0.973 green:0.973 blue:0.973 alpha:1]; //change this to match your navigation bar [self.window.rootViewController.view addSubview:addStatusBar]; } 

而对于Interface Builder来说,这是为了当你用iOS 6打开时; 它从0像素开始。

注意:只有在详细信息窗格的“文件检查器”(最左边的图标)中取消选中“使用Autolayout”才能看到iOS 6/7 Deltas。

在这里输入图像说明

scheme:

通过重写该方法将其设置在您的视图控制器或rootviewcontroller:

 -(BOOL) prefersStatusBarHidden { return YES; } 

这里是广泛使用Storyboard的另一种方法:

目标:

这种方法的目标是在iOS7中重新创build与iOS6中相同的状态栏样式(请参阅问题标题“iOS 7状态栏回到iOS 6样式?”)。

概要:

为了达到这个目的,我们尽可能地使用Storyboard,向下移动状态栏重叠的UI元素,同时使用deltas恢复iOS 6.1或更早版本的向下布局变化。 然后iOS 7中产生的额外空间被一个UIView占用,背景颜色设置为我们select的颜色。 后者可以用代码或使用Storyboard创build(请参阅下面的选项)

假设:

为了在下面的步骤中获得所需的结果,假定View controller-based status bar appearance设置为NO,并且Status bar style设置为“透明黑色样式(0.5的alpha)”或“不透明黑色样式”。 这两个设置都可以在您的项目设置中的“信息”下find/或添加。

脚步:

  • 添加一个子视图到UIWindow作为您的状态栏背景。 为了达到这个目的,把下面的代码添加到你的AppDelegate的application: didFinishLaunchingWithOptions: makeKeyAndVisible

     if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_1) { UIView *statusBarBackgroundView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, yourAppsUIWindow.frame.size.width, 20)]; statusBarBackgroundView.backgroundColor = [UIColor blackColor]; [yourAppsUIWindow addSubview:statusBarBackgroundView]; } 
  • 由于您以编程方式为iOS 7添加了背景,因此您必须相应地调整状态栏重叠的UI元素的布局,同时保留iOS6的布局。 要做到这一点,请执行以下操作:

    • 确保您的故事板取消选中“ Use Autolayout (这是因为“尺寸检查器”中未显示“iOS 6/7 Deltas”)。 去做这个:
      • select你的Storyboard文件
      • 显示实用程序
      • select“显示文件检查器”
      • 在“界面生成器文档”下取消选中“使用Autolayout”
    • 或者,为了帮助您在应用iOS 7和6时监视布局更改,请select“助理编辑器”,select“预览”和“iOS 6.1或更低版本”: 在这里输入图像描述在这里输入图像描述
    • 现在select你想要调整的UI元素,这样它就不会被状态栏重叠了
    • 在“实用程序”列中select“显示大小检查器”
    • 沿Y轴重新定位UI元素的量与状态栏bg高度相同: 在这里输入图像描述
    • 并将Y的iOS6 / 7 Deltas值更改为与statusbar bg高度相同的负值(请注意,如果使用的是iOS 6预览中的更改): 在这里输入图像描述

备择scheme:

要在故事板大量的项目中添加更less的代码,并让状态栏背景自动旋转,而不是通过编程为状态栏添加背景,则可以将彩色视图添加到位于所述视图控制器主视图顶部的每个视图控制器。 然后,您可以将此新视图的高度增量更改为与视图高度相同的负值(以使其在iOS 6下消失)。

这个替代scheme的缺点(尽pipe考虑到自动旋转的兼容性可能忽略不计),事实上,如果你正在查看你的Storyboard for iOS 6,这个额外的视图是不能立即看到的。你只会知道它是在那里,如果你看看“文档大纲“的故事板。

如果您不希望视图控制器与状态栏(和导航栏)重叠,请取消选中Xcode 5中的界面生成器中的“扩展顶部条边下边缘”框。

取消选中顶部酒吧下的边缘

苹果发布技术问答QA1797:防止状态栏覆盖您的观点 。 它适用于iOS 6和iOS 7版本。

我已经看过许多许多许多教程来解决这个问题。 但是没有一个可行! 这是我的解决scheme,它适用于我:

 if( [[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0f ) { float statusBarHeight = [[UIApplication sharedApplication] statusBarFrame].size.height; for( UIView *v in [self.view subviews] ) { CGRect rect = v.frame; rect.origin.y += statusBarHeight; v.frame = rect; } } 

逻辑很简单。 我使用20个像素将self.view上的所有子视图移位。 就这样。 然后,截图就会像iOS 6一样显示。 我讨厌iOS7状态栏! 〜“〜

Archy Holt的答案是一个小的select,更简单一点:

一个。 组

 UIViewControllerBasedStatusBarAppearance to NO in info.plist 

湾 在AppDelegate's application:didFinishLaunchingWithOptions: ,call:

 if ([[UIDevice currentDevice].systemVersion floatValue] < 7) { self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds]; } else { // handling statusBar (iOS7) application.statusBarStyle = UIStatusBarStyleLightContent; self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].applicationFrame]; self.window.clipsToBounds = YES; // handling screen rotations for statusBar (iOS7) [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationDidChangeStatusBarOrientationNotification:) name:UIApplicationDidChangeStatusBarOrientationNotification object:nil]; } 

并添加方法:

 - (void)applicationDidChangeStatusBarOrientationNotification:(NSNotification *)notification { // handling statusBar (iOS7) self.window.frame = [UIScreen mainScreen].applicationFrame; } 

你也可以考虑UIWindow来处理UIApplicationDidChangeStatusBarOrientationNotification本身。

我在所有的视图控制器中使用了这个,很简单。 在所有viewDidLoad方法中添加以下行:

 - (void)viewDidLoad{ //add this 2 lines: if ([self respondsToSelector:@selector(edgesForExtendedLayout)]) self.edgesForExtendedLayout = UIRectEdgeNone; [super viewDidLoad]; } 

试试这个简单的方法….

步骤1 :在单个viewController更改

 [[UIApplication sharedApplication] setStatusBarStyle: UIStatusBarStyleBlackOpaque]; 

第二步 :改变整个应用程序

 info.plist ----> Status Bar Style --->UIStatusBarStyle to UIStatusBarStyleBlackOpaque 

第3步 :在每个viewWillAppear添加这个以调整iOS7 statusbar高度

  [[UIApplication sharedApplication]setStatusBarStyle:UIStatusBarStyleLightContent]; if ([[UIDevice currentDevice].systemVersion floatValue] >= 7) { CGRect frame = [UIScreen mainScreen].bounds; frame.origin.y+=20.0; frame.size.height-= 20.0; self.view.frame = frame; [self.view layoutIfNeeded]; } 

Interface Builder中有一个选项,它调用旨在解决偏移问题的iOS 6/7 Delta属性。

看看它堆栈溢出问题界面生成器:什么是UIView布局iOS 6/7三angular洲?

我已经在iOS 7中实现了iOS 6的状态栏。

在info.plist中将UIViewControllerBasedStatusBarAppearance设置为NO

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions放入下面的代码- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions方法

 if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7) { [application setStatusBarStyle:UIStatusBarStyleLightContent]; self.window.clipsToBounds =YES; self.window.frame = CGRectMake(0,20,self.window.frame.size.width,self.window.frame.size.height); //Added on 19th Sep 2013 NSLog(@"%f",self.window.frame.size.height); self.window.bounds = CGRectMake(0,0, self.window.frame.size.width, self.window.frame.size.height); } 

它可能会将所有视图压低20像素。在-(void)viewDidAppear:(BOOL)animated中使用以下代码-(void)viewDidAppear:(BOOL)animated方法

 if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7) { CGRect frame=self.view.frame; if (frame.size.height==[[NSUserDefaults standardUserDefaults] floatForKey:@"windowHeight"]) { frame.size.height-=20; } self.view.frame=frame; } 

您必须在didFinishLauncing方法中的窗口分配之后设置windowHeight Userdefaults值

 self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; [[NSUserDefaults standardUserDefaults] setFloat:self.window.frame.size.height forKey:@"windowHeight"]; 

如果您使用的是界面构build器,请尝试以下操作:

在你的xib文件中:

1)select主视图,将背景颜色设置为黑色(或任何你想要的状态栏的颜色

2)确保背景是一个独立的子视图,定位为控制器视图的顶层子视图。
移动你的背景成为控制器视图的直接子。 检查自动调整面板,确保已经locking了所有边框,激活了两个灵活轴,如果这是UIImageView,请将内容模式设置为“缩放”进行填充。 以编程方式,这将转换为contentMode设置为UIViewContentModeScaleToFill并将其自动resize掩码设置为(UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight)。

3)现在将所有locking的内容上移20点,并将iOS 6/7 delta Y设置为-20。
所有locking在自动化面板顶部框架的顶级儿童需要向下移动20pts,并将他们的iOS 6/7 delta Y设置为-20。 (Cmdselect所有这些,然后点击向下箭头20次 – 有没有更好的方法吗?)

4)调整具有灵活高度的上述所有项目的iOS 6/7三angular洲高度。 任何被locking到框架顶部和底部并且在自动调整面板中启用了灵活高度的项目也必须将其iOS 6/7 delta高度设置为20,其中包括上述背景视图。 这可能看起来是反直觉的,但由于这些应用的顺序,这是必要的。 首先设置框架高度(基于设备),然后应用变化量,最后根据所有子帧的偏移位置应用自动调整的遮罩 – 考虑一下,这是有道理的。

5)最后,locking在底框但不是顶框的物品根本不需要增量。

这会给你在iOS7和iOS6相同的状态栏。

另一方面,如果您在保持iOS6兼容性的情况下使用iOS7样式,请将背景视图的增量Y /增量高度值设置为0。

要查看更多iOS7迁移信息,请阅读完整的文章: http ://uncompiled.blogspot.com/2013/09/legacy-compatible-offsets-in-ios7.html

我的解决scheme是在iOS 7上在窗口顶部添加一个20点高度的UIView 。然后,在AppDelegate类中创build一个方法来显示/隐藏“实心”状态栏背景。 在application:didFinishLaunchingWithOptions: ::

 // ... // Add a status bar background self.statusBarBackground = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.window.bounds.size.width, 20.0f)]; self.statusBarBackground.backgroundColor = [UIColor blackColor]; self.statusBarBackground.alpha = 0.0; self.statusBarBackground.userInteractionEnabled = NO; self.statusBarBackground.layer.zPosition = 999; // Position its layer over all other views [self.window addSubview:self.statusBarBackground]; // ... return YES; 

然后我创build了一个淡入/淡出黑色状态栏背景的方法:

 - (void) showSolidStatusBar:(BOOL) solidStatusBar { [UIView animateWithDuration:0.3f animations:^{ if(solidStatusBar) { [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent]; self.statusBarBackground.alpha = 1.0f; } else { [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault]; self.statusBarBackground.alpha = 0.0f; } }]; } 

All I have to do now is call is [appDelegate showSolidStatusBar:YES] when needed.

This may be a overwhelming problem if you use Auto layout because you can not directly manipulate frames anymore. There is a simple solution without too much work.

I ended up writing an utility method in an Utility Class and called it from all the view controllers's viewDidLayoutSubviews Method.

 + (void)addStatusBarIfiOS7:(UIViewController *)vc { if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_1) { CGRect viewFrame = vc.view.frame; if(viewFrame.origin.y == 20) { //If the view's y origin is already 20 then don't move it down. return; } viewFrame.origin.y+=20.0; viewFrame.size.height-= 20.0; vc.view.frame = viewFrame; [vc.view layoutIfNeeded]; } } 

Override your viewDidLayoutSubviews method in the view controller, where you want status bar. It will get you through the burden of Autolayout.

 - (void)viewDidLayoutSubviews { [[UIApplication sharedApplication]setStatusBarStyle:UIStatusBarStyleLightContent]; [super viewDidLayoutSubviews]; [MyUtilityClass addStatusBarIfiOS7:self]; } 

The easiest way to do so is installing an older SDK to your newest Xcode.

How to install older SDK to the newest Xcode?

  1. U can get the iOS 6.1 SDK from http://www.4shared.com/zip/NlPgsxz6/iPhoneOS61sdk.html or downloading an older Xcode and geting the SDK from its contents

  2. Unzip and paste this folder to /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs

  3. Restart the xcode.

  4. U can now select an older SDK on your project's build settings

希望它可以帮助你。 It worked for me =)

As using presentViewController:animated:completion: messed-up the window.rootViewController.view , I had to find a different approach to this issue. I finally got it to work with modals and rotations by subclassing the UIView of my rootViewController.

.h

 @interface RootView : UIView @end 

.M

 @implementation RootView -(void)setFrame:(CGRect)frame { if (self.superview && self.superview != self.window) { frame = self.superview.bounds; frame.origin.y += 20.f; frame.size.height -= 20.f; } else { frame = [UIScreen mainScreen].applicationFrame; } [super setFrame:frame]; } - (void)layoutSubviews { self.frame = self.frame; [super layoutSubviews]; } @end 

You now have a strong workaround for iOS7 animations.

I am late for this Answer, but i just want to share what i did, which is basically the easiest solution

First of all-> Go to your info.plist File and add Status Bar Style->Transparent Black Style(Alpha of 0.5)

Now ,here it Goes:-

Add this code in your AppDelegate.m

 - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { //Whatever your code goes here if(kDeviceiPad){ //adding status bar for IOS7 ipad if (IS_IOS7) { UIView *addStatusBar = [[UIView alloc] init]; addStatusBar.frame = CGRectMake(0, 0, 1024, 20); addStatusBar.backgroundColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:1]; //change this to match your navigation bar [self.window.rootViewController.view addSubview:addStatusBar]; } } else{ //adding status bar for IOS7 iphone if (IS_IOS7) { UIView *addStatusBar = [[UIView alloc] init]; addStatusBar.frame = CGRectMake(0, 0, 320, 20); addStatusBar.backgroundColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:1]; //You can give your own color pattern [self.window.rootViewController.view addSubview:addStatusBar]; } return YES; } 

My very simple solution (assuming you have only vertical orientation supported) is to redefine application window bounds for iOS versions below 7, in App delegate didFinishLaunchingWithOptions method:

 CGRect screenBounds = [[UIScreen mainScreen] bounds]; if ([HMService getIOSVersion] < 7) { // handling statusBar (iOS6) by leaving top 20px for statusbar. screenBounds.origin.y = 20; self.window = [[UIWindow alloc] initWithFrame:screenBounds]; } else { self.window = [[UIWindow alloc] initWithFrame:screenBounds]; } 

You can hide the status bar all together. So your app will be full-screen. I think that's the best you will get.

UIStatusBarStyleNone or set in the target settings.

步骤隐藏iOS 7中的状态栏:

1.转到您的应用程序info.plist文件。

2.设置,查看基于控制器的状态栏外观:Boolean NO

希望我解决了状态栏问题…..

In order to continue working with setStatusBarHidden: I use this category:

 @interface UIApplication (StatusBar) -(void)setIOS7StatusBarHidden:(BOOL)statusBarHidden; @end @implementation UIApplication (StatusBar) -(void)setIOS7StatusBarHidden:(BOOL)statusBarHidden{ if (!IOS7) { [self setStatusBarHidden:statusBarHidden]; return; } if ([self isStatusBarHidden] == statusBarHidden) { return; } [self setStatusBarHidden:statusBarHidden]; [self keyWindow].clipsToBounds = YES; CGFloat offset = statusBarHidden ? 0 : 20; [self keyWindow].frame = CGRectMake(0,offset,[self keyWindow].frame.size.width,[self keyWindow].frame.size.height-offset); [self keyWindow].bounds = CGRectMake(0, offset, [self keyWindow].frame.size.width,[self keyWindow].frame.size.height); } @end 

I found here is the best alternatives and solution for this navigation bar issue in iOS7!!

http://www.appcoda.com/customize-navigation-status-bar-ios-7/

I hope it will clear our all queries and worries.

This might be too late to share, but I have something to contribute which might help someone, I was trying to sub-class the UINavigationBar and wanted to make it look like ios 6 with black status bar and status bar text in white.

Here is what I found working for that

  self.navigationController?.navigationBar.clipsToBounds = true self.navigationController?.navigationBar.translucent = false self.navigationController?.navigationBar.barStyle = .Black self.navigationController?.navigationBar.barTintColor = UIColor.whiteColor() 

It made my status bar background black, status bar text white and navigation bar's color white.

iOS 9.3, XCode 7.3.1