2011-03-03 76 views
19

我正在研究通用应用程序,并且我试图在iPhone和iPad版本之间尽可能多地分享代码。我需要使用TabBarController作为我的根视图控制器,尽管我想在每个选项卡中使用SplitViewController,但SplitViewController的文档说它需要成为根视图控制器。因此,考虑到所有这些,理解我正试图并行放置两个导航控制器,并且(主要)复制SplitViewController的行为/布局。ViewController中的UINavigationController,位于视图顶部的间隙

一切正常,除了视图的布局。当应用程序以纵向模式启动时,当设备方向更改时,所有功能都会正常工作并调整大小/位置。

portrait orientation

如果该应用在除UIDeviceOrientationPortrait其他任何方向开始,则视图显示与导航控制器上方的20点间隙/余量。我试过在运行时调整帧,但没有完美的结果。将帧的原点调整为-20并将高度增加20,可以使视图与其父母的顶部齐平,但它会在底部留下20点的间隙!

landscape orientation

+0

为什么不调整帧中的每个旋转'self.view.frame.size.height'? – 2011-03-03 16:55:33

+0

@sudo - 是的,我已经做到了这一点,这有助于...但只有当设备旋转!如果应用程序以纵向(按钮向下)以外的任何方向启动,则它看起来像上一个屏幕截图。我试过的没有任何调整消除了差距。 – 2011-03-03 17:01:33

+0

他们尝试将其设置为[[UIScreen mainScreen]范围] .size.height'? – 2011-03-03 17:03:49

回答

3

UINavigationController的通常显示为全屏幕控制器,这意味着它的视图的顶部部分(当作为窗口的根视图控制器显示)的状态栏之下。然后,在状态栏可见时,手动将其导航栏和内容视图置于而不是的状态栏下方。不幸的是,它在被某个其他视图控制器定位时并不能真正处理事情,它(有时)会假定它需要保留20px的间隙而不检查其视图在状态栏下的是否为

解决的方法是将UINavigationController上的wantsFullScreenLayout设置为NO,因此它甚至不会尝试为状态栏留下空隙。

+1

谢谢,但这没有什么区别。 – 2011-03-03 17:30:15

+0

这是正确的解决方案。适用于我。 – 2013-04-06 03:15:09

3

我能够蛮横的力量如下。在viewDidLoadloadView

if (self.navigationController.navigationBar.frame.origin.y > 0.0) { 
    self.navigationController.navigationBar.frame = CGRectOffset(self.navigationController.navigationBar.frame, 0.0, -20.0); 
} 

而且在viewDidAppear:

if (self.view.superview.frame.origin.y > 44.0) { 
    UIView *container = self.view.superview; 
    container.frame = CGRectMake(container.frame.origin.x, container.frame.origin.y - 20.0, container.frame.size.width, container.frame.size.height + 20.0); 
} 

这是丑陋的,但它似乎工作。

-1

正确的答案是:

CGRect r = [[_navController view] frame]; 
r.origin = CGPointMake(0.0f, -20.0f); 
[[_navController view] setFrame:r]; 
2

不知道是否会有所帮助的,但我已经在过去也有类似的问题,已经能够解决这个设置的框架将其添加到其超级视图时,将UINavigationController视图添加到CGRectZero。

在layoutSubviews当然我更新了UINavigationController视图的框架。

+0

天才,工作! – 2011-11-18 19:05:32

2

将视图控制器添加到选项卡时,这是一个常见问题。

从苹果公司的文件(Tab Bar Controllers - Tab Bars and Full-Screen Layout):

标签栏控制器支持全屏幕布局不同于大多数其他控制器支持的方式。如果您希望其视图在状态栏或导航栏(如果存在)的下方,您仍然可以将自定义视图控制器的wantsFullScreenLayout属性设置为YES。但是,将此属性设置为YES不会导致视图与选项卡栏视图重叠。标签栏控制器总是调整您的视图的大小,以防止它在标签栏下面。

在代码的话,你应该做到以下几点:

UINavigationController *myNavController = [[UINavigationView alloc] init]; 
myNavController.wantsFullScreenLayout = YES; 

//... 

NSArray* controllers = [NSArray arrayWithObjects:myNavController, nil]; 
myTabBarController.viewControllers = controllers; 

如果然而,你遇到的问题是,在比UIInterfaceOrientationPortraitmyNavController的动作来看其他方向打开应用程序时20像素离开屏幕顶部,那么您将根据初始方向动态设置控制器的wantsFullScreenLayout属性(而不是上述解决方案)。 我用你的导航控制器实现定义一个静态变量它:

static UIInterfaceOrientation _initialOrientation = -1; 

之后,你需要重载viewDidAppear:方法,并适当设置变量:

- (void)viewDidAppear:(BOOL)animated 
{ 
    if (_initialOrientation == -1) 
    _initialOrientation = [[UIApplication sharedApplication] statusBarOrientation]; 
    self.wantsFullScreenLayout = (_initialOrientation != UIInterfaceOrientationPortrait); 

    [super viewDidAppear:animated]; 
} 

希望这有助于。

25

我在添加导航控制器视图后隐藏然后显示导航栏,在我的应用程序中解决了这个问题。例如。

[parentView addSubview:navController.view]; 
[navController setNavigationBarHidden:YES]; 
[navController setNavigationBarHidden:NO]; 
+4

这对我很有用,我强烈建议这个解决方案胜过其他-20像素的黑客。 – 2012-09-13 12:44:54

+1

应该被接受回答我猜。 – 2013-02-07 19:35:41

+1

真棒破解^ H^H^H ^解析:) – DrMickeyLauer 2013-06-19 13:05:23

0

曾与状态栏和视图之间不必要的差距类似的问题直接below它,通过在界面生成器将autosizing并设置有问题的观点坚持其父视图顶部解决它。

16

奇怪的是,是什么在iOS 6中帮助我的子类的UINavigationController和实施此方法:

- (BOOL)wantsFullScreenLayout { 
    return NO; 
} 

取消勾选“要全屏”在我的故事板没有做的伎俩,所以我不知道知道有什么不同。这在未来的iOS版本中肯定会崩溃。但现在,我会接受。

+1

是的,这真的很奇怪,当我在iOS 6中将导航控制器设置为关键窗口的rootViewController时,即使设置为NO,wantFullScreenLayout始终为YES。这篇文章解决了我的问题,谢谢!但是在iOS 5中,它被设置为NO后的值为NO。这可能是苹果的错误吗? – Chengjiong 2012-11-29 06:45:28

+0

它工作正常,谢谢@Brent。 :-) – 2013-01-23 13:13:05

+0

谢谢你!奇怪的故事板.. – velkopopovizky 2013-04-18 13:18:59

0

在我看来,那是我把这个代码viewDidAppear

内navigationcontroller内显示该代码可能不适合所有的应用,但它固定我的问题,我花了几个小时在踢..

// START OF BUG FIX FOR iOS 
if (self.navigationController.navigationBar.frame.origin.y ==20) { 
    // Move the navigation Bar up 
    [self.navigationController.navigationBar setFrame:CGRectMake(0, 0, self.navigationController.navigationBar.frame.size.width, self.navigationController.navigationBar.frame.size.height)]; 
    // move up the table view 
    [self.view setFrame:CGRectMake(0, -20, self.view.frame.size.width, self.view.frame.size.height+20)]; 
} 
// END OF BUG FIX for IOS6 
3

要解决这个问题,只需勾选故事板上的Wants Full Screen

问题出现,因为ParentViewController显示导航栏。

苹果文件说:

如果您的应用程序显示在状态栏,认为缩小,使其不欠重叠的状态栏。毕竟,如果状态栏不透明,则无法查看或与其下面的内容交互。但是,如果您的应用显示半透明状态栏,则可以将视图控制器的wantsFullScreenLayout属性的值设置为YES,以允许您的视图全屏显示。状态栏绘制在视图的顶部。

2

当我在viewDidLoad的ViewController中添加一个UITableView时遇到了同样的问题。而是抓住从self.view的框架,我把它形成的主窗口,使其看起来像这样

UIWindow *keyWindow = [[[UIApplication sharedApplication] delegate] window]; 
self.uiTable = [[UITableView alloc] initWithFrame:[keyWindow frame] style:UITableViewStylePlain]; 
相关问题