Navigation bar gets adjusted after calling completeTransition: in custom transition

The problem is that you are setting the transform before inserting the destination view controller's view into the container.

Switching the order should fix it:

if (self.reverse) {
    [container insertSubview:toViewController.view belowSubview:fromViewController.view];
} else {
    [container addSubview:toViewController.view];
    toViewController.view.transform = transform;
}

See point 4 here. Since you've applied a transform prior to inserting the navigation controller's view as a subview, the layout engine doesn't think the navigation bar is at the top edge of the window, and therefore doesn't need to be adjusted to avoid the status bar.


I've found a solution, although pretty hacky. I have to manually adjust the navigation bar frame before the animation starts:

if (self.reverse) {
    [container insertSubview:toViewController.view belowSubview:fromViewController.view];
} else {
    toViewController.view.transform = transform;
    [container addSubview:toViewController.view];

    // fix navigation bar position to prevent jump when completeTransition: is called
    if ([toViewController isKindOfClass:[UINavigationController class]]) {
        UINavigationController* navigationController = (UINavigationController*) toViewController;
        UINavigationBar* bar = navigationController.navigationBar;
        CGRect frame = bar.frame;
        bar.frame = CGRectMake(frame.origin.x, frame.origin.y + 20.0f, frame.size.width, frame.size.height);
    }
}