查看身高问题(续)

时间:2013-07-26 13:10:14

标签: ios objective-c cocoa-touch

这是我在这里遇到的问题(仍未解决)的延续:link

但这可能有助于了解问题所在。 我只创建了一个简单的测试项目('Empty Application')并添加了一个带有XIB文件的视图控制器(复选框:'选择了用户界面的XIB文件')。代码如下所示:

- (void)viewDidLoad
{
    [super viewDidLoad];
    NSLog(@"didLoad: %@",NSStringFromCGRect(self.view.bounds));

    // Do any additional setup after loading the view from its nib.
}

-(void) viewDidAppear:(BOOL)animated
{
    NSLog(@"didAppear: %@",NSStringFromCGRect(self.view.bounds));

}

这是输出:

2013-07-26 17:05:28.502 testtest[5926:c07] didLoad: {{0, 0}, {320, 548}}
2013-07-26 17:05:28.506 testtest[5926:c07] didAppear: {{0, 0}, {320, 460}}

他们为何如此不同?

(ps。我在6.1模拟器上测试)

5 个答案:

答案 0 :(得分:3)

当调用viewDidLoad方法时,您的视图控制器刚从故事板或XIB加载,因此视图尺寸等于XIB中的视图尺寸(看起来像iPhone 5高度)尺寸)。

稍后,当调用viewDidAppear:时,视图已经出现在屏幕上,因此它已经适当调整大小以实际适合屏幕,因此其尺寸可能与故事板中的尺寸不同,因此与加载视图时设置的不同。

在您的情况下,看起来您的故事板或XIB文件设置为iPhone 5屏幕大小(548 = 1136/2 - 状态栏),并且您正在使用480x320点的iPhone 5之前的模拟器或设备进行测试屏幕,因此视图可以调整大小到460点高,以适应屏幕。

答案 1 :(得分:1)

这可能有完美的感觉。

首次访问ViewDidLoad时,

controller.view会被懒惰地调用,所以此时框架尚未设置。这意味着此时您不能依赖于帧/边界大小,因为它只包含一个默认值(尽管在许多情况下它是正确的)。 在ViewDidAppear中,帧通常是设置的,但是如果你的父控制器正在设置任何动画,你也可以有一个时间帧状态而不是最后一个,但是按照惯例,这种方法通常不会被调用。视图已经显示。

例如,如果您从IB文件加载视图,那么您将在viewDidLoad中获得的框架是您在IB文件中获得的框架,但您的视图的最终尺寸可能更小/更大,然后你会在viewDidAppear中获得另一个。

而不是那样,你应该创建所有可调整大小的元素(使用Spring& Struts,AutoLayout或任何其他类似的替代方案),以便在设置框架时正确显示它们。

答案 2 :(得分:0)

  

ViewController显示其视图时,通常会缩小该视图   查看,使其框架不与设备的状态栏重叠。

因此,当您NSLog viewDidLoad时,视图i尚未加载,因此ViewController尚未缩小框架,但在viewDidAppear中,它已完成大小调整。 UIViewController中有一处房产 wantsFullScreenLayout

  

将此属性设置为YES会导致视图控制器调整其大小   查看,以便它填满整个屏幕,包括下面的区域   状态栏。 (当然,为了实现这一点,托管的窗口   视图控制器本身的大小必须足以填满整个屏幕,   包括状态栏下方的区域。)您通常会设置   如果您有半透明状态栏,则此属性为YES   并希望您的视图内容在该视图后面可见。

答案 3 :(得分:0)

据我所知,ViewDidLoad将根据定义设置应用程序的边界,在根视图的RootViewController / XIB文件中,或者可能是AppDelegate。

如果您在那里定义应用程序边界(不确定其中哪一个),整个应用程序中的ViewDidLoad函数最初将根据该值设置高度。

加载视图并准备“出现”后,可能会请求实际边界。 因此,建议在ViewWillAppear / ViewDidAppear方法中请求边界/大小。

答案 4 :(得分:0)

-viewDidLoad在第一次调用viewController.view时调用。在返回视图之前调用它。这具有非常重要的意义。为了显示或调整视图,需要将其添加到窗口或其他视图中。

这是怎么发生的?它看起来像[window addSubview:viewController.view]

因此,在将视图放入视图层次结构之前,需要满载视图。在self.view中使用时,这会对-viewDidLoad造成限制。

  1. self.view.superviewself.view.window始终为nil
  2. self.view尚未调整为适合self.view.superview
  3. 根据这种理解,您可以看到self.view在调用-viewDidLoad时无法知道它的最终大小。


    <强>更新

    如果您需要将自定义布局应用于视图的子视图,您可能需要考虑将UIView子类化并使用-[UIView layoutSubviews]

    除非您在使用-viewWillAppear:而不是-viewDidAppear:时遇到问题?在显示视图之前调用-viewWillAppear:,因此在调整视图大小时不会产生奇怪的视觉效果。