- 使用 Spring Initializr 创建 Spring Boot 应用程序
- 在Spring Boot中配置Cassandra
- 在 Spring Boot 上配置 Tomcat 连接池
- 将Camel消息路由到嵌入WildFly的Artemis上
我们这里先创建一个简单的工程 , 在storyboard 中拖一个导航控制器 , rootViewController 改成我们的ViewController 。
为了实现自定义动画切换 , 我们需要实现两个协议 。 UIViewControllerAnimatedTransitioning
,UINavigationControllerDelegate
UIViewControllerAnimatedTransitioning 这个协议目的是在需要使用自定义动画的同时,又不影响视图的其他属性,让你把焦点集中在动画实现的本身上,然后通过在这个协议的回调里编写自定义的动画代码,负责切换的具体内容,任何实现了这一协议的对象被称之为动画控制器。
其中有两个比较重要的方法:
transitionDuration(transitionContext: UIViewControllerContextTransitioning?) -> NSTimeInterval
animateTransition(transitionContext: UIViewControllerContextTransitioning)
第一个返回一个动画持续时间就行了 , 第二个是动画主体 。transitionContext
在这里是一个核心 ,通过这个对象能获取到切换时的上下文信息,比如从哪个VC切换到哪个VC等。
let toViewController = transitionContext.viewControllerForKey(UITransitionContextToViewControllerKey);
//let fromViewController = transitionContext.viewControllerForKey(UITransitionContextFromViewControllerKey);
let container = transitionContext.containerView()
container!.addSubview((toViewController?.view)!);
if oper == UINavigationControllerOperation.Push {
toViewController?.view.layer.anchorPoint = CGPointMake(0, 0)
toViewController?.view.center = CGPointMake(0, 0)
toViewController?.view.transform = CGAffineTransformMakeRotation(CGFloat(-M_PI_2))
UIView.animateWithDuration(self.transitionDuration(transitionContext), delay: 0, usingSpringWithDamping: 0.5, initialSpringVelocity: 0.7, options: UIViewAnimationOptions.AllowUserInteraction, animations: { () -> Void in
toViewController?.view.transform = CGAffineTransformMakeRotation(0)
}, completion: { (b) -> Void in
toViewController?.view.transform = CGAffineTransformIdentity
//动画完成
//没有取消就执行完成 取消了 就不能完成
transitionContext.completeTransition(!transitionContext.transitionWasCancelled())
})
}else if oper == UINavigationControllerOperation.Pop{
toViewController?.view.layer.anchorPoint = CGPointMake(1,0) //0-1之间 不要犯傻。。
toViewController?.view.center = CGPointMake(toViewController!.view.bounds.width, 0)
toViewController?.view.transform = CGAffineTransformMakeRotation(CGFloat(-M_PI_2*3))
UIView.animateKeyframesWithDuration(1.3, delay: 0, options: UIViewKeyframeAnimationOptions.AllowUserInteraction, animations: { () -> Void in
UIView.addKeyframeWithRelativeStartTime(0.0, relativeDuration: 0.4, animations: { () -> Void in
toViewController?.view.transform = CGAffineTransformMakeRotation(CGFloat(-M_PI_2)*4)
})
UIView.addKeyframeWithRelativeStartTime(0.4, relativeDuration: 0.2, animations: { () -> Void in
toViewController?.view.transform = CGAffineTransformMakeRotation(CGFloat(M_PI_2/10))
})
UIView.addKeyframeWithRelativeStartTime(0.6, relativeDuration: 0.3, animations: { () -> Void in
toViewController?.view.transform = CGAffineTransformMakeRotation(CGFloat(-M_PI_2)*4)
})
}, completion: { (b) -> Void in
toViewController?.view.transform = CGAffineTransformIdentity
print(transitionContext.transitionWasCancelled())
//动画完成
//没有取消就执行完成 取消了 就不能完成
transitionContext.completeTransition(!transitionContext.transitionWasCancelled())
})
}
这里是我写的一段代码, 当然我这里分了pop 和 push, oper
变量是从另一个方法中获得的,下面会说 。to 和 from没啥说的 ,container
这是一个特殊的容器,切换时的动画将在这个容器中进行。其他的就是push和pop 我自己做得一个动画主体 。当然你可以根据你的需求更改这些部分 。这里主要讲自定义 , 不讲动画。
我们还需要实现另一个协议UINavigationControllerDelegate
,这个协议用来配置一些导航控制器的交互方式等。
在我们的类中定义 var navgationController:UINavigationController
初始化的时候
init(nav:UINavigationController){
self.navgationController = nav
super.init()
self.navgationController.delegate = self
}
func navigationController(navigationController: UINavigationController, animationControllerForOperation operation: UINavigationControllerOperation, fromViewController fromVC: UIViewController, toViewController toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
oper = operation
return self
}
我们上面的oper
就是从这里来的, 这个可以得到当前进行的是push 还是 pop 。return nil
就表示用系统默认的动画 ,return self
就表示使用我们自己定的 ,如果你只定义了一个push 或者 pop ,可以加个判断 。
这时候的效果应该是这样的:
gif有点卡顿 ,应该都有弹的效果的。。。后面会附上源码 ,大家自己运行看看
如果还要支持手势先加上这个方法
func navigationController(navigationController: UINavigationController, interactionControllerForAnimationController animationController: UIViewControllerAnimatedTransitioning) -> UIViewControllerInteractiveTransitioning? {
/**
* 监控进度
*/
if animationController.isKindOfClass(MyAnimation.self)
{
return self._interactivePushTransition
}
return nil;
}
然后写两个手势操作 ,分别针对 push和pop
func handleControllerPush(sender:UIPanGestureRecognizer){
let location = sender.translationInView(sender.view)
var progress = location.x / (sender.view?.bounds.size.width)!
// print("\(location.x),\((sender.view?.bounds.size.width)!)")
progress = max(-1, min(progress, 0));
let pz = progress * -1
//print(progress)
if sender.state == UIGestureRecognizerState.Began{
/**
* 手势开始,新建一个监控对象
*/
self._interactivePushTransition = UIPercentDrivenInteractiveTransition()
/**
* 告诉控制器开始执行push的动画
*/
self.navgationController.pushViewController(toVc!, animated: true)
}else if sender.state == UIGestureRecognizerState.Changed{
/**
* 更新手势的完成进度
*/
//print(progress * -1)
_interactivePushTransition?.updateInteractiveTransition(pz)
}else if(sender.state == UIGestureRecognizerState.Ended || sender.state == UIGestureRecognizerState.Changed){
/**
* 手势结束时如果进度大于一半,那么就完成push操作,否则重新来过。
*/
print(pz)
if(pz > 0.14 ){
self._interactivePushTransition?.finishInteractiveTransition()
}else{
self._interactivePushTransition?.cancelInteractiveTransition()
}
//当切换动画完毕时,设定interactionController为nil非常重要。如果下一个动画是非交互的,我们不希望得到一个奇怪的 interactionController
self._interactivePushTransition = nil
}
}
pop的就不放了 , 自己下载代码看吧 。。
写一个自己的导航控制器 。
protocol MyPushNav{
func pushView()->UIViewController;
}
class MyNavigationController: UINavigationController {
var pushDele:MyPushNav?
var animate:MyAnimation?
override func viewDidLoad() {
super.viewDidLoad()
animate = MyAnimation(nav: self);
let pan = UIPanGestureRecognizer(target: animate, action: "handleControllerPop:")
self.view.addGestureRecognizer(pan)
}
override func viewDidAppear(animated: Bool) {
pushView();
}
func pushView(){
let pan2 = UIPanGestureRecognizer(target: animate, action: "handleControllerPush:")
if let _ = pushDele {
let sc = pushDele?.pushView()
self.animate?.toVc = sc
(pushDele as! UIViewController).view.addGestureRecognizer(pan2)
}else{
self.view.removeGestureRecognizer(pan2)
}
}
}
需要push的必须告知我们用push哪个,所以这些用了协议 。
pop的不用做任何操作 。
class ViewController: UIViewController,MyPushNav {
override func viewDidLoad() {
super.viewDidLoad()
(self.navigationController as! MyNavigationController).pushDele = self
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func pushView()->UIViewController {
return SecondViewController()
}
}
这个是push的 。。
附上一张有用的图理解理解
源码地址 :MyNavigationController
学习iOS,有他就够了,小码哥视频,传智、黑马、各种swift书籍
好的,所以我编辑了以下... 只需将以下内容放入我的 custom.css #rt-utility .rt-block {CODE HERE} 但是当我尝试改变... 与 #rt-sideslid
在表格 View 中,我有一个自定义单元格(在界面生成器中高度为 500)。在该单元格中,我有一个 Collection View ,我按 (10,10,10,10) 固定到边缘。但是在 tablev
对于我的无能,我很抱歉,但总的来说,我对 Cocoa、Swift 和面向对象编程还很陌生。我的主要来源是《Cocoa Programming for OS X》(第 5 版),以及 Apple 的充满
我正在使用 meta-tegra 为我的 NVIDIA Jetson Nano 构建自定义图像。我需要 PyTorch,但没有它的配方。我在设备上构建了 PyTorch,并将其打包到设备上的轮子中。现
在 jquery 中使用 $.POST 和 $.GET 时,有没有办法将自定义变量添加到 URL 并发送它们?我尝试了以下方法: $.ajax({type:"POST", url:"file.php?
Traefik 已经默认实现了很多中间件,可以满足大部分我们日常的需求,但是在实际工作中,用户仍然还是有自定义中间件的需求,为解决这个问题,官方推出了一个 Traefik Pilot[1] 的功
我想让我的 CustomTextInputLayout 将 Widget.MaterialComponents.TextInputLayout.OutlinedBox 作为默认样式,无需在 XML 中
我在 ~/.emacs 中有以下自定义函数: (defun xi-rgrep (term) (grep-compute-defaults) (interactive "sSearch Te
我有下表: 考虑到每个月的权重,我的目标是在 5 个月内分散 10,000 个单位。与 10,000 相邻的行是我最好的尝试(我在这上面花了几个小时)。黄色是我所追求的。 我试图用来计算的逻辑如下:计
我的表单中有一个字段,它是文件类型。当用户点击保存图标时,我想自然地将文件上传到服务器并将文件名保存在数据库中。我尝试通过回显文件名来测试它,但它似乎不起作用。另外,如何将文件名添加到数据库中?是在模
我有一个 python 脚本来发送电子邮件,它工作得很好,但问题是当我检查我的电子邮件收件箱时。 我希望该用户名是自定义用户名,而不是整个电子邮件地址。 最佳答案 发件人地址应该使用的格式是: You
我想减小 ggcorrplot 中标记的大小,并减少文本和绘图之间的空间。 library(ggcorrplot) data(mtcars) corr <- round(cor(mtcars), 1)
GTK+ noob 问题在这里: 是否可以自定义 GtkFileChooserButton 或 GtkFileChooserDialog 以删除“位置”部分(左侧)和顶部的“位置”输入框? 我实际上要
我正在尝试在主页上使用 ajax 在 magento 中使用 ajax 显示流行的产品列表,我可以为 5 或“N”个产品执行此操作,但我想要的是将分页工具栏与结果集一起添加. 这是我添加的以显示流行产
我正在尝试使用 PasswordResetForm 内置函数。 由于我想要自定义表单字段,因此我编写了自己的表单: class FpasswordForm(PasswordResetForm):
据我了解,新的 Angular 7 提供了拖放功能。我搜索了有关 DnD 的 Tree 组件,但没有找到与树相关的内容。 我在 Stackblitz 上找到的一个工作示例.对比drag'ndrop功能
我必须开发一个自定义选项卡控件并决定使用 WPF/XAML 创建它,因为我无论如何都打算学习它。完成后应该是这样的: 到目前为止,我取得了很好的进展,但还有两个问题: 只有第一个/最后一个标签项应该有
我要定制xtable用于导出到 LaTeX。我知道有些问题是关于 xtable在这里,但我找不到我要找的具体东西。 以下是我的表的外观示例: my.table <- data.frame(Specif
用ejs在这里显示日期 它给我结果 Tue Feb 02 2016 16:02:24 GMT+0530 (IST) 但是我需要表现为 19th January, 2016 如何在ejs中执行此操作?
我想问在 JavaFX 中使用自定义对象制作 ListView 的最佳方法,我想要一个每个项目如下所示的列表: 我搜了一下,发现大部分人都是用细胞工厂的方法来做的。有没有其他办法?例如使用客户 fxm
我是一名优秀的程序员,十分优秀!