close
当前位置: 物联网在线 > 技术文库 > ios >

使用 UIPresentationController 实现自定义弹窗

UIPresentationController 是 iOS8 新增的一个 API,可以用它实现自定义的弹窗。但 UIPresentationController 的使用门槛比较高,需要实现几个类和相关代理。 Presentr 让这一切变得简单,轻松实现自定义警告窗、菜单或其他任何弹窗。如下图:

使用 UIPresentationController 实现自定义弹窗

Presentr 实现弹窗

Presentr 提供了一个默认的弹窗类 AlertViewController,以下代码即可显示上面的弹窗:

let presenter = Presentr(presentationType: .Alert) presenter.transitionType = TransitionType.CrossDissolve let controller = Presentr.alertViewController(title: title, body: body) let cancelAction = AlertAction(title: "NO, SORRY! :scream:", style: .Cancel) { alert in print("CANCEL!!") } let okAction = AlertAction(title: "DO IT! ��", style: .Destructive) { alert in print("OK!!") } alertController.addAction(cancelAction) alertController.addAction(okAction) customPresentViewController(presenter, viewController: controller, animated: true, completion: nil)

要实现自定义的窗口,只需将上面的 AlertViewController 换成我们自己的窗口类即可,如下的 SomeViewController。

let alertController = SomeViewController() customPresentViewController(presenter, viewController: alertController, animated: true, completion: nil)

Presentr 提供了五种显示类型,如下

public enum PresentationType { case Alert case Popup case TopHalf case BottomHalf case Custom(width: ModalSize, height: ModalSize, center: ModalCenterPosition) }

通过 PresentationType.Custom 我们可自定义弹窗的大小

let width = ModalSize.Custom(size: 320) let height = ModalSize.Custom(size: 150) let center = ModalCenterPosition.Center //CustomOrigin(origin: CGPoint(x: 0, y: 100)) let customType = PresentationType.Custom(width: width, height: height, center: center) let customPresenter = Presentr(presentationType: customType) customPresenter.transitionType = .CrossDissolve Presentr 如何实现弹窗

Presentr 封装了 UIPresentationController,UIViewControllerTransitioningDelegate,UIViewControllerAnimatedTransitioning,类图如下:

使用 UIPresentationController 实现自定义弹窗

首先要清楚两个概念:当前的窗口为 presentingViewController,即将显示的窗口为 presentedViewController。 主要函数调用步骤:

在主窗口 UIViewController 中调用 customPresentViewController(presenter, viewController: alertController, animated: true, completion: nil)

Presentr: presentationControllerForPresentedViewController ,返回 PresentrController

Presentr: animationControllerForPresentedController

PresentrController: presentationTransitionWillBegin

PresentrController: frameOfPresentedViewInContainerView

PresentrController: containerViewWillLayoutSubviews

第一步是 Presentr 对 UIPresentationController 细节封装后提供的 UIViewController 的扩展函数。我们只需要写这行代码,剩下的步骤都由 Presentr 完成。这里,Presentr 将设置 PresentedView 的代理 —— transitioningDelegate = self 。

第二步和第三步都是 UIViewControllerTransitioningDelegate 协议的函数,由 Presentr 实现。第二步完成 UIPresentationController 的 子类 PresentrController 的初始化。在初始化创建一个黑色半透明背景视图,如下

init(presentedViewController: UIViewController, presentingViewController: UIViewController, presentationType: PresentationType, roundCorners: Bool, dismissOnTap: Bool) { self.presentationType = presentationType self.roundCorners = roundCorners self.dismissOnTap = dismissOnTap super.init(presentedViewController: presentedViewController, presentingViewController: presentingViewController) setupChromeView() } private func setupChromeView() { let tap = UITapGestureRecognizer(target: self, action: #selector(chromeViewTapped)) chromeView.addGestureRecognizer(tap) chromeView.backgroundColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0.7) chromeView.alpha = 0 }

第三步是 PresentedView 出现时的动画效果。苹果自带的动画有从底向上弹窗、渐隐渐现、翻转,Presentr 实现了两个自定义的动画效果:从左往右或从右往左,从上往下。如果需要其他动画效果需要自己实现。

第四步,在 PresentedView 显示之前,添加半透明视图 chromeView 到 PresentrController 的 containerView 中,并添加 chromeView 的显示动画

override func presentationTransitionWillBegin() { chromeView.frame = containerView!.bounds chromeView.alpha = 0.0 containerView?.insertSubview(chromeView, atIndex: 0) if let coordinator = presentedViewController.transitionCoordinator() { coordinator.animateAlongsideTransition({ context in self.chromeView.alpha = 1.0 }, completion: nil) } else { chromeView.alpha = 1.0 } }

第五步,设置 PresentedView 的 frame 大小。


(责任编辑:ioter)

用户喜欢...

有意义的步骤让私有云实现更容易

有些人认为,私有云只是本地已经实施的虚拟化的一个扩展,但事实上却不只如此。私有云的实现可以帮助打破数据...


在 Airbnb 使用机器学习预测房源的价格

作者:Robert Chang 位于希腊爱琴海伊莫洛维里的一个 Airbnb 民宿的美好风景 简介 数据产品一直是 Airbnb 服务的重要组成...


如何使用可编程逻辑为按钮输入消抖

可编程逻辑具有传统分立 IC 无法提供的灵活性。 借助现成的开发工具,可轻松使用现场可编程门阵列和复杂可编程逻辑器件创建应用特定型功能。 按钮开关输入消抖便是此类功能的一个例子...


使用 LoRa 进行低速率、长距离物联网应用开发

设计人员可以使用各种各样的无线技术将产品连接到物联网 (IoT)。每种技术适用于不同的应用,需要设计人员仔细考虑作用距离和数据速率、成本、功耗、体积和外形等因素。 本文将介绍 LoR...


Vicor 高密度合封电源方案​助力人工智能处理器实现更高的性能

Vicor 公司(NASDAQ 股票交易代码:VICR)今日宣布推出适用于高性能、大电流 CPU/GPU/ASIC(“XPU”)处理器合封的模块化电流倍增器。Vicor 合封电源方案不仅可以减少 XPU 插座的引脚数,还可减少...


这款智能手表心率检测超强 可当做心电图机使用

Cronovo智能手表特别强调心率追踪功能,它安装了Android系统,可以成为个人健身教练,拥有先进的感知追踪系统。Cr...


用于实现脉宽调制 (PWM) 控制的 Allegro MicroSystems A3916 全桥电机驱动器

Allegro MicroSystems的 A3916设计用于实现低电压步进电机和单、双直流电机的脉宽调制 (PWM) 控制。A3916 每通道输出电池可达 1 A,工作电压范围为 2.7 V 至 15 V。A3916 具有内部固定关断时间 PWM 定时器,...


Quora是如何使用机器学习的?

作者:Nikhil Dandekar 2015年,公司的工程副总裁Xavier Amatriain,关于如何在Quora上使用机器学习给了一个很好的答案。从那...


超少量数据训练神经网络:IEEE论文提出径向变换实现图像增强

作者:李亚洲 近日,一篇题为《Training Neural Networks with Very Little Data-A Draft》IEEE 论文提出...


机器学习算法的基本知识(使用Python和R代码)

本篇文章是原文的译文,然后自己对其中做了一些修改和添加内容(随机森林和降维算法)。文章简洁地介绍了机器学习的主要算法和一些伪代码,对于初学者有很大帮助,是一篇不错的总结...