Search code examples
objective-cios8uipresentationcontroller

Animate the presenting controller view while animating presented controller view


I have a view controller that on certain action presents another view controller that covers bottom half of the screen.

When I animate the second view controller (presented view controller) from the bottom to cover the bottom half of the screen, I also want animate the presenting view to top half of the screen. See the code below -

- (void)animatePresentationWithTransitioningContext:(id<UIViewControllerContextTransitioning>) transitioningContext
{
    UIViewController *presentedController = [transitioningContext viewControllerForKey:UITransitionContextToViewControllerKey];
    UIView *presentedControllerView = [transitioningContext viewForKey:UITransitionContextToViewKey];
    UIView *containerView = [transitioningContext containerView];

    presentedControllerView.frame = [transitioningContext finalFrameForViewController:presentedController];

    CGPoint center = presentedControllerView.center;
    center.y = containerView.bounds.size.height;
    presentedControllerView.center = center;

    [containerView addSubview:presentedControllerView];

    // This returns nil
    UIView *presentingControllerView = [transitioningContext viewForKey:UITransitionContextFromViewKey];

    [UIView animateWithDuration:[self transitionDuration:transitioningContext] delay:0.0 usingSpringWithDamping:1.0 initialSpringVelocity:0.0 options:UIViewAnimationOptionAllowUserInteraction animations:^{
        CGPoint presentedViewCenter = presentedControllerView.center;
        presentedViewCenter.y -= containerView.bounds.size.height/2.0;
        presentedControllerView.center = presentedViewCenter;

        // This is where I want to move the presenting view controller.
        // of course it does not work.
        CGPoint presentingViewCenter = presentingControllerView.center;
        presentingViewCenter.y -= containerView.bounds.size.height/2.0;
        presentingControllerView.center = presentingViewCenter;

    } completion:^(BOOL finished) {
        [transitioningContext completeTransition:finished];
    }];
}

The viewForKey:UITransitionContextFromViewKey returns nil. I overrode shouldRemovePresentersView to return NO in my custom UIPresentationController but I still get nil. I am using UIModalPresentationCustom as the modal presentation style for the view that I am presenting.

EDIT:

I realized that I can achieve the same affect by animating the presenting view by overriding the presentationTransitionWillBegin method in my custom UIPresentationController. But I would like to get an answer on accessing the presenting view controller.

EDIT: Since I have found a solution, clarifying my question: (1) Is this the expected behavior i.e. the presentingViewController is going to be nil in the animator object?


Solution

  • I am using UIModalPresentationCustom as the modal presentation style for the view that I am presenting.

    Well, there's your problem. In that case, the From view will be nil. It is nil unless you are using the FullScreen presentation style.

    I'm not saying you are wrong to make the presentation style Custom. You need to do that, if you want to leave the presenting view controller's view in place, and if you want to supply your own presentation controller. And you do! But in that case, the work is divided: it is the presentation controller that becomes responsible for the final position of the view.

    By the way, it occurs to me (thinking about it some more) that you are doing something you should probably not be doing. You are not expected to move the presenting view controller's view. It might be safer to take a snapshot view of the presenting view controller's view and animate that, behind your presented view controller's view.