从iOS8开始,controller之间的跳转特效,需要用新的API UIPresentationController来实现。比如希望实现这样一个特效:显示一个模态窗口,大小和位置是自定义的,遮罩在原来的页面上。在iOS8之前,可以在viewWillAppear里设置superview的frame:
- (void)presentModal:(NSDictionary*)result
{
YLSCheckoutSignatureController *controller = [[YLSCheckoutSignatureController alloc] initWithModel:result];
if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0) {
controller.modalPresentationStyle = UIModalPresentationCustom;
}else{
controller.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;
controller.modalPresentationStyle = UIModalPresentationFormSheet;
}
[self presentViewController:controller animated:YES completion:nil];
}
-(void) viewWillAppear:(BOOL)animated
{
// in iOS8, handle by UIPresentationController
if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0) {
return;
}
self.view.superview.layer.cornerRadius = 10;
self.view.superview.layer.borderColor = [UIColor darkGrayColor].CGColor;
self.view.superview.clipsToBounds = YES;
self.view.superview.frame = CGRectMake(62, 114, 900, 540);
}
但是以上的代码,在iOS8里就不再生效了,要用UIPresentationController来实现
首先明确一点,从Controller A->B,B的样式和跳转特效,还是由B来控制的。只不过以前是直接在Controller的生命周期方法里操作,而现在有专门的API来完成而已。这种设计也是合理的,否则如果从A可以跳转到B和C,但是样式和特效不一样,就只能通过在A里面设置实例变量来区分了,容易出错也很别扭。所以把跳转的行为由目标Controller来控制是很合理的
不过这组API的文档不太全,后续SDK升级可能会逐渐完善。以下介绍实现步骤:
目标Controller实现特定protocol
首先目标Controller要实现特定的协议,创建一个UIPresentationController
@interface YLSCheckoutSignatureController : UIViewController<UIScrollViewDelegate, UIViewControllerTransitioningDelegate>
self.transitioningDelegate = self;
- (UIPresentationController *)presentationControllerForPresentedViewController:(UIViewController *)presented presentingViewController:(UIViewController *)presenting sourceViewController:(UIViewController *)source
{
return [[YLSMainPresentationController alloc] initWithPresentedViewController:presented presentingViewController:presenting];
}
当条件满足时,iOS系统会调用这个方法,于是可以实例化自定义的UIPresentationController子类,定义跳转的样式和特效
自定义UIPresentationController
然后就要实现自定义的UIPresentationController,下面这段实例代码,实现居中展示一个自定义frame的模态页面,同时有半透明背景遮住原来的页面
@implementation YLSMainPresentationController
{
UIView *dimmingView;
}
-(id) initWithPresentedViewController:(UIViewController *)presentedViewController presentingViewController:(UIViewController *)presentingViewController
{
self = [super initWithPresentedViewController:presentedViewController presentingViewController:presentingViewController];
if(self){
dimmingView = [[UIView alloc] init];
dimmingView.backgroundColor = [UIColor grayColor];
dimmingView.alpha = 0.0;
}
return self;
}
- (void)presentationTransitionWillBegin
{
dimmingView.frame = self.containerView.bounds;
[self.containerView addSubview:dimmingView];
[self.containerView addSubview:self.presentedView];
id<UIViewControllerTransitionCoordinator> coordinator = self.presentingViewController.transitionCoordinator;
[coordinator animateAlongsideTransition:^(id<UIViewControllerTransitionCoordinatorContext> context) {
dimmingView.alpha = 0.5;
} completion:nil];
}
- (void)presentationTransitionDidEnd:(BOOL)completed
{
if(!completed){
[dimmingView removeFromSuperview];
}
}
- (void)dismissalTransitionWillBegin
{
id<UIViewControllerTransitionCoordinator> coordinator = self.presentingViewController.transitionCoordinator;
[coordinator animateAlongsideTransition:^(id<UIViewControllerTransitionCoordinatorContext> context) {
dimmingView.alpha = 0.0;
} completion:nil];
}
- (void)dismissalTransitionDidEnd:(BOOL)completed
{
if(completed){
[dimmingView removeFromSuperview];
}
}
- (CGRect)frameOfPresentedViewInContainerView
{
return CGRectMake(62.f, 114.f, 900.f, 540.f);
}
@end
代码确实比以前复杂了一点,但是其实每个生命周期方法都是比较明确的,开发者可控的粒度也更细了。比如设置presented frame,就有专门的方法,只要返回CGRect就可以了,还是比较方便的
原始的ViewController发起跳转动作
经过前面2步,当自定义跳转发生时,就可以很细致地控制样式和跳转行为。接下来就是由原始controller(presenting view controller)来发起跳转动作:
- (void)presentModal:(NSDictionary*)result
{
YLSCheckoutSignatureController *controller = [[YLSCheckoutSignatureController alloc] initWithModel:result];
if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0) {
controller.modalPresentationStyle = UIModalPresentationCustom;
}else{
controller.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;
controller.modalPresentationStyle = UIModalPresentationFormSheet;
}
[self presentViewController:controller animated:YES completion:nil];
}
关键是设置modalPresentationStyle为UIModalPresentationCustom,然后当presentViewController方法调用时,iOS系统就会创建出UIPresentationController的实例,来控制跳转的行为
分享到:
相关推荐
iOS的UIPresentationController和附带的UIPresentationController提供了固定在屏幕边缘的视图控制器(如动作表)的视图控制器。 安装 迅捷软件包管理器 要将SheetPresentation与,请将其作为依赖项从Xcode中添加到您...
在iOS 8中,苹果为开发者带来了众多新特性和API更新,极大地扩展了应用程序的功能和可能性。本示例代码库提供了对这些新功能的详细演示,帮助开发者更好地理解和利用这些新特性来提升应用的用户体验。以下是一些主要...
在Swift编程中,UIPresentationController是一个非常重要的类,它允许我们自定义视图控制器的呈现方式,从而实现一些独特和富有创意的用户界面效果。在本教程中,我们将深入探讨如何利用UIPresentationController来...
UIPresentationController是 iOS8 新增的一个API,苹果的官方定义是:对象为所呈现的视图控制器提供高级视图的转换管理。这里将使用UIPresentationController实现一些modal动画效果,有详细的注释和讲解,欢迎点赞和...
6. **互动性(Interactivity)**:在iOS 8及以上版本,`UIPresentationController`允许在动画过程中进行交互,例如用户在动画进行时选择一个菜单项。开发者可能会实现这个特性,使用户体验更加流畅。 7. **代码组织...
这似乎是iOS 7或iOS 8上的UIKit错误UIPresentationController通过提供一种在方向更改时调整控制器大小的方法来解决该问题。 状态恢复是可能的,但提出的VC应该恢复transitioningDelegate , ...
在iOS开发中,过渡动画(Transition Animation)是用户体验设计中的一个重要组成部分,它们为用户界面的交互增添生动性和吸引力。过渡动画不仅仅是美观的装饰,更是帮助用户理解应用操作流程、导航结构以及状态变化...
8. **NSStoryboardSegue (Mac Catalyst)**: 如果你正在为Mac Catalyst开发应用,NSStoryboardSegue提供了类似UIStoryboardSegue的功能,可以用来实现跨平台的自定义转场动画。 在"TransitionAnimation"这个压缩包中...
`UIWebView`是苹果早期提供的API,用于在iOS应用中显示网页内容,而`WKWebView`则是在iOS 8之后引入的新一代组件,具有更好的性能和安全性。尽管`UIWebView`已经被标记为过时,但在某些老版本的应用中可能仍会用到。...
UIActionSheet是UIAlertView的替代品,在iOS 8之后被推荐使用。它通常用于在全屏或部分屏幕显示一组操作选项,如“取消”、“删除”等。使用UIActionSheet时,我们需要创建一个UIActionSheet实例,添加按钮,然后...
在实现弹出效果时,开发者可能使用了UIPresentationController或UIPopoverPresentationController。前者提供了自定义呈现行为的机会,而后者特别适用于iPad上的popover样式,它可以从任意视图边缘弹出,非常适合展示...
- iOS 8引入了`UIPresentationController`,它提供了自定义视图控制器呈现行为的能力。通过自定义这个控制器,我们可以控制子视图如何显示,包括动画效果、大小和位置等。在这个例子中,我们需要自定义一个子类,...
自定义转场往往涉及到多个视图控制器的协同工作,因此理解`UIContainerView`和`UIPresentationController`的概念至关重要。在MagicTransitionDemo中,可能涉及到嵌套的容器视图控制器,它们负责管理子控制器的生命...
8. **响应式设计**:考虑到iOS设备的多样性,弹出视图的大小和位置应根据屏幕尺寸进行适配。可以使用Auto Layout的约束或者programmatically计算布局。 9. **手势处理**:为了关闭弹出视图,通常会添加手势识别器,...
iPhone Xs模拟器上的DEMO视频iOS CardPresentationController自定义UIPresentationController中的模态演示,它模仿Apple Music UI的行为。 在iOS 10及更高版本上应该可以正常工作。 iPhone Xs模拟器上的DEMO视频iOS ...
在iOS开发中,有时我们希望实现一种特殊的效果,比如在presenting一个新的视图控制器时,不仅保持原有的背景可见,还能给用户带来半透明或者毛玻璃(Blur Effect)的视觉体验。在这种情况下,我们需要创建一个透明的...
4. 弹窗效果:使用`UIPresentationController`或`UIViewControllerTransitioningDelegate`来实现弹出和关闭的动画效果。你还可以添加阴影和背景模糊,以模拟系统弹窗的视觉感受。 5. 响应事件:监听用户点击确认或...
在iOS中,我们可以通过自定义UIView或者利用UIPresentationController来实现这种效果。 1. **自定义UIView**:创建一个继承自UIView的类,负责绘制通知的背景、文字、图标等。在需要显示通知时,将这个视图添加到...
8. **动画和过渡**:通过 `UIViewPropertyAnimator` 或 `CATransition` 可以创建更复杂的动画效果,使模态视图的出现和消失更加吸引人。 9. ** Accessibility**:确保模态视图对辅助功能的支持,比如 VoiceOver。...
4. **UIPresentationController**:iOS 8引入了UIPresentationController,可以自定义控制器的呈现方式,例如创建一个全屏的预览视图。自定义预览视图时,需要继承UIPresentationController,并在子类中实现相关布局...