沿着贝塞尔曲线的一部分为UIView制作动画 [英] Animate a UIView along a part of a bezier path

查看:210
本文介绍了沿着贝塞尔曲线的一部分为UIView制作动画的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试沿着bezier路径的一部分动画UIView。我发现了一种使用此代码将视图移动到路径的任何部分的方法:

I'm trying animate a UIView along a portion of a bezier path. I found a way to move the the view to any part of the path using this code:

let animation = CAKeyframeAnimation(keyPath: "position")

animation.path = trackPath.cgPath

animation.rotationMode = kCAAnimationRotateAuto
animation.speed = 0
animation.timeOffset = offset
animation.duration = 1
animation.calculationMode = kCAAnimationPaced
square.layer.add(animation, forKey: "animate position along path")

但是,这只会将视图移动到所需的点,而不会为其设置动画。如何在Bezier路径的一部分上为视图设置动画?

However, this just moves the view to the desired point and doesn't animate it. How do you animate a view along over a portion of a bezier path?

谢谢

推荐答案

你可以通过修改时间来实现这个目的完整动画和包装它的动画组。

You can accomplish this by modifying the timing of the "complete" animation and a animation group that wraps it.

为了说明这种动画的时间是如何工作的,想象 - 而不是沿着路径设置动画的位置 - 颜色正在被动画化。然后,从一种颜色到另一种颜色的完整动画可以这样说明,其中右边的值是稍后的时间 - 所以最左边是起始值,最右边是结束值:

To illustrate how the timing of such an animation works, imagine – instead of animating a position along a path – that a color is being animated. Then, the complete animation from one color to another can be illustrated as this, where a value further to the right is at a later time — so that the very left is the start value and the very right is the end value:

请注意,此动画的时间是线性的。这是故意的,因为最终结果的时间将在稍后配置。

在这个动画中,想象一下我们只想制作动画中间三分,这部分动画:

In this animation, imagine that we're looking to animate only the middle third, this part of the animation:

动画只有动画的这一部分有几个步骤。

There are a few steps to animating only this part of the animation.

首先,将完整动画配置为具有线性定时(或者在沿着路径的动画的情况下;具有起搏的计算模式)并具有完整持续时间。

First, configure the "complete" animation to have linear timing (or in the case of an animation along a path; to have a paced calculation mode) and to have a the "complete" duration.

例如:如果您想动画动画的三分之一, 需要1秒,请配置完整的动画3秒。

For example: if you're looking to animate a third of the animation an have that take 1 second, configure the complete animation to take 3 seconds.

let relativeStart = 1.0/3.0
let relativeEnd   = 2.0/3.0

let duration      = 1.0
let innerDuration = duration / (relativeEnd - relativeStart) // 3 seconds

// configure the "complete" animation
animation.duration = innerDuration

这意味着当前的动画如下所示(完整动画):

This means that the animation currently is illustrated like this (the full animation):

接下来,为了让动画开始进入完整动画的三分之一,我们将其时间偏移了持续时间的三分之一:

Next, so that the animation "starts" a third of the way into the full animation, we "offset" its time by a third of the duration:

animation.timeOffset = relativeStart * innerDuration

现在动画如图所示这,抵消和愤怒从其最终值到其起始值:

Now the animation is illustrated like this, offset and wrapping from its end value to its start value:

接下来,我们只显示此动画的一部分,我们创建一个具有所需持续时间的动画组,并仅添加完整动画到它。

Next, so that we only display part of this animation, we create an animation group with the wanted duration and add only the "complete" animation to it.

let group = CAAnimationGroup()
group.animations = [animation]
group.duration = duration

即使这个组包含3秒长的动画,它也会在刚刚结束后结束1秒,意味着永远不会显示偏移完成动画的2秒。

Even though this group contains an animation that is 3 seconds long it will end after just 1 second, meaning that the 2 seconds of the offset "complete" animation will never be shown.

现在,组动画如下所示,在三分之一后结束完整动画:

Now the group animation is illustrated like this, ending after a third of the "complete" animation:

如果仔细观察,你会发现这个(未淡出的部分)是compl的中间三分之一eteanimation。

If you look closely you'll see that this (the part that isn't faded out) is the middle third of the "complete" animation.

现在该组为想要的值之间的动画设置动画,可以进一步配置它(组),然后添加到图层。例如,如果你想要这个部分动画反转,重复,并有一个时间曲线,你可以在组上配置这些东西:

Now that this group animates animates between the wanted values, it (the group) can be configured further and then added to a layer. For example, if you wanted this "partial" animation to reverse, repeat, and have a timing curve you would configure these things on the group:

group.repeatCount = HUGE
group.autoreverses = true
group.timingFunction = CAMediaTimingFunction(name: "easeInEaseOut")

使用这个额外的配置,动画组将如下所示:

With this additional configuration, the animation group would be illustrated like this:

作为一个更具体的例子,这是我使用这种技术创建的动画(实际上所有代码都来自该示例),它像钟摆一样来回移动图层。在这种情况下,完整动画是沿着一个完整圆的路径的位置动画

As a more concrete example, this is an animation that I created using this technique (in fact all the code is from that example) that moves a layer back and forth like a pendulum. In this case the "complete" animation was a "position" animation along a path that was a full circle

这篇关于沿着贝塞尔曲线的一部分为UIView制作动画的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆