首页 > 解决方案 > 在将视图控制器推到导航控制器上时旋转不会正确调整推视图控制器的大小

问题描述

我看到了一个非常奇怪的问题;就像用户旋转设备一样将视图控制器推入导航控制器会导致被推入的视图控制器不会自动布局到导航控制器。

这是一个按下按钮触发 pushViewController 的演示:

[1]

首先,您可以看到推送按预期工作(无旋转),然后在推送时搞砸(旋转),最后在弹出时搞砸(旋转)。

我特意做了一个我能想到的最简单的项目来测试它,所以故事板是一个视图控制器,在导航控制器中有一个按钮,整个代码是:

- (void)didTapButton:(id)sender
{
    UIViewController *viewController = [[UIViewController alloc] init];
    viewController.view.backgroundColor = [UIColor whiteColor];

    [self.navigationController pushViewController:viewController animated:YES];
}

我很难相信我在 iOS11 和 12 中遇到了一个迄今为止未被注意到的错误(在 10 中不会发生)但我真的很茫然,如果这是我的错的话,我真的很茫然。 .

任何人以前见过这个或有建议我在这里缺少什么?

标签: iosobjective-cautolayout

解决方案


我的猜测是,在过渡到不同尺寸时,这是一种与推动有关的竞争条件。当转换到新尺寸完成时,updateConstraints/needsLayout 标志可能为 NO(即,在推送完成但旋转尚未完成后,它已经认为它已经完全完成了它的视图布局)。我会认为这是一个 Apple Bug,如果您还没有报告,我会报告它。

作为一种解决方法,您可以使用 UINavigationController 的子类并实现,viewWillTransitionToSize:withTransitionCoordinator:然后如果需要抛出额外的[self.view setNeedsLayout][self.view setNeedsUpdateConstraints]在完成块中coordinator animateAlongsideTransition:completion:

- (void)viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id<UIViewControllerTransitionCoordinator>)coordinator {
    [coordinator animateAlongsideTransition:^(id<UIViewControllerTransitionCoordinatorContext>  _Nonnull context) {
    } completion:^(id<UIViewControllerTransitionCoordinatorContext>  _Nonnull context) {
        UIView *topView = [self.topViewController view];
        // we should only need an additional layout if the topView's size doesn't match the size
        // we're transitioning to (otherwise it should have already beend layed out properly)
        BOOL needsAdditionalLayout = topView && CGSizeEqualToSize(topView.frame.size, size) == NO;
        if (needsAdditionalLayout) {
            // either of these two should do the trick
            [self.view setNeedsUpdateConstraints];
            // [self.view setNeedsLayout];
        }
    }];
}

在完成大小转换后,这似乎正确调整了视图的大小。


推荐阅读