在模式演示中使用[UIViewControllerTransitionCoordinator animateAlongsideTransition:completion:]时,不调用动画块

Ell*_*eal 3 objective-c uiviewcontroller modalviewcontroller uiviewanimationtransition ios

我有一个UIViewController通过故事板中的模态segue(嵌入在a中UINavigationController)呈现的.我试图在模态演示文稿旁边设置键盘外观的动画(这个逻辑超出了问题的范围).

我使用的是[self.transitionCoordinator animateAlongsideTransition:completion:]viewWillAppear:这样做,但我注意到,该动画块永远不会被调用.因此,一些日志记录让我看到在新创建的模态视图控制器上唯一一次调用动画块的时间.viewDidLoad:

@implementation MyModalViewController

- (void)viewDidLoad {
    NSLog(@"%s", __PRETTY_FUNCTION__);
    [super viewDidLoad];

    [self.transitionCoordinator animateAlongsideTransition:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s ANIMATION", __PRETTY_FUNCTION__);
    } completion:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s COMPLETION", __PRETTY_FUNCTION__);
    }];
}

- (void)viewWillAppear:(BOOL)animated {
    NSLog(@"%s", __PRETTY_FUNCTION__);
    [super viewWillAppear:animated];

    [self.transitionCoordinator animateAlongsideTransition:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s ANIMATION", __PRETTY_FUNCTION__);
    } completion:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s COMPLETION", __PRETTY_FUNCTION__);
    }];
}

- (void)viewWillDisappear:(BOOL)animated {
    NSLog(@"%s", __PRETTY_FUNCTION__);
    [super viewWillDisappear:animated];

    [self.transitionCoordinator animateAlongsideTransition:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s ANIMATION", __PRETTY_FUNCTION__);
    } completion:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSLog(@"%s COMPLETION", __PRETTY_FUNCTION__);
    }];
}

@end
Run Code Online (Sandbox Code Playgroud)

该控制器的模态表示的输出是:

SampleAnimatedTransition[43690:1768171] -[MyModalViewController viewDidLoad]
SampleAnimatedTransition[43690:1768171] __36-[MyModalViewController viewDidLoad]_block_invoke ANIMATION
SampleAnimatedTransition[43690:1768171] -[MyModalViewController viewWillAppear:]
SampleAnimatedTransition[43690:1768171] __36-[MyModalViewController viewDidLoad]_block_invoke_2 COMPLETION
SampleAnimatedTransition[43690:1768171] __40-[MyModalViewController viewWillAppear:]_block_invoke_2 COMPLETION
Run Code Online (Sandbox Code Playgroud)

但在解雇期间,输出是:

SampleAnimatedTransition[43690:1768171] -[MyModalViewController viewWillDisappear:]
SampleAnimatedTransition[43690:1768171] __43-[MyModalViewController viewWillDisappear:]_block_invoke ANIMATION
SampleAnimatedTransition[43690:1768171] __43-[MyModalViewController viewWillDisappear:]_block_invoke_2 COMPLETION
Run Code Online (Sandbox Code Playgroud)

注意动画块是如何被调用的viewWillAppear:,甚至更令人讨厌的是动画块viewDidLoad:被调用之前viewWillAppear:被调用.

任何人都可以帮助我获得动画块viewWillAppear:吗?

请注意,当我推另一个视图控制器到导航控制器和在回击,动画块viewWillAppear: 调用.

如果它有帮助,我做了一个示例项目.

更新

这已被提交为rdar:// 20171073

Dar*_*ren 6

你提出了一个UINavigationController.您可以通过子类化UINavigationController和覆盖来使用该演示文稿进行动画处理-viewWillAppear:.但是,此时导航控制器尚未将其根视图控制器添加到视图层次结构中,因此您设置的任何动画都不起作用.

@implementation MyNavigationController
- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    [self.transitionCoordinator animateAlongsideTransition:^ (id <UIViewControllerTransitionCoordinatorContext> context) {
        NSAssert([self.viewControllers[0] superview] != nil, @""); // Fails
    } completion:nil];
}
@end
Run Code Online (Sandbox Code Playgroud)

事实证明,您可以使用以下命令强制UINavigationController设置其视图层次结构layoutIfNecessary:

@implemenation MyNavigationController
- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    [self.view layoutIfNeeded];
}
@end
Run Code Online (Sandbox Code Playgroud)

这也需要-viewWillAppear:在允许您使用模态演示文稿进行动画处理的位置调用根视图控制器.

有了这个黑客,我就能够在模态演示中进行动画制作.这很难看,我不会用它,但它至少可以让你测试你的键盘动画方法是否有任何优点.

根据您实际想要完成的任务,您可以更好地创建自定义模式演示文稿UIPresentationController.