开发者

Wrong positioning after orientation change on iPad

开发者 https://www.devze.com 2023-02-04 01:11 出处:网络
Having some problems when changing the orientation of my iPadd app. I wrote a function that lays out my subviews so I can call it when the view appears or is rotated.

Having some problems when changing the orientation of my iPadd app.

I wrote a function that lays out my subviews so I can call it when the view appears or is rotated.

The function works perfectly when it is called by the "viewWillAppear" function. But when the "willAnimateRotationToInterfaceOrientation" function calls my layout function ("setPositionsForOrientation") I'm facing following issues:

  • When changing from portrait to landscape I have a 128px offset on the left side
  • When changing from landscape to portrait I have a negative offset on the left side

I have the impression, that somehow the new frame-properties are not handled correctly, as my UIScrollViews should also resize, but they don't do it.

That's the code I wrote:

- (void)viewWillAppear:(BOOL)animated{
 [self setPositionsForOrientation:self.interfaceOrientation];
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
 return YES;
}

- (void)willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)newInterfaceOrientation duration:(NSTimeInterval)duration {
 [self setPositionsForOrientation:newInterfaceOrientation];
}

- (void)setPositionsForOrientation:(UIInterfaceOrientation)interfaceOrientation {
 // Position the UI elements for landscape mode
 if (interfaceOrientation == UIInterfaceOrientationLandscapeLeft || interfaceOrientation == UIInterfaceOrientationLandscapeRight) {
  self.view.frame = CGRectMake(0, 0, 1024, 748);
  self.menubarImage.frame = CGRectMake(0, 0, 1024, 121);
  self.backgroundImage.frame = CGRectMake(0, 0, 1024, 748);
  self.mainCategories.frame = CGRectMake(6, 6, 1012, 55);
  self.subCategories.frame = CGRectMake(58, 79, 960, 30);
  self.moviesContainer.frame = CGRectMake(6, 204, 1012, 456);
  self.searchButton.frame = CGRectMake(935, 709, 80, 30);
 }
 // Position the UI elements for portrait mode
 else {
  self.view.frame = CGRectMake(0, 0, 768, 1004);
  self.menubarImage.frame = CGRectMake(0, 256, 768, 121);
  self.toolbarImage.frame = CGRectMake(0, 924, 768, 80);
  self.backgroundImage.frame = CGRectMake(0, 256, 768, 748);
  self.mainCategories.frame = CGRectMake(6, 262, 756, 55);
  self.subCategories.frame = CGRectMake(58, 335, 704, 30);
  self.moviesContainer.frame = CGRectMake(6, 460, 756, 456);
  self.searchButton.frame = CGRectMake(680, 963, 80, 30);
 }
}

And here are some pictures to illustrate my problem..

Layout in IB (All subviews have contentMode set to Top-Left)

http://www.abload.de/image.php?img=interfacebuilderl9ey.png 

Portrait mode shown correctly / strange

http://www.abload.de/i开发者_开发技巧mage.php?img=portrait_oklxf1.png
http://www.abload.de/image.php?img=portrait_failma8y.png

Landscape mode shown correctly / strange

http://www.abload.de/image.php?img=landscape_ok4z2l.png
http://www.abload.de/image.php?img=landscape_failvzuy.png

What have I done wrong and more important, how can I fix it?

I found this post which describes the usual way, but I don't get how I can override my views "layoutSubviews" method, as the view is just a property of my UIViewController..


If you want to create you own subclass of UIView and set it to UIViewController so you can implement layoutSubviews method, is very easy actually!.

UIViewController does not creates a view it expects the user to set the view but when using Interface BUilder there is a UIView already set for us.

To change the view do:

  • Create your subclass, here I will assume it is called MyView, and put there all your UI stuff (toolbars, buttons, etc).
  • Open your view controller file in IB (the *.xib)
  • Select the view (the view that we are changing)
  • Go to the Identity Inspector (or press Cmd+4)
  • Enter "MyView" in the class identity field

Since you put all your UI elements in the view as ivar you cannot access them from your UIViewController anymore right? So, make sure you have the correct accessors/properties and methods to handle your view (and its ivars) from UIViewController. ;)

Wrong positioning after orientation change on iPad

Good Luck ;)

EDIT:2011/01/17

When you are in your controller and do [self.view xyz] you get the warning right? That is because a UIViewController's view is declared to be an UIView object. And you subclassed UIView and set it in IB. So everytime you access the view you have to cast it or the compiler will think it is still the normal UIView which does not have the methods you have declared in MyView. Do like this:

[(MyView *)self.view xyz]; //and for that don't forget to #import "MyView.h"

This should work. But I don't understand why then got: "property 'view' type does not match super class 'UIViewController' property type" First try what I just said ;) Are you sure you Declared MyView as:

@interface MyView: UIView{
...
}
@property (...) XYZ *xyz;
...
@end


I added following code in the MyView class in the .m file and it helped me out of my misery:

- (void)awakeFromNib
{
    self.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
}
0

精彩评论

暂无评论...
验证码 换一张
取 消