2013-03-08 23 views
8

我有以下視圖控制器設置推:在iOS6的,麻煩迫使視圖控制器某些interfaceOrientation當棧

viewController1能夠自由旋轉到任何方位除了肖像倒掛。

viewController2被推到viewController1之上,我想它是相同的方向viewController1是,我希望它不能夠旋轉。

viewController3被推到viewController2之上。我希望viewController3處於縱向模式。

我有很多問題試圖在iOS6中完成這一點(還沒有在iOS5中嘗試過)。首先,我已經創建了自己的導航控制器,並把它下面:

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation 
{ 
    return [self.topViewController preferredInterfaceOrientationForPresentation]; 
} 

- (NSUInteger)supportedInterfaceOrientations 
{ 
    return [self.topViewController supportedInterfaceOrientations]; 
} 

- (BOOL) shouldAutorotate 
{ 
    return [self.topViewController shouldAutorotate]; 
} 

我已經嘗試了很多這些東西的不同組合就知道結果。主要是我在掙扎的地方是,如果vc2處於風景中,強制將vc3呈現爲肖像。任何幫助,將不勝感激。

回答

12

你在這裏試圖做的是打架。你所描述的並不是iOS 6中導航控制器體系結構的工作原理。如果你想顯示視圖控制器的視圖和強制旋轉,使用一個呈現的視圖控制器。這是唯一的時候preferredInterfaceOrientationForPresentation是有意義的,並且您的視圖控制器的supportedInterfaceOrientations將被實際諮詢,因爲被呈現,它將在界面的根部。

+1

那麼你的意思是我不得不推動它作爲模態觀來強制輪換?我無法將它推到導航堆棧上並強制它? – 2013-03-08 19:05:19

+2

是的,除了你所說的方式之外,你必須將它呈現爲過去被稱爲模態視圖控制器的形式,而不是將其推送到導航堆棧上。呈現的視圖控制器可以強制旋轉。推到導航堆棧上的視圖控制器不能;該應用程序可以動態決定如何在*用戶旋轉設備*時作出響應,但僅僅將視圖控制器推入導航堆棧的操作不會導致應用程序界面旋轉。 – matt 2013-03-08 19:10:18

+0

您是否碰巧知道是否有手動方式強制視圖控制器在提交後旋轉?不是讓用戶旋轉它,而是讓它自行旋轉? – 2013-03-08 19:14:11

5

我已經解釋了另一個不同的答案,它在iOS 6中不支持將新視圖控制器推到導航控制器上時的旋轉。您可以構造關於補償性的旋轉的規則(即,如果用戶旋轉設備會發生什麼情況),但是您不能旋轉接口。 iOS 6高興地讓你旋轉的唯一情況是在呈現或解散視圖控制器(presentViewController:animated:dismissViewControllerAnimated:)時。

但是,您可以像使用導航控制器那樣使用一個呈現的視圖控制器,使其類似看起來像。我做了一個電影展示了我的意思:

http://youtu.be/O76d6FhPXlE

現在,這是不以任何方式完全完美。狀態欄沒有旋轉動畫,並且在兩個視圖之間有一種黑色的「閃爍」 - 這是故意的,因爲它在那裏掩蓋了真正的。真正發生的是真實的兩個差異導航控制器和三個視圖控制器,如故事板的此屏幕截圖所示。

enter image description here

我們擁有的是:

  • 一個導航控制器子類設置爲縱向,其根視圖控制器

  • 第二導航控制器子類設置爲橫向,和它的根視圖控制器,它是黑色的,作爲媒介發揮作用

  • 第三視圖控制器被推到第二導航控制器的堆棧

當用戶請求去「向前」從第一視圖控制器,我們呈現第二導航控制器,從而在看到黑色視圖控制器暫時,但是我們立即第三個視圖控制器。所以我們得到了強制旋轉,以及一種黑色閃光和一個推動畫。當用戶點擊第三個視圖控制器中的「後退」按鈕時,我們會反轉該過程。

所有的過渡代碼都在黑色視圖控制器(ViewControllerIntermediary)中。我試圖調整它給予最滿意的動畫我可以:

@implementation ViewControllerIntermediary { 
    BOOL _comingBack; 
} 

- (void) viewDidLoad { 
    [super viewDidLoad]; 
    self.navigationController.delegate = self; 
} 

-(void)navigationController:(UINavigationController *)nc 
     willShowViewController:(UIViewController *)vc 
     animated:(BOOL)anim { 
    if (self == vc) 
     [nc setNavigationBarHidden:YES animated:_comingBack]; 
    else 
     [nc setNavigationBarHidden:NO animated:YES]; 
} 

-(void)viewDidAppear:(BOOL)animated { 
    [super viewDidAppear:animated]; 
    if (!_comingBack) { 
     [self performSegueWithIdentifier:@"pushme" sender:self]; 
     _comingBack = YES; 
    } 
    else 
     [self.navigationController dismissViewControllerAnimated:YES 
      completion:nil]; 
} 
1
- (NSUInteger)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window 
{ 
if ([self.window.rootViewController.presentedViewController isKindOfClass: [SecondViewController class]]) 
{ 
    SecondViewController *secondController = (SecondViewController *) self.window.rootViewController.presentedViewController; 

    if (secondController.isPresented) 
     return UIInterfaceOrientationMaskAll; 
    else return UIInterfaceOrientationMaskPortrait; 
} 
else return UIInterfaceOrientationMaskPortrait; 
} 

而對於斯威夫特

func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow) -> Int { 

    if self.window?.rootViewController?.presentedViewController? is SecondViewController { 

     let secondController = self.window!.rootViewController.presentedViewController as SecondViewController 

     if secondController.isPresented { 
      return Int(UIInterfaceOrientationMask.All.toRaw()); 
     } else { 
      return Int(UIInterfaceOrientationMask.Portrait.toRaw()); 
     } 
    } else { 
     return Int(UIInterfaceOrientationMask.Portrait.toRaw()); 
    } 

} 

有關詳情,請這個link

相關問題