UINavigationController的文档不包含带pushViewController
参数的completion:
方法。
答案 0 :(得分:61)
更好的解决方案是通过CATransaction包装推送动画并设置completionBlock。没有必要处理时间问题。
[CATransaction begin];
[CATransaction setCompletionBlock:^{
//whatever you want to do after the push
}];
[[self navigationController] pushViewController:viewController animated:YES];
[CATransaction commit];
答案 1 :(得分:12)
CATransaction.begin()
navigationController?.pushViewController(viewController, animated: true)
CATransaction.setCompletionBlock({
//your post animation logic
})
CATransaction.commit()
答案 2 :(得分:5)
使用CATransaction
的解决方案很棒,但还有另一种方法可以做到这一点。您可以将控制器设为UINavigationController
的委托,并实施didShowViewController
方法:
class FooBarController: UIViewController, UINavigationControllerDelegate {
func viewDidLoad() {
self.navigationController?.delegate = self
}
func navigationController(navigationController: UINavigationController, didShowViewController viewController: UIViewController, animated: Bool) {
// your awesome completion code here
}
}
这种方法可以更方便您的任务
答案 3 :(得分:2)
不确定我是否理解正确,但我按如下方式在完成块中推送了一个视图控制器。在表视图控制器中,将以下行添加到头文件中:
typedef void(^myCompletion)(BOOL);
然后在课堂上,添加了以下方法:
-(void) myMethod:(myCompletion) compblock
{
compblock(YES);
}
现在在didSelectRowAtIndexPath
中,我调用了myMethod
并在完成块中推送了一个视图控制器。
[self myMethod:^(BOOL finished) {
if(finished){
dispatch_async(dispatch_get_main_queue(), ^{
DVSecondTableViewController *vc = [[DVSecondTableViewController alloc] init];
[self.navigationController pushViewController:vc animated:YES];
});
}
}];
我不确定是否可以将视图控制器推送到主线程之外,因此我将该调用嵌入dispatch_async()
。
答案 4 :(得分:0)
尝试使用-[UIViewControllerTransitionCoordinator animateAlongsideTransitionInView:animation:completion:]
:
- (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated
{
if (!self.isPushing) {
self.pushing = YES;
[super pushViewController:viewController animated:animated];
if (!self.transitionCoordinator) {
self.pushing = NO;
} else {
[self.transitionCoordinator animateAlongsideTransition:nil completion:^(id<UIViewControllerTransitionCoordinatorContext> context) {
self.pushing = NO;
}];
}
}
}
答案 5 :(得分:-9)
我会选择@ justMartin的回答。但下面是另一种方法。
推动动画需要0.3秒。所以,如果你想在完成后在这里运行一些函数,请在0.3秒的延迟后使用performSelector。
[self performSelector:@selector(completedPushing:) withObject:nil afterDelay:.3];
或强>
将new viewController
推到navigation stack
后,old viewController view
将从视图层次结构中删除。这会导致在旧ViewController上调用viewDidDisappear
。您可以编写completion
那里有代码。不要忘记在viewDidDisappear的某个实现点调用super
。