How to control a UIViewController's view frame

3.6k views Asked by At

I'm creating a view controller like this:

MyViewController* viewController = [[MyViewController alloc] initWithNibName:nil bundle:nil];
viewController.view.frame = CGRectMake(0,0,320,300);
[self addChildViewController:viewController];
[self.view addSubview:viewController.view];
[viewController didMoveToParentViewController:self];

Obviously I want the view to be sized to 0,0,320,300.

However, viewDidLoad gets called before the frame gets set, and thus in viewDidLoad I get this:

<UIView: 0x155d3180; frame = (0 0; 320 568); autoresize = W+H; layer = <CALayer: 0x155c20c0>>

So the views in the new view controller get laid out based on a height of 568 instead of the 300 that I want. What can I do to prevent this new view from being created with the wrong frame size?

4

There are 4 answers

0
rmaddy On BEST ANSWER

Your calling of viewController.view (followed by .frame) is what triggers the call to viewDidLoad.

The proper solution is to layout the subviews in the viewWillLayoutSubviews method of your view controller, not in viewDidLoad.

0
simalone On

I think you want to get a proper size in the new ViewController viewDidLoad. The view frame init just when you call viewController.view. when will call the new ViewController loadView where the view will init with frame(0 0; 320 568) and then viewDidLoad, so where you call view.frame = CGRectMake(0,0,320,300); is too later for your layout in viewDidLoad.

you can try this in the new ViewController loadView:

- (void)loadView{
    [super loadView];
    self.view.frame = CGRectMake(0,0,320,300);
}

If you want to set frame outside, you can add a initFrame property and a new init method for the new ViewController:

- (id)initWithMyFrame:(CGRect)myFrame{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        self.myInitFrame = initFrame;
    }
    return self;
}

- (void)loadView{
    [super loadView];
    self.view.frame = self.myInitFrame;
}
0
Hossam Ghareeb On

What about calling

self.view.frame = CGRectMake(0,0,320,300);

in the ViewDidLoad of MyViewController

0
HoanNguyen On

Fist of all, viewDidload call when load xib file. It still has default size. This is result a test for changing size(on iPad screen):

{{0, 0}, {768, 1004}} viewDidLoad
{{0, 0}, {768, 1004}} shouldAutorotateToInterfaceOrientation:
{{0, 0}, {768, 1004}} shouldAutorotateToInterfaceOrientation:
{{0, 0}, {768, 1004}} viewWillAppear:
{{0, 0}, {768, 1004}} shouldAutorotateToInterfaceOrientation:
{{0, 0}, {768, 1004}} shouldAutorotateToInterfaceOrientation:
{{0, 0}, {768, 1004}} willRotateToInterfaceOrientation:duration:
{{0, 0}, {1024, 748}} viewWillLayoutSubviews
{{0, 0}, {1024, 748}} layoutSubviews
{{0, 0}, {1024, 748}} viewDidLayoutSubviews
{{0, 0}, {1024, 748}} willAnimateRotationToInterfaceOrientation:duration:
{{0, 0}, {1024, 748}} shouldAutorotateToInterfaceOrientation:
{{0, 0}, {1024, 748}} viewDidAppear:

As you can see,view frame in viewDidLoad not exactly.

Second, I think your code work well. Maybe you should check other code in MyViewController