iOS 5では、次のようにプログラムでデバイスの向きを変更できました。
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationLandscapeRight];
しかし、iOS 6は非推奨ですが、iOS 6setOrientation
でデバイスの向きをプログラムで変更するにはどうすればよいですか?
iOS 5では、次のようにプログラムでデバイスの向きを変更できました。
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationLandscapeRight];
しかし、iOS 6は非推奨ですが、iOS 6setOrientation
でデバイスの向きをプログラムで変更するにはどうすればよいですか?
これが私の「5セント」で、ARCを使用してiOS7でテストされています
[[UIDevice currentDevice] setValue:
[NSNumber numberWithInteger: UIInterfaceOrientationPortrait]
forKey:@"orientation"];
これは、performSelector のように「リーク」警告を生成しません。
UIAlertView - このコードを使用すると、ビュー中に UIAlertView を開くと (will/Did) が表示されますUIAlertView を開く前に少し遅らせてから、ビューの向きを変更する時間があります。
2014 年 12 月 9 日からアプリの週をリリースしていることに注意してください。合格または不合格の場合は投稿を更新します。
これは、デバイスの向きを変更する方法には答えませんが、役立つ追加情報です。
iOS 6 UI インターフェイスの向き - shouldAutorotateToInterfaceOrientation :機能しない
メソッドshouldAutorotateToInterfaceOrientation : は iOS 6 ではサポートされていません。あなたがココアでの作業を始めたばかりの初心者で、iOS 6 ではビュー コントローラーがめちゃくちゃで、iOS 5 では完全である理由を疑問に思っている場合に備えて、 shouldAutorotateToInterfaceOrientation : はもうサポートされていないことを知っておいてください。Xcode 4 から 4.3 では問題なく動作する可能性がありますが、Xcode 4.5 では動作しません。
Apple は、これをよりクリーンな方法で行うための新しい方法を提供しています。代わりにsupportedInterfaceOrientationsを使用してください。ビューコントローラーがサポートするすべてのインターフェイスの向き、インターフェイスの向きの値のマスクを返します。
UIInterfaceOrientationMask 列挙型:
これらの定数は、View Controller がサポートするインターフェイスの向きを指定するためのマスク ビットです。
typedef enum {
UIInterfaceOrientationMaskPortrait = (1 << UIInterfaceOrientationPortrait),
UIInterfaceOrientationMaskLandscapeLeft = (1 << UIInterfaceOrientationLandscapeLeft),
UIInterfaceOrientationMaskLandscapeRight = (1 << UIInterfaceOrientationLandscapeRight),
UIInterfaceOrientationMaskPortraitUpsideDown = (1 << UIInterfaceOrientationPortraitUpsideDown),
UIInterfaceOrientationMaskLandscape =
(UIInterfaceOrientationMaskLandscapeLeft | UIInterfaceOrientationMaskLandscapeRight),
UIInterfaceOrientationMaskAll =
(UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskLandscapeLeft |
UIInterfaceOrientationMaskLandscapeRight | UIInterfaceOrientationMaskPortraitUpsideDown),
UIInterfaceOrientationMaskAllButUpsideDown =
(UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskLandscapeLeft |
UIInterfaceOrientationMaskLandscapeRight),
} UIInterfaceOrientationMask;
shouldAutorotateToInterfaceOrientation: メソッドの使用:
-(BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation {
return UIInterfaceOrientationIsLandscapeRight(toInterfaceOrientation);
}
supportedInterfaceOrientations メソッドの使用:
-(NSUInteger)supportedInterfaceOrientations{
return UIInterfaceOrientationMaskLandscapeRight;
}
これらは、iOS6 の方向に関する UIViewController に追加されたメソッドです。
iOS6 の Orientation に関するメソッドを UIApplication に追加
デバイスの向きを強制的に変更する最も簡単な方法はpresentViewController:animated:completion:
、新しいView Controllerが特定の優先方向を指定した新しいView Controllerを( を使用して)提示することであることがわかりました(メソッドを実装することにより-(UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
)。
新しいView Controllerが表示されると、予想どおり、新しいView Controllerが優先する向きに向きが変わります。したがって、最も単純な実装 (ベスト プラクティス?) は、特定の方向に必要なすべての機能を別のビュー コントローラーに埋め込み、必要に応じて表示することです。システムが向きを変更します。
明らかに、これはすべてのユースケースに適しているわけではありませんが、幸いなことに、同じトリックを適用して、デバイスに既存のビュー コントローラーの向きを強制的に変更させることができます。
秘訣は、必要な特定の優先方向で新しいビュー コントローラーを表示し、すぐに非表示にすることです。これにより、新しいView Controllerが表示されたときに向きが一時的に変更されます。最良の部分は、新しいView Controllerが閉じられると、元の(提示している)View Controller preferredInterfaceOrientationForPresentation
が再度照会されることです。ここで必要な最終的な向きを指定できます。
ここで注意すべき重要なことの 1 つは、元のビュー コントローラーで自動回転を一時的に無効にすることです (新しく表示されてから閉じられたビュー コントローラーから戻るとき)。さらに自動回転をトリガーしました。
次のコードは私のポイントを説明する必要があります。私の例では、回転を縦向きに強制します。他の向きが必要な場合は、それに応じて変更してください。
Original
という名前の元のView Controllerと、という名前の一時的なView Controllerがあると仮定しますForcePortrait
@interface Original : UIViewController
{
BOOL orientationToPortrait; //should set to NO by default
}
@end
@implementation Original
- (UIInterfaceOrientation) preferredInterfaceOrientationForPresentation
{
if(orientationToPortrait)
{
//when we manually changed, show in Portrait
return UIInterfaceOrientationPortrait;
}
else
{
//before manual orientation change, we allow any orientation
return self.interfaceOrientation;
}
}
-(BOOL) shouldAutorotate
{
//we should 'lock' the rotation once we manually change it
return !orientationToPortrait;
}
-(void) changeOrientationToPortrait
{
//Sample method to change the orientation
//when called, will show (and hide) the temporary view
//Original.preferredInterfaceOrientationForPresentation will be called again after this method
//flag this to ensure that we tell system we prefer Portrait, whenever it asked again
orientationToPortrait = YES;
//presenting the following VC will cause the orientation to temporary change
//when the new VC is dismissed, system will ask what is our (Original) orientation preference again
ForcePortrait* forcePortrait = [[ForcePortrait alloc] init];
[self presentViewController:forcePortrait animated:NO completion:^{
[forcePortrait dismissViewControllerAnimated:NO completion:nil];
}];
}
@end
@interface ForcePortrait : UIViewController
@end
@implementation ForcePortrait
- (NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskPortrait;
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIInterfaceOrientationPortrait;
}
@end
これを試して:
#import <objc/message.h>
if(UIDeviceOrientationIsLandscape(self.interfaceOrientation)){
if ([[UIDevice currentDevice] respondsToSelector:@selector(setOrientation:)])
{
objc_msgSend([UIDevice currentDevice], @selector(setOrientation:), UIInterfaceOrientationPortrait );
}
}
[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications];
AppDelegatedidFinishLaunchingWithOptions
メソッドに配置する必要があります。
次に、アプリケーションのどこでも、次の方法で現在の方向を取得できます。
UIDeviceOrientation orientation = [[UIDevice currentDevice] orientation];
そして、オリエンテーションをテストします。
UIInterfaceOrientationIsPortrait(orientation)
UIInterfaceOrientationIsLandscape(orientation)
など
if (UIDeviceOrientationIsLandscape([UIDevice currentDevice].orientation))
{
// code for landscape orientation
// OR
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationLandscapeRight];
// OR
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationLandscapeLeft];
}
else if (UIDeviceOrientationIsPortrait([UIDevice currentDevice].orientation))
{
// code for Portrait orientation
// OR
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationPortraitUpsideDown];
// OR
[[UIDevice currentDevice] setOrientation:UIInterfaceOrientationPortrait];
}
これは iOS7 で機能し、自動回転を強制的に縦向きにします。
//In your viewController.m
#import <objc/message.h>
// for autorotate viewController to portraid
- (void)viewWillAppear:(BOOL)animated {
UIInterfaceOrientation orientationStatusBar =[[UIApplication sharedApplication] statusBarOrientation];
switch (orientationStatusBar) {
case UIInterfaceOrientationPortrait:break;
case UIInterfaceOrientationLandscapeLeft:
objc_msgSend([UIDevice currentDevice], @selector(setOrientation:), UIInterfaceOrientationPortrait);
break;
case UIInterfaceOrientationLandscapeRight:
objc_msgSend([UIDevice currentDevice], @selector(setOrientation:), UIInterfaceOrientationPortrait);
break;
default:
break;
}
}
// this permit autorotate
- (BOOL) shouldAutorotate
{
// this lines permit rotate if viewController is not portrait
UIInterfaceOrientation orientationStatusBar =[[UIApplication sharedApplication] statusBarOrientation];
if (orientationStatusBar != UIInterfaceOrientationPortrait) {
return YES;
}
//this line not permit rotate is the viewController is portrait
return NO;
}
注: 私はこのオプションを自分のアプリに実装しましたが、おそらく Apple に拒否されるでしょう (2012 年 10 月に編集された Sergey K. の 6 に対する Austin のコメント)。
Apple は、 ios6でデバイスの向きをプログラムで変更することを非常に困難にしました (意図的に)。
私の知る限り、あなたが求めていることを達成する唯一の方法は、デバイスの向きの変化をシミュレートすることです。
を使用setTransform
して を回転させ、UIView
独自のフレームを再適用すると、目的の結果が得られます。
[YourView setTransform:CGAffineTransformMakeRotation(1.57)];
[YourView setFrame:CGRectMake(0, 0, YourView.frame.size.width, YourView.frame.size.height)];
また、デバイスの物理的な向きが変わると、変換を元に戻すことができます。
- (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration {
[YourView setTransform:CGAffineTransformMakeRotation(0)];
[YourView setFrame:CGRectMake(0, 0, YourView.frame.size.width, YourView.frame.size.height)];
}
@implementation UINavigationController (自動回転)
-(NSUInteger)supportedInterfaceOrientations
{
//make the check for iphone/ipad here
if(IPHONE)
{
return UIInterfaceOrientationMaskPortrait;
}
else
{
return UIInterfaceOrientationMaskLandscape;
}
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIInterfaceOrientationPortrait;
}
- (BOOL)shouldAutorotate
{
return NO;
}
これを試してください...うまくいきました...
UIWindow *window = [[UIApplication sharedApplication] keyWindow];
UIView *view = [window.subviews objectAtIndex:0];
[view removeFromSuperview]; [window addSubview:view];
if (self.interfaceOrientation != UIInterfaceOrientationLandscapeRight) {
// http://stackoverflow.com/questions/181780/is-there-a-documented-way-to-set-the-iphone-orientation
// http://openradar.appspot.com/radar?id=697
// [[UIDevice currentDevice] setOrientation: UIInterfaceOrientationLandscapeRight]; // Using the following code to get around apple's static analysis...
[[UIDevice currentDevice] performSelector:NSSelectorFromString(@"setOrientation:") withObject:(id)UIInterfaceOrientationLandscapeRight];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return NO;
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return interfaceOrientation == UIInterfaceOrientationPortrait
|| interfaceOrientation == UIInterfaceOrientationPortraitUpsideDown ;
}