最近开发IOS遇到一个问题,
为了支持UI布局横屏竖屏,监听了
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(notifyOrientation:) name:UIDeviceOrientationDidChangeNotification object:nil];
收到消息后
-(void)notifyOrientation:(NSNotification *)notify
中在做处理。
但是处理后发现有的时候横竖屏还是处理不对,发现
[[UIDevice currentDevice] orientation]
取得UIDeviceOrientation一共有7个值除了横竖还有
UIDeviceOrientationUnknown、UIDeviceOrientationFaceUp、UIDeviceOrientationFaceDown,
后两个是平放朝上和朝下,这样就会有问题,在处理时会出错,所以想到用
[[UIApplication sharedApplication] statusBarOrientation]
取得UIInterfaceOrientation用UI的反转代替Device的反转,看下定义
typedef NS_ENUM(NSInteger, UIInterfaceOrientation) {
UIInterfaceOrientationUnknown = UIDeviceOrientationUnknown,
UIInterfaceOrientationPortrait = UIDeviceOrientationPortrait,
UIInterfaceOrientationPortraitUpsideDown = UIDeviceOrientationPortraitUpsideDown,
UIInterfaceOrientationLandscapeLeft = UIDeviceOrientationLandscapeRight,
UIInterfaceOrientationLandscapeRight = UIDeviceOrientationLandscapeLeft
};
UIInterfaceOrientation只有横竖,而且横屏时左右和Device是颠倒的。用它就不需要考虑平放的情况了。
最后总结,需要注意UIDeviceOrientation只是设备状态,至于应用中是什么情况还是要以UIInterfaceOrientation为准。
需要注意的在IOS7 和 更早的版本中UIWindow的transform并不随UIInterfaceOrientation方向的变化而变化,而且[UIScreen mainScreen]的bounds和applicationFrame也不随UIInterfaceOrientation方向变化而变化,bounds包含status bar高度20,applicationFrame则不包含,如果隐藏status bar则二者一致。
而在IOS8中UIWindow会随UIInterfaceOrientation的变化而变,所以之前写的一个应用中在UIWindow上添加UIView就会出现问题,
UIWindow* window = [[[UIApplication sharedApplication] delegate] window];
[window addSubview:self.view];
解决上述问题,几种解决方法,
1. 如果一定要在UIWindow中添加UIView的话,在IOS7或以前的IOS版本中需要自己处理旋转问题,
UIInterfaceOrientation orientation = [[UIApplication sharedApplication]statusBarOrientation];
if (orientation == UIInterfaceOrientationLandscapeLeft) {
CGAffineTransform rotation = CGAffineTransformMakeRotation(3*M_PI/2);
[view setTransform:rotation];
}
if (orientation == UIInterfaceOrientationLandscapeRight) {
CGAffineTransform rotation = CGAffineTransformMakeRotation(M_PI/2);
[view setTransform:rotation];
}
if (orientation == UIInterfaceOrientationPortraitUpsideDown ) {
CGAffineTransform rotation = CGAffineTransformMakeRotation(M_PI);
[view setTransform:rotation];
}
2. 为view创建UIViewController,使用UIViewController处理旋转问题,在UIViewController中添加
– (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
return YES;
}
并且UIViewController的view需要添加到UIWindow中
[window addSubview:self.view];
还需要保证UIViewController为UIWindow的主UIViewController,及第一个加入UIWindow中,
因为UIViewController继承自UIResponder,同一级别中只有第一个UIViewController能接受到上述消息。
3. 如果你的view不是第一个UIViewController,还可以直接把view加到UIWindow的第一个主view中,
UIWindow *window = [[UIApplication sharedApplication] keyWindow];
[[window.subviews objectAtIndex:0] addSubview:self.view];
一般建议用第三种做法。
如果想单独控制一个view的Orientation可以实现UIViewController的
-(NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskAll; // 表示支持全部方向
}
-(BOOL)shouldAutorotate
{
return YES;
}
- 本文固定链接: http://www.wy182000.com/2015/04/02/ios-orientation-详解/
- 转载请注明: wy182000 于 Studio 发表