[CB-1182] Fixing IOS6 screen orientation/rotation without breaking ios5.1 or 
xcode 4.4 build.


Project: http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/repo
Commit: 
http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/commit/d8575d7e
Tree: http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/tree/d8575d7e
Diff: http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/diff/d8575d7e

Branch: refs/heads/master
Commit: d8575d7eece28ec2c90de4b448af729accaf2567
Parents: a0558e3
Author: Michal Mocny <mmo...@gmail.com>
Authored: Wed Aug 29 10:53:59 2012 -0400
Committer: Shazron Abdullah <shaz...@apache.org>
Committed: Wed Aug 29 18:26:01 2012 -0700

----------------------------------------------------------------------
 CordovaLib/Classes/CDVAvailability.h               |    6 +
 CordovaLib/Classes/CDVCapture.m                    |   12 +--
 CordovaLib/Classes/CDVLocation.m                   |    3 +-
 CordovaLib/Classes/CDVViewController.h             |    2 +-
 CordovaLib/Classes/CDVViewController.m             |  124 ++++++---------
 .../project/__TESTING__/Classes/AppDelegate.m      |   31 +++--
 6 files changed, 83 insertions(+), 95 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/CordovaLib/Classes/CDVAvailability.h
----------------------------------------------------------------------
diff --git a/CordovaLib/Classes/CDVAvailability.h 
b/CordovaLib/Classes/CDVAvailability.h
index e593bef..9410a88 100644
--- a/CordovaLib/Classes/CDVAvailability.h
+++ b/CordovaLib/Classes/CDVAvailability.h
@@ -61,3 +61,9 @@
                         (CORDOVA_VERSION_MIN_REQUIRED / 10000), \
                         (CORDOVA_VERSION_MIN_REQUIRED % 10000) / 100, \
                         (CORDOVA_VERSION_MIN_REQUIRED % 10000) % 100 ]
+
+#ifdef UI_USER_INTERFACE_IDIOM
+#define IsIPad() (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad)
+#else
+#define IsIPad() NO
+#endif

http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/CordovaLib/Classes/CDVCapture.m
----------------------------------------------------------------------
diff --git a/CordovaLib/Classes/CDVCapture.m b/CordovaLib/Classes/CDVCapture.m
index c33e90a..75792f6 100644
--- a/CordovaLib/Classes/CDVCapture.m
+++ b/CordovaLib/Classes/CDVCapture.m
@@ -19,6 +19,7 @@
 
 #import "CDVCapture.h"
 #import "JSONKit.h"
+#import "CDVAvailability.h"
 #import "CDVViewController.h"
 
 #define kW3CMediaFormatHeight @"height"
@@ -532,15 +533,6 @@
 @implementation CDVAudioRecorderViewController
 @synthesize errorCode, callbackId, duration, captureCommand, doneButton, 
recordingView, recordButton, recordImage, stopRecordImage, timerLabel, 
avRecorder, avSession, resultString, timer, isTimed;
 
-- (BOOL) isIPad 
-{
-#ifdef UI_USER_INTERFACE_IDIOM
-    return (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
-#else
-    return NO;
-#endif
-}
-
 - (NSString*) resolveImageResource:(NSString*)resource
 {
        NSString* systemVersion = [[UIDevice currentDevice] systemVersion];
@@ -551,7 +543,7 @@
        if (isLessThaniOS4)
        {
                NSString* iPadResource = [NSString 
stringWithFormat:@"%@~ipad.png", resource];
-        if ([self isIPad] && [UIImage imageNamed:iPadResource]) {
+        if (IsIPad() && [UIImage imageNamed:iPadResource]) {
             return iPadResource;
                } else {
                        return [NSString stringWithFormat:@"%@.png", resource];

http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/CordovaLib/Classes/CDVLocation.m
----------------------------------------------------------------------
diff --git a/CordovaLib/Classes/CDVLocation.m b/CordovaLib/Classes/CDVLocation.m
index 58e105b..6dcb2af 100755
--- a/CordovaLib/Classes/CDVLocation.m
+++ b/CordovaLib/Classes/CDVLocation.m
@@ -499,8 +499,7 @@
         if (currentOrientation != UIDeviceOrientationUnknown) {
             CDVViewController* cdvViewController = 
(CDVViewController*)self.viewController;
             
-            if ([cdvViewController.supportedOrientations containsObject:
-                 [NSNumber numberWithInt:currentOrientation]]) {
+            if ([cdvViewController supportsOrientation:currentOrientation]) {
                 
                 self.locationManager.headingOrientation = 
(CLDeviceOrientation)currentOrientation;
                 // FYI UIDeviceOrientation and CLDeviceOrientation enums are 
currently the same

http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/CordovaLib/Classes/CDVViewController.h
----------------------------------------------------------------------
diff --git a/CordovaLib/Classes/CDVViewController.h 
b/CordovaLib/Classes/CDVViewController.h
index 23d703b..4003551 100644
--- a/CordovaLib/Classes/CDVViewController.h
+++ b/CordovaLib/Classes/CDVViewController.h
@@ -35,7 +35,6 @@
 @property (nonatomic, readonly, strong) NSDictionary* pluginsMap;
 @property (nonatomic, readonly, strong) NSDictionary* settings;
 @property (nonatomic, readonly, strong) CDVWhitelist* whitelist; // readonly 
for public
-@property (nonatomic, readonly, strong) NSArray* supportedOrientations;
 @property (nonatomic, readonly, assign) BOOL loadFromString;
 @property (nonatomic, readwrite, copy) NSString* invokeString __attribute__ 
((deprecated));
 
@@ -62,5 +61,6 @@
 - (NSString*) appURLScheme;
 
 - (NSArray*) parseInterfaceOrientations:(NSArray*)orientations;
+- (BOOL) supportsOrientation:(UIInterfaceOrientation)orientation;
 
 @end

http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/CordovaLib/Classes/CDVViewController.m
----------------------------------------------------------------------
diff --git a/CordovaLib/Classes/CDVViewController.m 
b/CordovaLib/Classes/CDVViewController.m
index 8cdb109..ed75c2e 100644
--- a/CordovaLib/Classes/CDVViewController.m
+++ b/CordovaLib/Classes/CDVViewController.m
@@ -51,9 +51,8 @@
     if (self != nil && !self.initialized) 
     {
         [[UIDevice currentDevice] 
beginGeneratingDeviceOrientationNotifications];
-        [[NSNotificationCenter defaultCenter] addObserver:self 
selector:@selector(receivedOrientationChange) 
+        [[NSNotificationCenter defaultCenter] addObserver:self 
selector:@selector(receivedOrientationChange)
                                                      
name:UIDeviceOrientationDidChangeNotification object:nil];
-        
         [[NSNotificationCenter defaultCenter] addObserver:self 
selector:@selector(onAppWillTerminate:) 
                                                      
name:UIApplicationWillTerminateNotification object:nil];
         [[NSNotificationCenter defaultCenter] addObserver:self 
selector:@selector(onAppWillResignActive:) 
@@ -302,58 +301,67 @@
     return result;
 }
 
+- (NSInteger) 
mapIosOrientationToJsOrientation:(UIInterfaceOrientation)orientation
+{
+    switch (orientation) {
+        case UIInterfaceOrientationPortraitUpsideDown:
+            return 180;
+        case UIInterfaceOrientationLandscapeLeft:
+            return -90;
+        case UIInterfaceOrientationLandscapeRight:
+            return 90;
+        case UIInterfaceOrientationPortrait:
+            return 0;
+        default:
+            return 0;
+    }
+}
+
 - (BOOL) 
shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
 
 {
-       // First ask the webview via JS if it wants to support the new 
orientation -jm
-       int i = 0;
-       
-       switch (interfaceOrientation){
-            
-               case UIInterfaceOrientationPortraitUpsideDown:
-                       i = 180;
-                       break;
-               case UIInterfaceOrientationLandscapeLeft:
-                       i = -90;
-                       break;
-               case UIInterfaceOrientationLandscapeRight:
-                       i = 90;
-                       break;
-               default:
-               case UIInterfaceOrientationPortrait:
-                       // noop
-                       break;
-       }
-       
+       // First, ask the webview via JS if it supports the new orientation
        NSString* jsCall = [NSString stringWithFormat:
                         @"(function(){ \
                                 if('shouldRotateToOrientation' in window) { \
                                     return 
window.shouldRotateToOrientation(%d); \
                                 } \
                             })()"
-                        , i];
+                        , [self 
mapIosOrientationToJsOrientation:interfaceOrientation]];
        NSString* res = [webView stringByEvaluatingJavaScriptFromString:jsCall];
        
-       if([res length] > 0)
-       {
+       if([res length] > 0) {
                return [res boolValue];
        }
        
-       // if js did not handle the new orientation ( no return value ) we will 
look it up in the plist -jm
-       
-       BOOL autoRotate = [self.supportedOrientations count] > 0; // autorotate 
if only more than 1 orientation supported
-       if (autoRotate)
-       {
-               if ([self.supportedOrientations containsObject:
-                        [NSNumber numberWithInt:interfaceOrientation]]) {
-                       return YES;
-               }
-    }
-       
-       // default return value is NO! -jm
-       
-       return NO;
+       // if js did not handle the new orientation (no return value), use 
values from the plist (via supportedOrientations)
+       return [self supportsOrientation:interfaceOrientation];
+}
+
+- (BOOL)shouldAutorotate
+{
+    return YES;
 }
 
+- (NSUInteger)supportedInterfaceOrientations
+{
+    NSUInteger ret = 0;
+    
+    if ([self 
shouldAutorotateToInterfaceOrientation:UIInterfaceOrientationPortrait])
+        ret = ret | (1 << UIInterfaceOrientationPortrait);
+    if ([self 
shouldAutorotateToInterfaceOrientation:UIInterfaceOrientationPortraitUpsideDown])
+        ret = ret | (1 << UIInterfaceOrientationPortraitUpsideDown);
+    if ([self 
shouldAutorotateToInterfaceOrientation:UIInterfaceOrientationLandscapeRight])
+        ret = ret | (1 << UIInterfaceOrientationLandscapeRight);
+    if ([self 
shouldAutorotateToInterfaceOrientation:UIInterfaceOrientationLandscapeLeft])
+        ret = ret | (1 << UIInterfaceOrientationLandscapeLeft);
+    
+    return ret;
+}
+
+- (BOOL) supportsOrientation:(UIInterfaceOrientation)orientation
+{
+    return [self.supportedOrientations containsObject:[NSNumber 
numberWithInt:orientation]];
+}
 
 /**
  Called by UIKit when the device starts to rotate to a new orientation.  This 
fires the \c setOrientation
@@ -361,28 +369,11 @@
  */
 - (void)didRotateFromInterfaceOrientation: 
(UIInterfaceOrientation)fromInterfaceOrientation
 {
-       int i = 0;
-       
-       switch (self.interfaceOrientation){
-               case UIInterfaceOrientationPortrait:
-                       i = 0;
-                       break;
-               case UIInterfaceOrientationPortraitUpsideDown:
-                       i = 180;
-                       break;
-               case UIInterfaceOrientationLandscapeLeft:
-                       i = -90;
-                       break;
-               case UIInterfaceOrientationLandscapeRight:
-                       i = 90;
-                       break;
-       }
-    
     if (!IsAtLeastiOSVersion(@"5.0")) {
         NSString* jsCallback = [NSString stringWithFormat:
                                 
@"window.__defineGetter__('orientation',function(){ return %d; }); \
                                   
cordova.fireWindowEvent('orientationchange');"
-                                , i];
+                                , [self 
mapIosOrientationToJsOrientation:fromInterfaceOrientation]];
         [self.webView stringByEvaluatingJavaScriptFromString:jsCallback];    
     }
 }
@@ -471,7 +462,6 @@
         self.activityView.hidden = YES;    
         [self.view.superview bringSubviewToFront:self.webView];
     }
-    
     [self didRotateFromInterfaceOrientation:(UIInterfaceOrientation)[[UIDevice 
currentDevice] orientation]];
     
     // Tell the webview that native is ready.
@@ -585,15 +575,6 @@
     [webView stringByEvaluatingJavaScriptFromString:jsString];
 }
 
-+ (BOOL) isIPad 
-{
-#ifdef UI_USER_INTERFACE_IDIOM
-    return (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
-#else
-    return NO;
-#endif
-}
-
 + (NSString*) resolveImageResource:(NSString*)resource
 {
     NSString* systemVersion = [[UIDevice currentDevice] systemVersion];
@@ -602,7 +583,7 @@
     // the iPad image (nor retina) differentiation code was not in 3.x, and we 
have to explicitly set the path
     if (isLessThaniOS4)
     {
-        if ([[self class] isIPad]) {
+        if (IsIPad()) {
             return [NSString stringWithFormat:@"%@~ipad.png", resource];
         } else {
             return [NSString stringWithFormat:@"%@.png", resource];
@@ -649,13 +630,12 @@
     CGRect screenBounds = [[UIScreen mainScreen] bounds];
     CGRect statusBarFrame = [UIApplication sharedApplication].statusBarFrame;
     UIInterfaceOrientation statusBarOrientation = [UIApplication 
sharedApplication].statusBarOrientation;
-    BOOL isIPad = [[self class] isIPad];
     UIImage* launchImage = nil;
     
     // default to center of screen as in the original implementation. This 
will produce the 20px jump
     CGPoint center = CGPointMake((screenBounds.size.width / 2), 
(screenBounds.size.height / 2));
-    
-    if (isIPad)
+
+    if (IsIPad())
     {
         if 
(!UIDeviceOrientationIsValidInterfaceOrientation(deviceOrientation)) {
             deviceOrientation = (UIDeviceOrientation)statusBarOrientation;
@@ -701,7 +681,7 @@
     
     launchImage = [UIImage imageNamed:[[self class] 
resolveImageResource:orientedLaunchImageFile]];
     if (launchImage == nil) {
-        NSLog(@"WARNING: Splash-screen image '%@' was not found. Orientation: 
%d, iPad: %d", orientedLaunchImageFile, deviceOrientation, isIPad);
+        NSLog(@"WARNING: Splash-screen image '%@' was not found. Orientation: 
%d, iPad: %d", orientedLaunchImageFile, deviceOrientation, IsIPad());
     }
     
     self.imageView = [[UIImageView alloc] initWithImage:launchImage];

http://git-wip-us.apache.org/repos/asf/incubator-cordova-ios/blob/d8575d7e/bin/templates/project/__TESTING__/Classes/AppDelegate.m
----------------------------------------------------------------------
diff --git a/bin/templates/project/__TESTING__/Classes/AppDelegate.m 
b/bin/templates/project/__TESTING__/Classes/AppDelegate.m
index b6b14e8..c1b36fa 100644
--- a/bin/templates/project/__TESTING__/Classes/AppDelegate.m
+++ b/bin/templates/project/__TESTING__/Classes/AppDelegate.m
@@ -85,23 +85,27 @@
     }
     
     if (UIDeviceOrientationIsValidInterfaceOrientation(curDevOrientation)) {
-        for (NSNumber *orient in self.viewController.supportedOrientations) {
-            if ([orient intValue] == curDevOrientation) {
-                forceStartupRotation = NO;
-                break;
-            }
-        }
+        if ([self.viewController supportsOrientation:curDevOrientation]) {
+            forceStartupRotation = NO;
+        } 
     } 
     
     if (forceStartupRotation) {
-        NSLog(@"supportedOrientations: %@", 
self.viewController.supportedOrientations);
-        // The first item in the supportedOrientations array is the start 
orientation (guaranteed to be at least Portrait)
-        UIInterfaceOrientation newOrient = 
[[self.viewController.supportedOrientations objectAtIndex:0] intValue];
+        UIInterfaceOrientation newOrient;
+        if ([self.viewController 
supportsOrientation:UIInterfaceOrientationPortrait])
+            newOrient = UIInterfaceOrientationPortrait;
+        else if ([self.viewController 
supportsOrientation:UIInterfaceOrientationLandscapeLeft])
+            newOrient = UIInterfaceOrientationLandscapeLeft;
+        else if ([self.viewController 
supportsOrientation:UIInterfaceOrientationLandscapeRight])
+            newOrient = UIInterfaceOrientationLandscapeRight;
+        else
+            newOrient = UIInterfaceOrientationPortraitUpsideDown;
+
         NSLog(@"AppDelegate forcing status bar to: %d from: %d", newOrient, 
curDevOrientation);
         [[UIApplication sharedApplication] setStatusBarOrientation:newOrient];
     }
     
-    [self.window addSubview:self.viewController.view];
+    self.window.rootViewController = self.viewController;
     [self.window makeKeyAndVisible];
     
     return YES;
@@ -125,4 +129,11 @@
     return YES;    
 }
 
+- (NSUInteger) application:(UIApplication *)application 
supportedInterfaceOrientationsForWindow:(UIWindow *)window
+{    
+    // IPhone doesn't support upside down by default, while the IPad does.  
Override to allow all orientations always, and let the root view controller 
decide whats allowed (the supported orientations mask gets intersected).
+    NSUInteger supportedInterfaceOrientations = (1 << 
UIInterfaceOrientationPortrait) | (1 << UIInterfaceOrientationLandscapeLeft) | 
(1 << UIInterfaceOrientationLandscapeRight) | (1 << 
UIInterfaceOrientationPortraitUpsideDown);
+    return supportedInterfaceOrientations;
+}
+
 @end

Reply via email to