2014-09-24 35 views
8

我正在構建一種中間有分支的複雜應用程序。解除堆棧中較低的ViewController的行爲並不像預期的那樣

在應用程序的某個位置,顯示了一個特定的UIViewController,我們將其稱爲mainViewController(縮寫爲mainVC)。

mainVC提出了另一個視圖控制器,通過代碼,使用下面的代碼(I去掉隱私的原因它的一部分):

UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"SecondaryStoryboard" bundle:secondaryBundle]; 
SecondViewController *secondVC = [storyboard instantiateInitialViewController]; 
[self presentViewController:secondVC animated:YES completion:nil]; 

所以​​稍後將呈現另一視圖控制器,稱爲thirdVC。這是使用自定義SEGUE完成的,在代碼中使用上面的故事板,其代碼如下設置:

@implementation VCCustomPushSegue 

- (void)perform { 

    UIView *sourceView = ((UIViewController *)self.sourceViewController).view; 
    UIView *destinationView = ((UIViewController *)self.destinationViewController).view; 

    UIWindow *window = [[[UIApplication sharedApplication] delegate] window]; 
    destinationView.center = CGPointMake(sourceView.center.x + sourceView.frame.size.width, destinationView.center.y); 

    [window insertSubview:destinationView aboveSubview:sourceView]; 

    [UIView animateWithDuration:0.4 
        animations:^{ 
         destinationView.center = CGPointMake(sourceView.center.x, destinationView.center.y); 
         sourceView.center = CGPointMake(0 - sourceView.center.x, destinationView.center.y); 
        } 
        completion:^(BOOL finished){ 

         [self.sourceViewController presentViewController:self.destinationViewController animated:NO completion:nil]; 
        }]; 

} 

@end 

正如你可以看到這個賽格瑞呈現目的地視圖控制器模態(通過使用presentViewController:)用自定義動畫(從右到左滑動)。

所以基本上到這裏一切都很好。我用典型的模態動畫(從底部向上滑動)呈現​​,並用我的自定義過渡呈現thirdVC

但是,當我想解僱thirdVC時,我想要直接返回到mainVC。所以我所說的從thirdVC如下:

self.modalTransitionStyle = UIModalTransitionStyleCoverVertical; 
[self.presentingViewController.presentingViewController dismissViewControllerAnimated:_animate completion:nil]; 

這樣的話,我直接調用dismissViewControllerAnimated:mainVC(由self.presentingViewController.presentingViewController引用),和我期待的thirdVC與動畫中被解僱,而​​沒有動畫就消失。

隨着蘋果說,在UIViewController類文檔:

的呈現視圖控制器負責駁回視圖 控制器它呈現。如果您在所呈現的視圖 控制器本身上調用此方法,它會自動將消息轉發給呈現視圖控制器的 。

如果連續介紹幾個視圖控制器,從而構建一個 堆棧呈現視圖控制器,調用視圖 控制器這種方法在堆棧中較低駁回其直接子視圖 控制器及以上的所有視圖控制器那個孩子在堆棧。 當發生這種情況時,只有最頂級的觀點被取消動畫 時尚;任何中間視圖控制器都會從 堆棧中簡單地刪除。最頂端的視圖使用其模式轉換 樣式被忽略,這可能與堆棧中較低的其他視圖控制器 使用的樣式不同。

問題是,它不會發生什麼。在我的場景中,thirdVC消失,並且顯示​​被經典模態幻燈片解散爲底部動畫。

我在做什麼錯?


編輯:

所以@ codeFi的回答以經典的項目可能是工作,但這裏的問題是,我工作的一個框架。因此,mainVC將位於客戶端應用程序中,並且​​和thirdVC位於我的框架中,位於單獨的故事板中。我不能以任何其他方式訪問mainVC而不是在我的代碼中引用它,所以不幸的是,這裏展開的segues不是一個選項。

+1

這種行爲的改變發生在iOS 8中,7它確實工作正常。我正在嘗試解決它。 – theLastNightTrain 2014-10-21 16:23:13

+0

@theLastNightTrain:嗯,你是對的,它只發生在iOS 8上。讓我知道你是否發現任何東西.. – rdurand 2014-10-22 07:17:57

+0

@theLastNightTrain:有沒有更新?我很樂意提供一個解決這個問題的答案賞金.. – rdurand 2014-10-27 13:58:19

回答

2

我一直有這個完全相同的問題,並且我設法通過將屏幕的快照添加到secondVC.view的子視圖來設法在視覺上解決它,如下所示:

if (self.presentedViewController.presentedViewController) { 
    [self.presentedViewController.view addSubview:[[UIScreen mainScreen] snapshotViewAfterScreenUpdates:NO]]; 
} 

[self dismissViewControllerAnimated:YES completion:nil]; 

不漂亮,但它似乎工作。

注:如果你的​​有一個導航欄,你將需要隱藏的導航欄快照屏幕並添加快照作爲一個子視圖之間​​,否則快照就會出現在導航欄下方,從而看起來在解僱動畫期間顯示雙導航欄。代碼:

if (self.presentedViewController.presentedViewController) { 
    UIView *snapshot = [[UIScreen mainScreen] snapshotViewAfterScreenUpdates:NO]; 
    [self.presentedViewController.navigationController setNavigationBarHidden:YES animated:NO]; 
    [self.presentedViewController.view addSubview:snapshot]; 
} 

[self dismissViewControllerAnimated:YES completion:nil]; 
+0

謝謝,我會測試,讓你知道它是如何工作的。 – rdurand 2014-11-12 09:19:25

+1

似乎很好地工作..它會很好,直到他們修復它。謝謝 ! – rdurand 2014-11-12 10:46:45

+0

請注意,如果您的'secondVC'有一個導航欄,則需要在快照屏幕和將快照添加到'secondVC'的子視圖之間隱藏導航欄,否則快照將顯示在導航欄下方,從而看起來在解僱動畫期間顯示雙導航欄。 – rhelba 2014-11-12 14:36:35

1

我有同樣的問題,我已經通過使用UnwindSegues修復它。

基本上,你所要做的就是在ViewController中添加一個IBAction Unwind Segue方法,然後在IB中將Exit操作連接到你的Unwind Segue方法。

例子:

比方說,你有三個ViewControllers(VC1,VC2,VC3),你想去從VC3 VC1到。

步驟1 添加方法VC1類似如下:

- (IBAction)unwindToVC1:(UIStoryboardSegue*)sender 
{ 
} 

步驟2 轉到在界面生成器VC3和選擇它。然後按住CTRL拖動你的VC圖標到Exit圖標,並選擇你在VC1中添加的方法。

Add Unwind Segue

步驟3 同時還在IB,並與選定的VC3,選擇您放鬆身心Segue公司,並在屬性檢查器中添加一個Segue公司標識。

enter image description here enter image description here

步驟4 轉到VC3,你需要執行你的賽格瑞(或者解聘VC),並添加以下內容:

[self performSegueWithIdentifier:@"VC1Segue" sender:self]; 
+0

嘿!感謝您的回答。過去我已經使用過放鬆式賽段,但在這種情況下它們不是一種選擇。我沒有提到保持「簡單」的問題是第二個和第三個視圖控制器在一個框架內。所以基本上,主要的VC在客戶端的應用程序中,另外兩個在框架中分離(因此是另一個故事板)。對不起,這不是說我的問題:) – rdurand 2014-09-24 13:46:11