UIPresentationController是iOS8以后出来的类,可以自定义模态视图跳转动画。
我现在Storyboard创建个视图控制器ShowInfoViewController,这就是我要跳转到的视图控制器。想要自定义跳转动画,先要设置视图控制器实例的modalPresentationStyle为UIModalPresentationCustom。然后实现设置该实例的UIViewControllerTransitioningDelegate。说到UIViewControllerTransitioningDelegate,我们需要自己实现三个类才能达成目的。
- (IBAction)doPresentShowInfoVC:(id)sender {
ShowInfoViewController *showInfoVC = [[UIStoryboard storyboardWithName:@"Main" bundle:nil] instantiateViewControllerWithIdentifier:@"ShowInfoViewControllerSBID"];
// 必须设置为UIModalPresentationCustom才能自定义
showInfoVC.modalPresentationStyle = UIModalPresentationCustom;
// 实现代理
//ShowInfoTransitioning *showInfoTransitioning = [[ShowInfoTransitioning alloc] init];
showInfoVC.transitioningDelegate = [ShowInfoTransitioning sharedInstance];
[self presentViewController:showInfoVC animated:YES completion:nil];
//[self performSegueWithIdentifier:@"gotoShowInfoViewController" sender:self];
}
[self performSegueWithIdentifier:@"gotoShowInfoViewController" sender:self];
是在Storyboard连线,然后实现的跳转,用此代码跳转没达到自定义动画效果,有兴趣可以试试。
最主要的就是我们自己要实现三个类了,哪三个类?
1、实现了UIViewControllerTransitioningDelegate代理的类
2、继承UIPresentationController的类
3、实现UIViewControllerAnimatedTransitioning代理的类
当然这三个类中有两个是实现协议的类,我们也可以在要跳转到下个视图控制器的VC里实现,不一定非要自己创建三个吧。
UIViewControllerTransitioningDelegate我们要实现三个代理方法
- (nullable UIPresentationController *)presentationControllerForPresentedViewController:(UIViewController *)presented presentingViewController:(nullable UIViewController *)presenting sourceViewController:(UIViewController *)source NS_AVAILABLE_IOS(8_0) {
ShowInfoPresentationController *showInfoPresentationController = [[ShowInfoPresentationController alloc] initWithPresentedViewController:presented presentingViewController:presenting];
return showInfoPresentationController;
}
设置UIPresentationController。
- (nullable id )animationControllerForPresentedController:(UIViewController *)presented presentingController:(UIViewController *)presenting sourceController:(UIViewController *)source {
ShowInfoAnimatedTransitioning *showInfoAnimatedTransitioning = [[ShowInfoAnimatedTransitioning alloc] init];
// present
showInfoAnimatedTransitioning.isPresent = YES;
return showInfoAnimatedTransitioning;
}
当视图控制器present时执行动画
- (nullable id )animationControllerForDismissedController:(UIViewController *)dismissed {
ShowInfoAnimatedTransitioning *showInfoAnimatedTransitioning = [[ShowInfoAnimatedTransitioning alloc] init];
// present
showInfoAnimatedTransitioning.isPresent = NO;
return showInfoAnimatedTransitioning;
}
当视图控制器dismiss时执行动画
UIPresentationController也有它生存周期方法
// Begin
- (void)presentationTransitionWillBegin;
// 呈现
- (void)presentationTransitionDidEnd:(BOOL)completed;
// 快要销毁
- (void)dismissalTransitionWillBegin;
// 销毁
- (void)dismissalTransitionDidEnd:(BOOL)completed;
// 动画执行的时间
- (NSTimeInterval)transitionDuration:(nullable id )transitionContext;
// 实际的动画
- (void)animateTransition:(id )transitionContext {
if (self.isPresent) {
UIView *presentedView = [transitionContext viewForKey:UITransitionContextToViewKey];
presentedView.frame = CGRectMake(presentedView.frame.origin.x, -(presentedView.frame.size.height), presentedView.frame.size.width, presentedView.frame.size.height);
[UIView animateWithDuration:timeDuration animations:^{
presentedView.frame = CGRectMake(presentedView.frame.origin.x, 0, presentedView.frame.size.width, presentedView.frame.size.height);
} completion:^(BOOL finished) {
[transitionContext completeTransition:YES];
}];
}
else {
UIView *presentedView = [transitionContext viewForKey:UITransitionContextFromViewKey];
//NSLog(@"%@", NSStringFromCGRect(presentedView.frame));
[UIView animateWithDuration:timeDuration animations:^{
presentedView.frame = CGRectMake(presentedView.frame.origin.x, [UIScreen mainScreen].bounds.size.height, presentedView.frame.size.width, presentedView.frame.size.height);
//NSLog(@"%@", NSStringFromCGRect(presentedView.frame));
} completion:^(BOOL finished) {
[transitionContext completeTransition:YES];
}];
}
}