Last active
August 29, 2015 14:21
-
-
Save timriley/11f6716217b49c4b45a2 to your computer and use it in GitHub Desktop.
Workaround for dismissViewControllerAnimated failing to animate a stack of modal view controllers
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
- (void)loginViewControllerDidClose:(DSLoginViewController *)loginViewController | |
{ | |
// HACK | |
// | |
// Work around a bug(?) where the login VC's view disappears immediately | |
// (without animation) before our own view then animates away. We want | |
// only the login VC's view to animate, with all underlying views | |
// disappearing (invisibly) underneath at the same time. AFAICT, this is | |
// what _should_ happen: | |
// | |
// > If you present several view controllers in succession, thus building | |
// > a stack of presented view controllers, calling this method on a view | |
// > controller lower in the stack dismisses its immediate child view | |
// > controller and all view controllers above that child on the stack. | |
// > When this happens, only the top-most view is dismissed in an animated | |
// > fashion; any intermediate view controllers are simply removed from | |
// > the stack. | |
// | |
// However, this is not what actually happens. To make it look right, we | |
// basically fake out the same effect below, which only works here because | |
// we know exactly what kind of context we'll have when the login screen | |
// is dismissed. | |
// Get an image snapshot of the login VC (including its navigation bar) | |
UIGraphicsBeginImageContextWithOptions(self.presentedViewController.view.bounds.size, YES, 0); | |
[self.presentedViewController.view drawViewHierarchyInRect:self.presentedViewController.view.bounds afterScreenUpdates:YES]; | |
UIImage *image = UIGraphicsGetImageFromCurrentImageContext(); | |
UIGraphicsEndImageContext(); | |
// Add it to our own view | |
UIImageView *imageView = [[UIImageView alloc] initWithImage:image]; | |
[self.view addSubview:imageView]; | |
// And hide our navigation bar, since the snapshot includes the login VC's own navigation bar | |
[self.navigationController setNavigationBarHidden:YES animated:NO]; | |
// Then dismiss yourself | |
[self.presentingViewController dismissViewControllerAnimated:YES completion:nil]; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
There is a stack of 2 modally presented view controllers, on top of my main view controller:
When the login VC gets a tap on a “cancel” button, it sends a
loginViewControllerDidClose
message back to its delegate, which is the compose VC.At which point the compose VC was just calling
[self.presentingViewController dismissViewControllerAnimated:YES completion:nil];
This is meant to animate the stack of presented VCs away nicely, with the top-most VC’s view the one being animated away.However, what I get is the login VC’s view disappearing immediately, without any animation, followed by the compose VC's view animating away.
This switching around of views before the animation occurs is a horrible look. What I want to happen is the login VC's view animating away, with all other views being sorted out invisibly.