0

我有一个使用 Cocos2dx 引擎开发的 IOS 应用程序。

应用程序被锁定为特定方向(例如纵向) 应用程序中的所有内容似乎都可以正常工作并且根据正确的方向,除了最近的应用程序栏和根据设备方向的通知。

我希望能够限制它,使其具有与应用程序本身相同的方向。

我注意到删除文件中的横向info.plist可以完成这项工作,但我希望能够通过代码来完成。

在 IOS 6 中,我发现我所要做的就是覆盖referredInterfaceOrientationForPresentation我的RootViewController 并给出正确的方向,这可以解决问题,但这种方法不适用于 IOS 5 及更低版本。

我需要做什么才能在 IOS 5 及更低版本的设备上进行这项工作?

这是代码RootViewController(我没有写,我只是添加了最后一个方法,我正在尝试弄清楚如何解决通知和最近的应用程序问题)

#include "cocos2d.h"

#import "RootViewController.h"
#import "AppDelegate.h"

#import "misc/deviceOrientation.h"
#import "services/ios/ConfigurationServiceImpl.h"

@implementation RootViewController
@synthesize progressView;
/*
 // The designated initializer.  Override if you create the controller programmatically and want to perform customization that is not appropriate for viewDidLoad.
 - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
    if ((self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil])) {
    // Custom initialization
    }
    return self;
 }
 */

/*
 // Implement loadView to create a view hierarchy programmatically, without using a nib.
 - (void)loadView {
 }
 */

/*
 // Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
 - (void)viewDidLoad {
    [super viewDidLoad];
 }
 */

-(NSUInteger)supportedInterfaceOrientations{

    ConfigurationServiceImpl* configurationService = [ConfigurationServiceImpl instance];
    if ([configurationService isLandscape])
        return UIInterfaceOrientationMaskLandscape;
    else
        return UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskPortraitUpsideDown;
}

-(BOOL)shouldAutorotate{
    return YES;
}


// Override to allow orientations other than the default portrait orientation.
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {

//    printf("shouldAutorotateToInterfaceOrientation\n");

    //
    // There are 2 ways to support auto-rotation:
    //  - The OpenGL / cocos2d way
    //     - Faster, but doesn't rotate the UIKit objects
    //  - The ViewController way
    //    - A bit slower, but the UiKit objects are placed in the right place
    //

#if GAME_AUTOROTATION==kGameAutorotationNone
    //
    // EAGLView won't be autorotated.
    // Since this method should return YES in at least 1 orientation,
    // we return YES only in the Portrait orientation
    //
    return ( interfaceOrientation == UIInterfaceOrientationPortrait );
#elif GAME_AUTOROTATION==kGameAutorotationCCDirector
    //
    // EAGLView will be rotated by cocos2d
    //
    // Sample: Autorotate only in landscape mode
    //
    if( interfaceOrientation == UIInterfaceOrientationLandscapeLeft ) {
        [[CCDirector sharedDirector] setDeviceOrientation: kCCDeviceOrientationLandscapeRight];
    } else if( interfaceOrientation == UIInterfaceOrientationLandscapeRight) {
        [[CCDirector sharedDirector] setDeviceOrientation: kCCDeviceOrientationLandscapeLeft];
    }
}

    // Since this method should return YES in at least 1 orientation,
    // we return YES only in the Portrait orientation
    return ( interfaceOrientation == UIInterfaceOrientationPortrait );

#elif GAME_AUTOROTATION == kGameAutorotationUIViewController
    //
    // EAGLView will be rotated by the UIViewController
    //
    // Sample: Autorotate only in landscpe mode
    //
    // return YES for the supported orientations
    ConfigurationServiceImpl* configurationService = [ConfigurationServiceImpl instance];
    return [configurationService shouldAutorotateToInterfaceOrientation: interfaceOrientation];

#else
#error Unknown value in GAME_AUTOROTATION

#endif // GAME_AUTOROTATION


    // Shold not happen
    return NO;
}


 //This callback only will be called when GAME_AUTOROTATION == kGameAutorotationUIViewController

#if GAME_AUTOROTATION == kGameAutorotationUIViewController
-(void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration
{
    if (toInterfaceOrientation == UIInterfaceOrientationLandscapeLeft)
        CDeviceOrientation::setDeviceOrientation(CDeviceOrientation::left);
    else if (toInterfaceOrientation == UIInterfaceOrientationLandscapeRight)
        CDeviceOrientation::setDeviceOrientation(CDeviceOrientation::right);
    else if (toInterfaceOrientation == UIInterfaceOrientationPortrait)
        CDeviceOrientation::setDeviceOrientation(CDeviceOrientation::down);
    else if (toInterfaceOrientation == UIInterfaceOrientationPortraitUpsideDown)
        CDeviceOrientation::setDeviceOrientation(CDeviceOrientation::up);
}
#endif // GAME_AUTOROTATION == kGameAutorotationUIViewController


- (void)didReceiveMemoryWarning {
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];

    // Release any cached data, images, etc that aren't in use.
}

- (void)viewDidUnload {
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}

- (void)dealloc {
    [super dealloc];
}

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
    ConfigurationServiceImpl* configurationService = [ConfigurationServiceImpl instance];
    if ([configurationService isLandscape])
        return UIInterfaceOrientationLandscapeRight;
    else
        return UIInterfaceOrientationPortrait;
}


@end
4

2 回答 2

1

对 iOS 5 使用 shouldAutorotateToInterfaceOrientation,对 iOS 6 使用 shouldAutorotate。在 iOS5 方法中,使用 if case 作为您支持的方向,并为它们返回 YES。在您的应用摘要中,启用所有方向。希望这些对您有所帮助。

于 2013-07-08T13:00:46.793 回答
0

我制作这个代码框架来处理想要的和不需要的设备方向,在我的情况下,我想忽略 UIDeviceOrientationUnknown、UIDeviceOrientationFaceUp 和 UIDeviceOrientationFaceDown,缓存最后允许的方向。此代码处理 iPhone 和 iPad 设备,可能对您有用。

- (void)modXibFromRotation {

UIDeviceOrientation orientation = [[UIDevice currentDevice] orientation];
NSString *device = [[UIDevice currentDevice]localizedModel];
UIInterfaceOrientation cachedOrientation = [self interfaceOrientation];

if ([device isEqualToString:@"iPad"]) {

    if (orientation == UIDeviceOrientationUnknown || 
        orientation == UIDeviceOrientationFaceUp || 
        orientation == UIDeviceOrientationFaceDown) {

            orientation = (UIDeviceOrientation)cachedOrientation;
    }

    if (orientation == UIDeviceOrientationLandscapeLeft || orientation == UIDeviceOrientationLandscapeRight) {

        /* Your code */
    }

    if (orientation == UIDeviceOrientationPortrait || orientation == UIDeviceOrientationPortraitUpsideDown) {

        /* Your code */     
    }
}

if ([device isEqualToString:@"iPhone"] || [device isEqualToString:@"iPod"]) {

    if (orientation == UIDeviceOrientationUnknown || 
    orientation == UIDeviceOrientationFaceUp || 
    orientation == UIDeviceOrientationFaceDown) {

        orientation = (UIDeviceOrientation)cachedOrientation;
    }

    if (orientation == UIDeviceOrientationLandscapeLeft || orientation == UIDeviceOrientationLandscapeRight) {

         /* Your code */
    }

    if (orientation == UIDeviceOrientationPortrait || orientation == UIDeviceOrientationPortraitUpsideDown) {

        /* Your code */
    }
  }
}

你必须从视图控制器中的两个位置调用此方法:

Fist 开始在您的 App 委托中生成设备方向通知:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.

//**** ADD THIS CODE *****
[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications];

// Add the main view controller's view to the window and display.
self.window.rootViewController = self.mainViewController;
[self.window makeKeyAndVisible];

return YES;

}

然后在您的视图控制器中侦听设备方向通知:

- (void)viewDidLoad {   

     [notificationCent addObserver:self
                          selector:@selector(modXibFromRotation)
                              name:UIDeviceOrientationDidChangeNotification object:nil];
}

最后从以下位置调用 modXibFromRotation 方法:

- (void)viewWillAppear:(BOOL)animated {

    [super viewWillAppear];

    [self modXibFromRotation];
}

这将在视图显示之前调用检查方向方法。

于 2013-07-09T14:15:41.033 回答