澳门威利斯人_威利斯人娱乐「手机版」

来自 威利斯人娱乐 2020-05-08 17:15 的文章
当前位置: 澳门威利斯人 > 威利斯人娱乐 > 正文

拼出一个3D纸盒人,Techniques学习笔记

老样子 先上效果与利益 全部压迫选拔 颜色微微丑 凑合着看

全体示例代码均可以在 Animations-德姆o 下载到

突显动漫

图片 1

上节涉及 UIView 上具备动漫归根到底都以发生在Layer 层,所以动漫的读书离不开Layer的上学。

属性动画

通过- (void)addAnimation:(CAAnimation *)anim forKey:(NSString *)key;措施,大家得以为三个图层加多多少个呈现动漫。不过,当以此图层并不是三个视图的图层属性的实例时,动画会发生一次,一个是由大家设置的体现动漫引起的,另一个那是因为图层的隐式动漫。为了制止这种意况,大家要求在配置展现动漫的时候钦点它的代办,并促成代理方法-animationDidStop:finished:,在当中设置叁个新的作业,并禁止使用图层行为。

在装置突显动漫的长河中,还会有八个难题便是在动漫实现以往图层的情事又回来了动漫以前的情事。那是因为在暗中认可情形下,动漫完毕之后将透彻移除,不会在其超越时间后还改善展现层的图层。一旦动漫达成,显示层的图层将回来模型层图层的值,而大家又不曾改变图层属性的值,由此动漫达成后图层显示的要么事情发生早先的动静。

此间有二种缓慢解决方案,一种是在设置动漫后更新图层对应属性的值:

// Add explicit animation to a single layer
CGFloat red = rand() / (double)INT_MAX;
CGFloat green = rand() / (double)INT_MAX;
CGFloat blue = rand() / (double)INT_MAX;

CABasicAnimation *animation = [CABasicAnimation animation];
animation.keyPath = @"backgroundColor";
animation.toValue = (__bridge id)[UIColor colorWithRed:red green:green blue:blue alpha:1].CGColor;
animation.delegate = self;
[self.colorLayer addAnimation:animation forKey:nil];

self.colorLayer.backgroundColor = [UIColor colorWithRed:red green:green blue:blue alpha:1].CGColor;

另一种则是安装动漫的 fillMode 属性为 kCAFillModeForward 以留在最终状态,并设置removedOnCompletion 为 NO 避防止它被自动移除:

// Add explicit animation to a single layer
CGFloat red = rand() / (double)INT_MAX;
CGFloat green = rand() / (double)INT_MAX;
CGFloat blue = rand() / (double)INT_MAX;

CABasicAnimation *animation = [CABasicAnimation animation];
animation.keyPath = @"backgroundColor";
animation.toValue = (__bridge id)[UIColor colorWithRed:red green:green blue:blue alpha:1].CGColor;
animation.delegate = self;

animation.fillMode = kCAFillModeForwards;
animation.removedOnCompletion = NO;

[self.colorLayer addAnimation:animation forKey:nil];

急需潜心的是:假诺将已成功的动漫片保持在 layer 上时,会招致额外的费用,因为渲染器会去举办额外的点染工作。

还会有很主要的有些正是,当大家创设好叁个动漫片并丰盛给一个layer时就及时复制了一份,因而那一个动画是能够重复增加个七个layer的。

思路计算

大家日常支出中比较少使用layer,然则我们却一直在接受layer。view是不具有绘制本事的,真正绘制的是他的underlying layer 。 各类view都有三个layer属性。view上体现相关的习性也是layer属性的贰个映射。荧屏凸显的时候 UIViewlayer制图上去。视图不会被常常重绘;相反,它的绘图会被缓存,在可用的地点都会使用缓存版本(bitmap backing storeState of Qatar。缓存的本子,实际上,正是layer。那么view的图片上下文也正是layer的图片上下文。

重视帧动漫

CAKeyframeAnimation是另一种UIKit未有暴表露来但功效强盛的类。和CABasicAnimation类似,CAKeyframeAnimation同样是CAPropertyAnimation的二个子类,它仍旧成效于单一的三个天性,不过和CABasicAnimation不等同的是,它不约束于设置三个胚胎和甘休的值,而是可以依据一连串随便的值来做动画。

示范代码:

CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
animation.keyPath = @"position.x";
animation.values = @[ @0, @10, @-10, @10, @0 ];
animation.keyTimes = @[ @0, @(1 / 6.0), @(3 / 6.0), @(5 / 6.0), @1 ];
animation.duration = 0.4;

animation.additive = YES;

[form.layer addAnimation:animation forKey:@"shake"];

在使用CAKeyframeAnimation做动漫时要求注意的是CAKeyframeAnimation并无法把当前layer的值作为第一帧动漫,那就形成动漫初阶时会突然跳到第一帧的值,再再动漫达成后复原到原本的值,所以为了动漫的平缓效果,我们需求开首和竣事时的关键帧来合作当前质量的值。

CAKeyframeAnimation再有其它一种方式来钦定动漫,就是运用CGPath。path属性能够用一种直观的办法,使用Core Graphics函数定义运动连串来绘制动漫。

示范代码:

- (void)viewDidLoad
{
    [super viewDidLoad];
    //create a path
    UIBezierPath *bezierPath = [[UIBezierPath alloc] init];
    [bezierPath moveToPoint:CGPointMake(0, 150)];
    [bezierPath addCurveToPoint:CGPointMake(300, 150) controlPoint1:CGPointMake(75, 0) controlPoint2:CGPointMake(225, 300)];

    //add the ship
    CALayer *shipLayer = [CALayer layer];
    shipLayer.frame = CGRectMake(0, 0, 64, 64);
    shipLayer.position = CGPointMake(0, 150);
    shipLayer.contents = (__bridge id)[UIImage imageNamed: @"Ship.png"].CGImage;
    [self.containerView.layer addSublayer:shipLayer];

    //create the keyframe animation
    CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
    animation.keyPath = @"position";
    animation.duration = 4.0;
    animation.path = bezierPath.CGPath;
    animation.rotationMode = kCAAnimationRotateAuto;

    [shipLayer addAnimation:animation forKey:nil];
}
  1. 用到了 transformLayer 分歧于其余layer (子图层仅仅绘制在图层表面 2d层级关系) 能够有3d层级的关系

故而浓烈学习layer依然很有不能缺少的,因为它能够达成都部队分view不可能成就的职分(比方,阴影、圆角、3d调换、透明遮罩、多级非线性动漫、路线动漫等)。特别是在动漫方便表现优越。 CALyaer 前面的 "CA" 代表的 " Core Animation "。但是CALayer 并不清楚具体的响应链(iOS通过视图层级关系用来传送触摸事件的编写制定),于是它并不可以知道响应事件,固然它提供了一部分主意来推断是或不是二个触点在图层的界定之内。

编造属性

在layer中,有一种属性其实是不设有的,如:transform.rotationtransform.rotationtransform.rotation等。因为CATransform3D并非二个目的,而是二个布局体,也尚无适合KVC相关属性,它们其实是CALayer用于拍卖动漫转变的诬捏属性。

它们不能够被一直利用。当对她们做动漫时,Core Animation自动地依据通过CAValueFunction来测算的值来更新transform属性。

CAValueFunction用以把大家赋给设想的transform.rotation简单浮点值转变来真正的用来摆放图层的CATransform3D矩阵值。大家能够透过安装CAPropertyAnimationvalueFunction属性来退换,那将会覆盖暗中认可的函数。

上行下效代码:

- (void)viewDidLoad
{
    [super viewDidLoad];
    //add the ship
    CALayer *shipLayer = [CALayer layer];
    shipLayer.frame = CGRectMake(0, 0, 128, 128);
    shipLayer.position = CGPointMake(150, 150);
    shipLayer.contents = (__bridge id)[UIImage imageNamed: @"Ship.png"].CGImage;
    [self.containerView.layer addSublayer:shipLayer];

    //animate the ship rotation
    CABasicAnimation *animation = [CABasicAnimation animation];
    animation.keyPath = @"transform.rotation";
    animation.duration = 2.0;
    animation.byValue = @(M_PI * 2);
    [shipLayer addAnimation:animation forKey:nil];
}

图上是由6个transformLayer 拼成的 用layer的transform属性 可决定分歧组成都部队分

我们一贯利用layer最佳是应用view的underlying layer 。 那样不仅能享受 UIView的高端api,也能接受到layer的性状。 layer是不协理 AutoLayout 的。大家得以行使AutoLayout 为view布局,那么她的layer的frame会跟随view frame改动。

动画组

CABasicAnimationCAKeyframeAnimation唯有功效于独立的属性,而CAAnimationGroup能够把这个动漫片组成在协同。CAAnimationGroup是另多个后续于CAAnimation的子类,它增加了八个animations数组的特性,用来组合别的动画。

亲自过问代码:

- (void)viewDidLoad
{
    [super viewDidLoad];

    //create a path
    UIBezierPath *bezierPath = [[UIBezierPath alloc] init];
    [bezierPath moveToPoint:CGPointMake(0, 150)];
    [bezierPath addCurveToPoint:CGPointMake(300, 150) 
                   controlPoint1:CGPointMake(75, 0) 
                   controlPoint2:CGPointMake(225, 300)];

    //draw the path using a CAShapeLayer
    CAShapeLayer *pathLayer = [CAShapeLayer layer];
    pathLayer.path = bezierPath.CGPath;
    pathLayer.fillColor = [UIColor clearColor].CGColor;
    pathLayer.strokeColor = [UIColor redColor].CGColor;
    pathLayer.lineWidth = 3.0f;
    [self.containerView.layer addSublayer:pathLayer];

    //add a colored layer
    CALayer *colorLayer = [CALayer layer];
    colorLayer.frame = CGRectMake(0, 0, 64, 64);
    colorLayer.position = CGPointMake(0, 150);
    colorLayer.backgroundColor = [UIColor greenColor].CGColor;
    [self.containerView.layer addSublayer:colorLayer];

    //create the position animation
    CAKeyframeAnimation *animation1 = [CAKeyframeAnimation animation];
    animation1.keyPath = @"position";
    animation1.path = bezierPath.CGPath;
    animation1.rotationMode = kCAAnimationRotateAuto;

    //create the color animation
    CABasicAnimation *animation2 = [CABasicAnimation animation];
    animation2.keyPath = @"backgroundColor";
    animation2.toValue = (__bridge id)[UIColor redColor].CGColor;

    //create group animation
    CAAnimationGroup *groupAnimation = [CAAnimationGroup animation];
    groupAnimation.animations = @[animation1, animation2]; 
    groupAnimation.duration = 4.0;

    //add the animation to the color layer
    [colorLayer addAnimation:groupAnimation forKey:nil];
}
  1. 纸盒人总体调控 用了sublayerTransform属性

layer的多少个基本特性:

过渡

属性动画只对layer的可动画属性起成效,假使要改成四个不可动漫属性(如图片、文本),可能从层级关系中加上或移除图层,属性动漫将不再起效果,这个时候,大家得以采用过渡来促成动漫效果。

为了创制四个连接动漫,我们将利用CATransition,相似是另二个CAAnimation的子类,和别的子类差别,CATransition有叁个type和subtype来标志转变效果。type属性是二个NSString类型,用来设置过渡动漫效果,可以被设置成如下类型:

  • kCATransitionFade
  • kCATransitionMoveIn
  • kCATransitionPush
  • kCATransitionReveal

透过subtype大家可以操纵动漫的大方向,它提供了之类七连串型:

  • kCATransitionFromRight
  • kCATransitionFromLeft
  • kCATransitionFromTop
  • kCATransitionFromBottom

示范代码:

- (IBAction)switchImage
{
    //set up crossfade transition
    CATransition *transition = [CATransition animation];
    transition.type = kCATransitionFade;

    //apply transition to imageview backing layer
    [self.imageView.layer addAnimation:transition forKey:nil];

    //cycle to next image
    UIImage *currentImage = self.imageView.image;
    NSUInteger index = [self.images indexOfObject:currentImage];
    index = (index   1) % [self.images count];
    self.imageView.image = self.images[index];
}

别的没啥好说 具体看代码 比较轻松 中意的star哦 博客园@itchycat

  • contents 是一个Any? ,但实际选取三个CGImage对象,假若是其余对象,图层将是白手。

隐式过渡

对于视图关联的图层,或然是其他隐式动漫的表现,过渡的天性依旧是被剥夺的,不过对于大家团结创制的图层,这意味对图层contents图片做的改动都会活动附上淡入淡出的卡通。

图片 2-图片 3示例

对图层树的动漫片

CATransition并不效率于钦赐的图层属性,那正是说大家可以在即便不能够纯粹获悉改换了怎么的意况下对图层做动漫,比如,在不知道UITableView哪一行被加上或然去除的情事下,直接就可以平滑地刷新它,或然在不清楚UIViewController内部的视图层级的情形下对多个不等的实例做衔接动漫。

在这里地,大家要是将接入动画增加到被影响图层的superlayer,就达成了对整个图层树增加过渡动漫。

UITabBarController丰富过渡动漫,示例代码:

#import "AppDelegate.h"
#import "FirstViewController.h" 
#import "SecondViewController.h"
#import 
@implementation AppDelegate
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame: [[UIScreen mainScreen] bounds]];
    UIViewController *viewController1 = [[FirstViewController alloc] init];
    UIViewController *viewController2 = [[SecondViewController alloc] init];
    self.tabBarController = [[UITabBarController alloc] init];
    self.tabBarController.viewControllers = @[viewController1, viewController2];
    self.tabBarController.delegate = self;
    self.window.rootViewController = self.tabBarController;
    [self.window makeKeyAndVisible];
    return YES;
}

- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController
{
    //set up crossfade transition
    CATransition *transition = [CATransition animation];
    transition.type = kCATransitionFade;

    //apply transition to tab bar controller's view
    [self.tabBarController.view.layer addAnimation:transition forKey:nil];
}

@end

图层少校会展现会对应的图像。

在动画进程中收回动漫

移除内定动漫:

- (void)removeAnimationForKey:(NSString *)key;

移除全体动漫:

- (void)removeAllAnimations;

  • contentGravity 相当于UIViewcontentMode 属性 , 有以下值

    • kCAGravityCenter
    • kCAGravityTop
    • kCAGravityBottom
    • kCAGravityLeft
    • kCAGravityRight
    • kCAGravityTopLeft
    • kCAGravityTopRight
    • kCAGravityBottomLeft
    • kCAGravityBottomRight
    • kCAGravityResize
    • kCAGravityResizeAspect
    • kCAGravityResizeAspectFill
  • contentsScale 图的像素尺寸和视图大小的比例,私下认可情状下它是五个值为1.0的浮点数,应该设置为相应的scale

图层时间

CAMediaTiming协议

CAMedia提姆ing探讨定义了在一段动漫内用来支配逝去岁月的性质的成团,CALayer和CAAnimation都完成了那一个左券,所以时间足以被专擅基于七个图层也许一段动漫的类调节。

本文由澳门威利斯人发布于威利斯人娱乐,转载请注明出处:拼出一个3D纸盒人,Techniques学习笔记

关键词: C 动画 Swift 纸盒 拼出