在此介绍一下基本知识:
1.在哪里写我们自定义的动画.
苹果给我们提供了UIViewControllerAnimatedTransitioning协议,这个协议提供了我们需要的接口,遵守这个协议的对象实现动画基本内容.
让我们跳转进去看看都有什么:
@protocol UIViewControllerAnimatedTransitioning <NSObject>
// This is used for percent driven interactive transitions, as well as for
// container controllers that have companion animations that might need to
// synchronize with the main animation.
// 这个接口返回的值为动画时长
- (NSTimeInterval)transitionDuration:(nullable id <UIViewControllerContextTransitioning>)transitionContext;
// This method can only be a nop if the transition is interactive and not a percentDriven interactive transition.
// 这个接口返回的值为具体动画内容,也就是说,自定义的动画操作都通过这个接口来实现
- (void)animateTransition:(id <UIViewControllerContextTransitioning>)transitionContext;
@optional
/// A conforming object implements this method if the transition it creates can
/// be interrupted. For example, it could return an instance of a
/// UIViewPropertyAnimator. It is expected that this method will return the same
/// instance for the life of a transition.
- (id <UIViewImplicitlyAnimating>) interruptibleAnimatorForTransition:(id <UIViewControllerContextTransitioning>)transitionContext NS_AVAILABLE_IOS(10_0);
// This is a convenience and if implemented will be invoked by the system when the transition context's completeTransition: method is invoked.
- (void)animationEnded:(BOOL) transitionCompleted;
@end
1.通过注释的解释,我们能够知道,遵守UIViewControllerAnimatedTransitioning协议的对象就可以实现我们自定义的动画.
2.通常我们会自定义NSObject的子类,遵守UIViewControllerAnimatedTransitioning协议,然后实现协议方法来自定义转场动画.
3.这个子类的对象就是我们的"自定义动画".如果把自定义转场动画比作为做菜的话,那么现在我们准备的就是食材.
1.From和To
在自定义转场动画的代码中,经常会出现fromViewController和toViewController。如果错误的理解它们的含义会导致动画逻辑完全错误。
fromViewController表示当前视图容器,toViewController表示要跳转到的视图容器。如果是从A视图控制器present到B,则A是from,B是to。从B视图控制器dismiss到A时,B变成了from,A是to。
2.Presented和Presenting
这也是一组相对的概念,它容易与fromView和toView混淆。简单来说,它不受present或dismiss的影响,如果是从A视图控制器present到B,那么A总是B的presentingViewController, B总是A的presentedViewController。
2.在哪里用我们自定义的动画.
这里要介绍三个协议: 注意每个协议方法的返回值,都是遵守UIViewControllerAnimatedTransitioning的对象
1.协议一: UIViewControllerTransitioningDelegate
// 实现present/dismiss动画的接口.
// 令我们需要自定义动画的控制器遵守UIViewControllerTransitioningDelegate协议,并设置代理,实现协议方法,返回遵守UIViewControllerAnimatedTransitioning协议的类对象即可
// 在这里需要清楚一点,假设由控制器A present 到B, A遵守UIViewControllerTransitioningDelegate协议,则设置B.transitioningDelegate = A,并设置B.modalPresentationStyle = UIModalPresentationCustom(或UIModalPresentationFullScreen);
// 一定要设置modalPresentationStyle,不然还是默认的转场动画.
// present动画
- (nullable id <UIViewControllerAnimatedTransitioning>)animationControllerForPresentedController:(UIViewController *)presented presentingController:(UIViewController *)presenting sourceController:(UIViewController *)source;
// dismiss动画
- (nullable id <UIViewControllerAnimatedTransitioning>)animationControllerForDismissedController:(UIViewController *)dismissed;
# modalPresentationStyl
// 这是一个枚举类型,表示present时动画的类型。
// 其中可以自定义动画效果的只有两种:FullScreen和Custom,两者的区别在于FullScreen会移除fromView,而Custom不会。
2.协议二:UINavigationControllerDelegate
// 实现push/pop动画的接口
// 这里同样是要遵守协议,设置代理,实现协议方法.
// 注意这里设置的是navigationController.delegate, self.navigationController.delegate = self.
// 我在其他的博客中看到: (注意: 这里的 self.navigationController.delegate = self 最好写在当前控制器的viewDidAppear方法中, 不然会导致在此push时无动画效果),为什么会失效我还不清楚,希望读者能够找到并分享一下~
- (nullable id <UIViewControllerAnimatedTransitioning>)navigationController:(UINavigationController *)navigationController
animationControllerForOperation:(UINavigationControllerOperation)operation
fromViewController:(UIViewController *)fromVC
toViewController:(UIViewController *)toVC
3.协议三:UITabBarControllerDelegate
// 实现tabBarController切换子控制器的动画
// 还是老套路,遵守协议,设置代理,实现协议方法
// 只是这里要设置tabBarController的代理,我的做法就是在UITabBarController的viewDidLoad方法里设置代理: self.delegate = self;
- (nullable id <UIViewControllerAnimatedTransitioning>)tabBarController:(UITabBarController *)tabBarController
animationControllerForTransitionFromViewController:(UIViewController *)fromVC
toViewController:(UIViewController *)toVC NS_AVAILABLE_IOS(7_0);
自定义present/dismiss动画要遵守UIViewControllerTransitioningDelegate协议
自定义push/pop动画要遵守UINavigationControllerDelegate协议
自定义tabbarController转场动画要遵守UITabBarControllerDelegate协议
以demo为例:
// DMMainViewController.m文件
@interface DMMainViewController ()<UITabBarControllerDelegate>// 遵守协议
@end
@implementation DMMainViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.delegate = self;// 设置代理
UIViewController *vc = [[UIViewController alloc] init];
vc.view.backgroundColor = [UIColor whiteColor];
[self setChildchildViewController:vc index:0 title:@"我是A"];
[self setChildchildViewController:[[UITableViewController alloc] init] index:1 title:@"我是B"];
[self setChildchildViewController:[[UIViewController alloc] init] index:2 title:@"我是C"];
}
// 动画 实现协议方法
- (nullable id <UIViewControllerAnimatedTransitioning>)tabBarController:(UITabBarController *)tabBarController animationControllerForTransitionFromViewController:(UIViewController *)fromVC toViewController:(UIViewController *)toVC{
return [[AnimationManager alloc] init];
}
这里其实就是遵守协议,设置代理,实现协议方法.
// AnimationManager.h文件
// 自定义NSObject的子类,遵守UIViewControllerAnimatedTransitioning协议
@interface AnimationManager : NSObject<UIViewControllerAnimatedTransitioning>
@property (nonatomic, assign) KAnimationType type;
- (instancetype)initWithType:(KAnimationType)type;
@end
// AnimationManager.m文件
#import "AnimationManager.h"
#import "DMNavigationViewController.h"
@interface AnimationManager ()
@end
@implementation AnimationManager
// 这个是动画时长
- (NSTimeInterval)transitionDuration:(id<UIViewControllerContextTransitioning>)transitionContext {
return 0.5;
}
// 具体动画,在这里可以根据你的想象去实现你要的动画效果了
- (void)animateTransition:(id<UIViewControllerContextTransitioning>)transitionContext {
// 获取fromVc和toVc
DMNavigationViewController *fromVc = (DMNavigationViewController *)[transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey];
DMNavigationViewController *toVc = (DMNavigationViewController *)[transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];
UIView *fromV = fromVc.view;
UIView *toV = toVc.view;
// 转场环境
UIView *containView = [transitionContext containerView];
containView.backgroundColor = [UIColor whiteColor];
// 判断滑动方向
if (toVc.index > fromVc.index) {
toV.frame = CGRectMake([UIScreen mainScreen].bounds.size.width, 0, containView.frame.size.width, containView.frame.size.height);
[containView addSubview:toV];
// 动画
[UIView animateWithDuration:[self transitionDuration:transitionContext] animations:^{
fromV.transform = CGAffineTransformTranslate(fromV.transform, -[UIScreen mainScreen].bounds.size.width,0);// containView.frame.size.height
toV.transform = CGAffineTransformTranslate(toV.transform, -[UIScreen mainScreen].bounds.size.width, 0);
} completion:^(BOOL finished) {
[transitionContext completeTransition:YES];
}];
}else if (toVc.index < fromVc.index) {
toV.frame = CGRectMake(- [UIScreen mainScreen].bounds.size.width, 0, containView.frame.size.width, containView.frame.size.height);
[containView addSubview:toV];
[UIView animateWithDuration:[self transitionDuration:transitionContext] animations:^{
fromV.transform = CGAffineTransformTranslate(fromV.transform, [UIScreen mainScreen].bounds.size.width,0);
toV.transform = CGAffineTransformTranslate(toV.transform, [UIScreen mainScreen].bounds.size.width, 0);
} completion:^(BOOL finished) {
[fromV removeFromSuperview];
[transitionContext completeTransition:YES];
}];
}
}
@end
# 这里面就涉及到前面讲的 1.From和To的关系,2.Presented和Presenting的关系.在2.1的底部有介绍
所谓的自定义转场动画,就是把系统默认的换成我们自己写的而已,关键就是在这些协议里.理清控制器与协议的关系.
简单的画了一个结构图
附: 以UITabBarController为例的简单转场动画demo地址 gitHub地址
近来换工作了,导入新项目时gradle各种添堵,使用最新的2.4的第7版预览版studio,gradle 3.4.1,工程使用的是gradle 2.1.3,然后项目各种卡在gradle 加载依赖,后来将以前环境的.gradle压缩拿过来重新配置studio中的gradle,将offline配置为c盘用户下的.gradle才解决一直依赖的问题然后就是tiinker的初体验了,这个其实也有些问题的
相关性系数和显著性水平在统计学中,皮尔逊相关系数( Pearson correlation coefficient),又称皮尔逊积矩相关系数(Pearson product-moment correlation coefficient,简称 PPMCC或PCCs)<很多英文文献中的叫法>,是用于度量两个变量X和Y之间的相关(线性相关),其值介于-1与1之间。P值,也就是Sig值或显著性值。如果P值小于0.01即说明某件事情的发生至少有99%的把握,如果P值小于0.05(并且大于0.01)则说
一.修改主机名1.通过VNC登录树莓派2.sudo gedit /etc/hosts 将“127.0.1.1 raspberrypi”中的raspberrypi改为hydx3.sudo gedit /etc/hostname 将raspberrypi改为hydx4.重启树莓派二.添加用户注意:想要进树莓派的时候切换用户需要sudo raspi-config 进入Boot option...
今天遇到了一个问题,大致描述如标题。当一个应用启动后,经过一些操作后,出现界面无反应现象。此时点击其中的按钮,如果是启动activity那就OK。如果是类似滚动条这样的,或者按钮点击不切换界面的,就看上没有任何反映。因为应用在跳转后再回来就会正常,而且界面就是在无反应情况下操作后的界面。所以怀疑是界面显示的操作功能部分OK,只是界面没有更新到屏幕上。所以下边通过在界面显示,绘制部分代码中增加l...
目录题目函数接口定义裁判测试程序样例输入样例输出样例分析答案整个程序的代码题目:本题要求实现一个函数,求给定的N个整数的和。函数接口定义:int Sum ( int List[], int N );其中给定整数存放在数组List[]中,正整数N是数组元素个数。该函数须返回N个List[]元素的和。裁判测试程序样例:#include <stdio.h>#define MAXN 10int Sum ( int List[],
key=&secret=&order_id=&onlystatus=0"请求地址: https://api-gw.onebound.cn/taobao/buyer_order_detail。请求参数:order_id=&onlystatus=0。-- 请求示例 url 默认请求参数已经URL编码处理。token:SaaS授权。
export NLS_LANG=AMERICAN_AMERICA.UTF8cat /dev/null > output.txtuser=$1password=$2url=$3sqlfile=$4/app/oracle/product/bin/sqlplus $user/$password@$url @$sqlfileexitE
1、(结构体)数组存储多个相同类型的数据,结构体可以存放不同类型的数据。结构体变量只能在初始化的时候采用{}的形式赋值,由于0开头是八进制,所以09这样的形式是错误的表示。结构体之间的变量赋值 a = b;只会成员变量之间值赋值过程,其中一个改变不会影响另一个。2、结构体所占内存的字节数一定是最大成员变量类型字节数的倍数3、结构体的定义方式:1. structDog{……}
参考资料: 使用Eclipse+Axis2開發Web Service應用 http://www.guan8.net/Java/74696.html 使用Eclipse+Axis2构建Web Service应用 http://panpan.blog.51cto.com/489034/119204Axis2 WebService(配置、发布、调用)
一、数据类型Python中可以自定义数据类型,可以具有无限种数据类型。 系统默认提供6个标准数据类型: Number类型 数值类型 String类型 字符类型 List类型 列表类型 tuple类型 元组类型 dict类型 字典类型 set类...
Nvidia AGX Xavier 配置CUDA,PyTorch,ONNX,TensorRT,将深度学习模型部署到小车上,测试三个计算框架的性能
(一)课题的核心概念及其界定(二)国内外同一研究领域现状与研究的价值(三)研究的目标、内容(或子课题设计)与重点(四)研究的思路、过程与方法(五)主要观点与可能的创新之处(请分5部分逐项填写,详述研究内容,限2500字内,可附页)一、课题的核心概念及其界定:1、课题的核心概念:“微课”的核心组成内容是课堂教学视频(课例片段),同时还包含与该教学主题相关的教学设计、素材课件、教学反思、练习测试及学生...